mirror of
https://github.com/ngoduykhanh/wireguard-ui.git
synced 2025-04-18 19:49:30 +03:00
chore: code adjustment (#512)
This commit is contained in:
parent
8cfe9a3d5b
commit
45849a2aee
9 changed files with 79 additions and 69 deletions
|
@ -75,7 +75,8 @@ func Login(db store.IStore) echo.HandlerFunc {
|
|||
|
||||
dbuser, err := db.GetUserByName(username)
|
||||
if err != nil {
|
||||
return c.JSON(http.StatusInternalServerError, jsonHTTPResponse{false, "Cannot query user from DB"})
|
||||
log.Infof("Cannot query user %s from DB", username)
|
||||
return c.JSON(http.StatusInternalServerError, jsonHTTPResponse{false, "Invalid credentials"})
|
||||
}
|
||||
|
||||
userCorrect := subtle.ConstantTimeCompare([]byte(username), []byte(dbuser.Username)) == 1
|
||||
|
@ -173,7 +174,7 @@ func Logout() echo.HandlerFunc {
|
|||
}
|
||||
|
||||
// LoadProfile to load user information
|
||||
func LoadProfile(db store.IStore) echo.HandlerFunc {
|
||||
func LoadProfile() echo.HandlerFunc {
|
||||
return func(c echo.Context) error {
|
||||
return c.Render(http.StatusOK, "profile.html", map[string]interface{}{
|
||||
"baseData": model.BaseData{Active: "profile", CurrentUser: currentUser(c), Admin: isAdmin(c)},
|
||||
|
@ -182,7 +183,7 @@ func LoadProfile(db store.IStore) echo.HandlerFunc {
|
|||
}
|
||||
|
||||
// UsersSettings handler
|
||||
func UsersSettings(db store.IStore) echo.HandlerFunc {
|
||||
func UsersSettings() echo.HandlerFunc {
|
||||
return func(c echo.Context) error {
|
||||
return c.Render(http.StatusOK, "users_settings.html", map[string]interface{}{
|
||||
"baseData": model.BaseData{Active: "users-settings", CurrentUser: currentUser(c), Admin: isAdmin(c)},
|
||||
|
|
59
main.go
59
main.go
|
@ -31,23 +31,23 @@ var (
|
|||
gitRef = "N/A"
|
||||
buildTime = fmt.Sprintf(time.Now().UTC().Format("01-02-2006 15:04:05"))
|
||||
// configuration variables
|
||||
flagDisableLogin bool = false
|
||||
flagBindAddress string = "0.0.0.0:5000"
|
||||
flagSmtpHostname string = "127.0.0.1"
|
||||
flagSmtpPort int = 25
|
||||
flagDisableLogin = false
|
||||
flagBindAddress = "0.0.0.0:5000"
|
||||
flagSmtpHostname = "127.0.0.1"
|
||||
flagSmtpPort = 25
|
||||
flagSmtpUsername string
|
||||
flagSmtpPassword string
|
||||
flagSmtpAuthType string = "NONE"
|
||||
flagSmtpNoTLSCheck bool = false
|
||||
flagSmtpEncryption string = "STARTTLS"
|
||||
flagSmtpHelo string = "localhost"
|
||||
flagSmtpAuthType = "NONE"
|
||||
flagSmtpNoTLSCheck = false
|
||||
flagSmtpEncryption = "STARTTLS"
|
||||
flagSmtpHelo = "localhost"
|
||||
flagSendgridApiKey string
|
||||
flagEmailFrom string
|
||||
flagEmailFromName string = "WireGuard UI"
|
||||
flagEmailFromName = "WireGuard UI"
|
||||
flagTelegramToken string
|
||||
flagTelegramAllowConfRequest bool = false
|
||||
flagTelegramFloodWait int = 60
|
||||
flagSessionSecret string = util.RandomString(32)
|
||||
flagTelegramAllowConfRequest = false
|
||||
flagTelegramFloodWait = 60
|
||||
flagSessionSecret = util.RandomString(32)
|
||||
flagWgConfTemplate string
|
||||
flagBasePath string
|
||||
flagSubnetRanges string
|
||||
|
@ -94,9 +94,9 @@ func init() {
|
|||
flag.StringVar(&flagSubnetRanges, "subnet-ranges", util.LookupEnvOrString("SUBNET_RANGES", flagSubnetRanges), "IP ranges to choose from when assigning an IP for a client.")
|
||||
|
||||
var (
|
||||
smtpPasswordLookup = util.LookupEnvOrString("SMTP_PASSWORD", flagSmtpPassword)
|
||||
sengridApiKeyLookup = util.LookupEnvOrString("SENDGRID_API_KEY", flagSendgridApiKey)
|
||||
sessionSecretLookup = util.LookupEnvOrString("SESSION_SECRET", flagSessionSecret)
|
||||
smtpPasswordLookup = util.LookupEnvOrString("SMTP_PASSWORD", flagSmtpPassword)
|
||||
sendgridApiKeyLookup = util.LookupEnvOrString("SENDGRID_API_KEY", flagSendgridApiKey)
|
||||
sessionSecretLookup = util.LookupEnvOrString("SESSION_SECRET", flagSessionSecret)
|
||||
)
|
||||
|
||||
// check empty smtpPassword env var
|
||||
|
@ -106,9 +106,9 @@ func init() {
|
|||
flag.StringVar(&flagSmtpPassword, "smtp-password", util.LookupEnvOrFile("SMTP_PASSWORD_FILE", flagSmtpPassword), "SMTP Password File")
|
||||
}
|
||||
|
||||
// check empty sengridApiKey env var
|
||||
if sengridApiKeyLookup != "" {
|
||||
flag.StringVar(&flagSendgridApiKey, "sendgrid-api-key", sengridApiKeyLookup, "Your sendgrid api key.")
|
||||
// check empty sendgridApiKey env var
|
||||
if sendgridApiKeyLookup != "" {
|
||||
flag.StringVar(&flagSendgridApiKey, "sendgrid-api-key", sendgridApiKeyLookup, "Your sendgrid api key.")
|
||||
} else {
|
||||
flag.StringVar(&flagSendgridApiKey, "sendgrid-api-key", util.LookupEnvOrFile("SENDGRID_API_KEY_FILE", flagSendgridApiKey), "File containing your sendgrid api key.")
|
||||
}
|
||||
|
@ -215,12 +215,12 @@ func main() {
|
|||
app.GET(util.BasePath+"/login", handler.LoginPage())
|
||||
app.POST(util.BasePath+"/login", handler.Login(db), handler.ContentTypeJson)
|
||||
app.GET(util.BasePath+"/logout", handler.Logout(), handler.ValidSession)
|
||||
app.GET(util.BasePath+"/profile", handler.LoadProfile(db), handler.ValidSession)
|
||||
app.GET(util.BasePath+"/users-settings", handler.UsersSettings(db), handler.ValidSession, handler.NeedsAdmin)
|
||||
app.GET(util.BasePath+"/profile", handler.LoadProfile(), handler.ValidSession)
|
||||
app.GET(util.BasePath+"/users-settings", handler.UsersSettings(), handler.ValidSession, handler.NeedsAdmin)
|
||||
app.POST(util.BasePath+"/update-user", handler.UpdateUser(db), handler.ValidSession, handler.ContentTypeJson)
|
||||
app.POST(util.BasePath+"/create-user", handler.CreateUser(db), handler.ValidSession, handler.ContentTypeJson, handler.NeedsAdmin)
|
||||
app.POST(util.BasePath+"/remove-user", handler.RemoveUser(db), handler.ValidSession, handler.ContentTypeJson, handler.NeedsAdmin)
|
||||
app.GET(util.BasePath+"/getusers", handler.GetUsers(db), handler.ValidSession, handler.NeedsAdmin)
|
||||
app.GET(util.BasePath+"/get-users", handler.GetUsers(db), handler.ValidSession, handler.NeedsAdmin)
|
||||
app.GET(util.BasePath+"/api/user/:username", handler.GetUser(db), handler.ValidSession)
|
||||
}
|
||||
|
||||
|
@ -276,10 +276,13 @@ func main() {
|
|||
if strings.HasPrefix(util.BindAddress, "unix://") {
|
||||
// Listen on unix domain socket.
|
||||
// https://github.com/labstack/echo/issues/830
|
||||
syscall.Unlink(util.BindAddress[6:])
|
||||
err := syscall.Unlink(util.BindAddress[6:])
|
||||
if err != nil {
|
||||
app.Logger.Fatalf("Cannot unlink unix socket: Error: %v", err)
|
||||
}
|
||||
l, err := net.Listen("unix", util.BindAddress[6:])
|
||||
if err != nil {
|
||||
app.Logger.Fatal(err)
|
||||
app.Logger.Fatalf("Cannot create unix socket. Error: %v", err)
|
||||
}
|
||||
app.Listener = l
|
||||
app.Logger.Fatal(app.Start(""))
|
||||
|
@ -292,7 +295,7 @@ func main() {
|
|||
func initServerConfig(db store.IStore, tmplDir fs.FS) {
|
||||
settings, err := db.GetGlobalSettings()
|
||||
if err != nil {
|
||||
log.Fatalf("Cannot get global settings: ", err)
|
||||
log.Fatalf("Cannot get global settings: %v", err)
|
||||
}
|
||||
|
||||
if _, err := os.Stat(settings.ConfigFilePath); err == nil {
|
||||
|
@ -302,23 +305,23 @@ func initServerConfig(db store.IStore, tmplDir fs.FS) {
|
|||
|
||||
server, err := db.GetServer()
|
||||
if err != nil {
|
||||
log.Fatalf("Cannot get server config: ", err)
|
||||
log.Fatalf("Cannot get server config: %v", err)
|
||||
}
|
||||
|
||||
clients, err := db.GetClients(false)
|
||||
if err != nil {
|
||||
log.Fatalf("Cannot get client config: ", err)
|
||||
log.Fatalf("Cannot get client config: %v", err)
|
||||
}
|
||||
|
||||
users, err := db.GetUsers()
|
||||
if err != nil {
|
||||
log.Fatalf("Cannot get user config: ", err)
|
||||
log.Fatalf("Cannot get user config: %v", err)
|
||||
}
|
||||
|
||||
// write config file
|
||||
err = util.WriteWireGuardServerConfig(tmplDir, server, clients, users, settings)
|
||||
if err != nil {
|
||||
log.Fatalf("Cannot create server config: ", err)
|
||||
log.Fatalf("Cannot create server config: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -37,14 +37,14 @@ func New(dbPath string) (*JsonDB, error) {
|
|||
}
|
||||
|
||||
func (o *JsonDB) Init() error {
|
||||
var clientPath string = path.Join(o.dbPath, "clients")
|
||||
var serverPath string = path.Join(o.dbPath, "server")
|
||||
var userPath string = path.Join(o.dbPath, "users")
|
||||
var wakeOnLanHostsPath string = path.Join(o.dbPath, "wake_on_lan_hosts")
|
||||
var serverInterfacePath string = path.Join(serverPath, "interfaces.json")
|
||||
var serverKeyPairPath string = path.Join(serverPath, "keypair.json")
|
||||
var globalSettingPath string = path.Join(serverPath, "global_settings.json")
|
||||
var hashesPath string = path.Join(serverPath, "hashes.json")
|
||||
var clientPath = path.Join(o.dbPath, "clients")
|
||||
var serverPath = path.Join(o.dbPath, "server")
|
||||
var userPath = path.Join(o.dbPath, "users")
|
||||
var wakeOnLanHostsPath = path.Join(o.dbPath, "wake_on_lan_hosts")
|
||||
var serverInterfacePath = path.Join(serverPath, "interfaces.json")
|
||||
var serverKeyPairPath = path.Join(serverPath, "keypair.json")
|
||||
var globalSettingPath = path.Join(serverPath, "global_settings.json")
|
||||
var hashesPath = path.Join(serverPath, "hashes.json")
|
||||
|
||||
// create directories if they do not exist
|
||||
if _, err := os.Stat(clientPath); os.IsNotExist(err) {
|
||||
|
@ -189,7 +189,7 @@ func (o *JsonDB) GetUsers() ([]model.User, error) {
|
|||
for _, i := range results {
|
||||
user := model.User{}
|
||||
|
||||
if err := json.Unmarshal([]byte(i), &user); err != nil {
|
||||
if err := json.Unmarshal(i, &user); err != nil {
|
||||
return users, fmt.Errorf("cannot decode user json structure: %v", err)
|
||||
}
|
||||
users = append(users, user)
|
||||
|
@ -267,7 +267,7 @@ func (o *JsonDB) GetClients(hasQRCode bool) ([]model.ClientData, error) {
|
|||
clientData := model.ClientData{}
|
||||
|
||||
// get client info
|
||||
if err := json.Unmarshal([]byte(f), &client); err != nil {
|
||||
if err := json.Unmarshal(f, &client); err != nil {
|
||||
return clients, fmt.Errorf("cannot decode client json structure: %v", err)
|
||||
}
|
||||
|
||||
|
@ -278,7 +278,7 @@ func (o *JsonDB) GetClients(hasQRCode bool) ([]model.ClientData, error) {
|
|||
|
||||
png, err := qrcode.Encode(util.BuildClientConfig(client, server, globalSettings), qrcode.Medium, 256)
|
||||
if err == nil {
|
||||
clientData.QRCode = "data:image/png;base64," + base64.StdEncoding.EncodeToString([]byte(png))
|
||||
clientData.QRCode = "data:image/png;base64," + base64.StdEncoding.EncodeToString(png)
|
||||
} else {
|
||||
fmt.Print("Cannot generate QR code: ", err)
|
||||
}
|
||||
|
@ -315,7 +315,7 @@ func (o *JsonDB) GetClientByID(clientID string, qrCodeSettings model.QRCodeSetti
|
|||
|
||||
png, err := qrcode.Encode(util.BuildClientConfig(client, server, globalSettings), qrcode.Medium, 256)
|
||||
if err == nil {
|
||||
clientData.QRCode = "data:image/png;base64," + base64.StdEncoding.EncodeToString([]byte(png))
|
||||
clientData.QRCode = "data:image/png;base64," + base64.StdEncoding.EncodeToString(png)
|
||||
} else {
|
||||
fmt.Print("Cannot generate QR code: ", err)
|
||||
}
|
||||
|
|
|
@ -23,7 +23,7 @@ func (o *JsonDB) GetWakeOnLanHosts() ([]model.WakeOnLanHost, error) {
|
|||
host := model.WakeOnLanHost{}
|
||||
|
||||
// get client info
|
||||
if err := json.Unmarshal([]byte(f), &host); err != nil {
|
||||
if err := json.Unmarshal(f, &host); err != nil {
|
||||
return hosts, fmt.Errorf("cannot decode client json structure: %v", err)
|
||||
}
|
||||
|
||||
|
|
|
@ -26,8 +26,8 @@ var (
|
|||
Bot *echotron.API
|
||||
BotMutex sync.RWMutex
|
||||
|
||||
floodWait = make(map[int64]int64, 0)
|
||||
floodMessageSent = make(map[int64]struct{}, 0)
|
||||
floodWait = make(map[int64]int64)
|
||||
floodMessageSent = make(map[int64]struct{})
|
||||
)
|
||||
|
||||
func Start(initDeps TgBotInitDependencies) (err error) {
|
||||
|
@ -84,12 +84,15 @@ func Start(initDeps TgBotInitDependencies) (err error) {
|
|||
continue
|
||||
}
|
||||
floodMessageSent[userid] = struct{}{}
|
||||
bot.SendMessage(
|
||||
_, err := bot.SendMessage(
|
||||
fmt.Sprintf("You can only request your configs once per %d minutes", FloodWait),
|
||||
userid,
|
||||
&echotron.MessageOptions{
|
||||
ReplyToMessageID: update.Message.ID,
|
||||
})
|
||||
if err != nil {
|
||||
log.Errorf("Failed to send telegram message. Error %v", err)
|
||||
}
|
||||
continue
|
||||
}
|
||||
floodWait[userid] = time.Now().Unix()
|
||||
|
@ -100,12 +103,15 @@ func Start(initDeps TgBotInitDependencies) (err error) {
|
|||
for _, f := range failed {
|
||||
messageText += f + "\n"
|
||||
}
|
||||
bot.SendMessage(
|
||||
_, err := bot.SendMessage(
|
||||
messageText,
|
||||
userid,
|
||||
&echotron.MessageOptions{
|
||||
ReplyToMessageID: update.Message.ID,
|
||||
})
|
||||
if err != nil {
|
||||
log.Errorf("Failed to send telegram message. Error %v", err)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -96,7 +96,7 @@ Users Settings
|
|||
$.ajax({
|
||||
cache: false,
|
||||
method: 'GET',
|
||||
url: '{{.basePath}}/getusers',
|
||||
url: '{{.basePath}}/get-users',
|
||||
dataType: 'json',
|
||||
contentType: "application/json",
|
||||
success: function (data) {
|
||||
|
|
|
@ -3,5 +3,5 @@ package util
|
|||
import "sync"
|
||||
|
||||
var IPToSubnetRange = map[string]uint16{}
|
||||
var TgUseridToClientID = map[int64]([]string){}
|
||||
var TgUseridToClientID = map[int64][]string{}
|
||||
var TgUseridToClientIDMutex sync.RWMutex
|
||||
|
|
|
@ -2,6 +2,7 @@ package util
|
|||
|
||||
import (
|
||||
"encoding/base64"
|
||||
"errors"
|
||||
"fmt"
|
||||
"golang.org/x/crypto/bcrypt"
|
||||
)
|
||||
|
@ -20,7 +21,7 @@ func VerifyHash(base64Hash string, plaintext string) (bool, error) {
|
|||
return false, fmt.Errorf("cannot decode base64 hash: %w", err)
|
||||
}
|
||||
err = bcrypt.CompareHashAndPassword(hash, []byte(plaintext))
|
||||
if err == bcrypt.ErrMismatchedHashAndPassword {
|
||||
if errors.Is(err, bcrypt.ErrMismatchedHashAndPassword) {
|
||||
return false, nil
|
||||
}
|
||||
if err != nil {
|
||||
|
|
35
util/util.go
35
util/util.go
|
@ -7,7 +7,6 @@ import (
|
|||
"fmt"
|
||||
"io"
|
||||
"io/fs"
|
||||
"io/ioutil"
|
||||
"math/rand"
|
||||
"net"
|
||||
"os"
|
||||
|
@ -189,7 +188,7 @@ func GetInterfaceIPs() ([]model.Interface, error) {
|
|||
return nil, err
|
||||
}
|
||||
|
||||
var interfaceList = []model.Interface{}
|
||||
var interfaceList []model.Interface
|
||||
|
||||
// get interface's ip addresses
|
||||
for _, i := range ifaces {
|
||||
|
@ -230,9 +229,9 @@ func GetPublicIP() (model.Interface, error) {
|
|||
consensus := externalip.NewConsensus(&cfg, nil)
|
||||
|
||||
// add trusted voters
|
||||
consensus.AddVoter(externalip.NewHTTPSource("http://checkip.amazonaws.com/"), 1)
|
||||
consensus.AddVoter(externalip.NewHTTPSource("https://checkip.amazonaws.com/"), 1)
|
||||
consensus.AddVoter(externalip.NewHTTPSource("http://whatismyip.akamai.com"), 1)
|
||||
consensus.AddVoter(externalip.NewHTTPSource("http://ifconfig.top"), 1)
|
||||
consensus.AddVoter(externalip.NewHTTPSource("https://ifconfig.top"), 1)
|
||||
|
||||
publicInterface := model.Interface{}
|
||||
publicInterface.Name = "Public Address"
|
||||
|
@ -244,7 +243,7 @@ func GetPublicIP() (model.Interface, error) {
|
|||
publicInterface.IPAddress = ip.String()
|
||||
}
|
||||
|
||||
// error handling happend above, no need to pass it through
|
||||
// error handling happened above, no need to pass it through
|
||||
return publicInterface, nil
|
||||
}
|
||||
|
||||
|
@ -292,7 +291,7 @@ func GetAllocatedIPs(ignoreClientID string) ([]string, error) {
|
|||
// append client's addresses to the result
|
||||
for _, f := range records {
|
||||
client := model.Client{}
|
||||
if err := json.Unmarshal([]byte(f), &client); err != nil {
|
||||
if err := json.Unmarshal(f, &client); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
|
@ -336,15 +335,15 @@ func GetBroadcastIP(n *net.IPNet) net.IP {
|
|||
|
||||
// GetBroadcastAndNetworkAddrsLookup get the ip address that can't be used with current server interfaces
|
||||
func GetBroadcastAndNetworkAddrsLookup(interfaceAddresses []string) map[string]bool {
|
||||
list := make(map[string]bool, 0)
|
||||
list := make(map[string]bool)
|
||||
for _, ifa := range interfaceAddresses {
|
||||
_, net, err := net.ParseCIDR(ifa)
|
||||
_, netAddr, err := net.ParseCIDR(ifa)
|
||||
if err != nil {
|
||||
continue
|
||||
}
|
||||
|
||||
broadcastAddr := GetBroadcastIP(net).String()
|
||||
networkAddr := net.IP.String()
|
||||
broadcastAddr := GetBroadcastIP(netAddr).String()
|
||||
networkAddr := netAddr.IP.String()
|
||||
list[broadcastAddr] = true
|
||||
list[networkAddr] = true
|
||||
}
|
||||
|
@ -354,14 +353,14 @@ func GetBroadcastAndNetworkAddrsLookup(interfaceAddresses []string) map[string]b
|
|||
// GetAvailableIP get the ip address that can be allocated from an CIDR
|
||||
// We need interfaceAddresses to find real broadcast and network addresses
|
||||
func GetAvailableIP(cidr string, allocatedList, interfaceAddresses []string) (string, error) {
|
||||
ip, net, err := net.ParseCIDR(cidr)
|
||||
ip, netAddr, err := net.ParseCIDR(cidr)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
|
||||
unavailableIPs := GetBroadcastAndNetworkAddrsLookup(interfaceAddresses)
|
||||
|
||||
for ip := ip.Mask(net.Mask); net.Contains(ip); inc(ip) {
|
||||
for ip := ip.Mask(netAddr.Mask); netAddr.Contains(ip); inc(ip) {
|
||||
available := true
|
||||
suggestedAddr := ip.String()
|
||||
for _, allocatedAddr := range allocatedList {
|
||||
|
@ -386,7 +385,7 @@ func ValidateIPAllocation(serverAddresses []string, ipAllocatedList []string, ip
|
|||
|
||||
// clientCIDR must be in CIDR format
|
||||
if ip == nil {
|
||||
return false, fmt.Errorf("Invalid ip allocation input %s. Must be in CIDR format", clientCIDR)
|
||||
return false, fmt.Errorf("invalid ip allocation input %s. Must be in CIDR format", clientCIDR)
|
||||
}
|
||||
|
||||
// return false immediately if the ip is already in use (in ipAllocatedList)
|
||||
|
@ -398,7 +397,7 @@ func ValidateIPAllocation(serverAddresses []string, ipAllocatedList []string, ip
|
|||
|
||||
// even if it is not in use, we still need to check if it
|
||||
// belongs to a network of the server.
|
||||
var isValid bool = false
|
||||
var isValid = false
|
||||
for _, serverCIDR := range serverAddresses {
|
||||
_, serverNet, _ := net.ParseCIDR(serverCIDR)
|
||||
if serverNet.Contains(ip) {
|
||||
|
@ -437,7 +436,7 @@ func findSubnetRangeForIP(cidr string) (uint16, error) {
|
|||
}
|
||||
}
|
||||
}
|
||||
return 0, fmt.Errorf("Subnet range not found for this IP")
|
||||
return 0, fmt.Errorf("subnet range not found for this IP")
|
||||
}
|
||||
|
||||
// FillClientSubnetRange to fill subnet ranges client belongs to, does nothing if SRs are not found
|
||||
|
@ -470,11 +469,11 @@ func ValidateAndFixSubnetRanges(db store.IStore) error {
|
|||
var serverSubnets []*net.IPNet
|
||||
for _, addr := range server.Interface.Addresses {
|
||||
addr = strings.TrimSpace(addr)
|
||||
_, net, err := net.ParseCIDR(addr)
|
||||
_, netAddr, err := net.ParseCIDR(addr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
serverSubnets = append(serverSubnets, net)
|
||||
serverSubnets = append(serverSubnets, netAddr)
|
||||
}
|
||||
|
||||
for _, rng := range SubnetRangesOrder {
|
||||
|
@ -544,7 +543,7 @@ func WriteWireGuardServerConfig(tmplDir fs.FS, serverConfig model.Server, client
|
|||
|
||||
// if set, read wg.conf template from WgConfTemplate
|
||||
if len(WgConfTemplate) > 0 {
|
||||
fileContentBytes, err := ioutil.ReadFile(WgConfTemplate)
|
||||
fileContentBytes, err := os.ReadFile(WgConfTemplate)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue