Skip to content
This repository has been archived by the owner on Mar 16, 2024. It is now read-only.

Commit

Permalink
Add discord integration and Fixed INI bug (#105)
Browse files Browse the repository at this point in the history
* added webhook

* added checks for duplicate values

if these values are empty the saving will fail, after this the manager fucks itself
  • Loading branch information
JensvandeWiel authored Nov 11, 2023
1 parent 487ba3c commit 7a9762e
Show file tree
Hide file tree
Showing 7 changed files with 190 additions and 58 deletions.
10 changes: 2 additions & 8 deletions frontend/src/pages/Server.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ import {
ForceStopServer,
GetServer, GetServerStatus,
SaveServer,
StartServer
StartServer, StopServer
} from "../../wailsjs/go/server/ServerController";
import {InstallUpdater} from "./InstallUpdater";
import {useAlert} from "../components/AlertProvider";
Expand Down Expand Up @@ -130,13 +130,7 @@ export const Server = ({id, className}: Props) => {

function onServerStopButtonClicked() {
addAlert("Stopping server...", "neutral")
SendRconCommand("saveworld", serv.ipAddress, serv.rconPort, serv.adminPassword)
.then((resp) => {
//send quit command
SendRconCommand("doexit", serv.ipAddress, serv.rconPort, serv.adminPassword)
.catch((err) => addAlert("error sending exit command: " + err, "danger"));
})
.catch((err) => addAlert("error sending save command: " + err, "danger"));
StopServer(serv.id).then(() => addAlert("Stopped server", "success")).catch((err) => addAlert("error stopping server: " + err, "danger"));
}

function onServerForceStopButtonClicked() {
Expand Down
13 changes: 12 additions & 1 deletion frontend/src/pages/server/Administration.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -190,8 +190,19 @@ export function Administration({setServ, serv, onServerFilesDeleted}: Props) {
<div className={'inline-block'}>
<Tooltip title={"Loads server config form ini first instead of json"}>
<Checkbox label="Use ini config (only reloads on server start) (not recommended)" checked={serv?.useIniConfig} onChange={(e) => setServ((p) => ({ ...p, useIniConfig: e.target.checked, convertValues: p.convertValues }))} />

</Tooltip>
<br/>
<Tooltip title={"Enables discord webhook messages"}>
<Checkbox label="Discord webhook messages" checked={serv?.discordWebHookEnabled} onChange={(e) => setServ((p) => ({ ...p, discordWebHookEnabled: e.target.checked, convertValues: p.convertValues }))} />
</Tooltip>
<Tooltip title={"The url from the webhook (if not set it will fail)"}>
<span>
<FormLabel>Discord webhook url</FormLabel>
<Input value={serv?.discordWebHook} onChange={(e) => setServ((p) => ({ ...p, discordWebHook: e.target.value, convertValues: p.convertValues }))}></Input>
</span>
</Tooltip>


</div>
</div>
</Card>
Expand Down
8 changes: 4 additions & 4 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,10 @@ func main() {

// Create an instance of the app structure
app := NewApp()
h := helpers.NewHelpersController()
c := config.NewConfigController()
s := server.NewServerController()
s := server.NewServerController(h)
i := installer.NewInstallerController(c)
h := helpers.NewHelpersController()

// Create application with options
err = wails.Run(&options.App{
Expand All @@ -59,19 +59,19 @@ func main() {
BackgroundColour: &options.RGBA{R: 255, G: 255, B: 255, A: 1},
OnStartup: func(ctx context.Context) {
app.startup(ctx)
h.Startup(ctx, WailsConfigFile)
c.Startup(ctx)
s.Startup(ctx)
i.Startup(ctx)
h.Startup(ctx, WailsConfigFile)
},
Logger: l,
LogLevel: wailsLogger.TRACE,
Bind: []interface{}{
app,
h,
c,
s,
i,
h,
},
})

Expand Down
83 changes: 83 additions & 0 deletions server/gus.go
Original file line number Diff line number Diff line change
Expand Up @@ -440,9 +440,92 @@ func (s *Server) SaveGameUserSettingsIni() error {
if err != nil {
return err
}

{
s.GameUserSettings.ServerSettings.RCONEnabled = true

if s.GameUserSettings.ServerSettings.RCONPort == 0 {
/*s.RCONPort = 28015
s.GameUserSettings.ServerSettings.RCONPort = 28015*/
s.GameUserSettings.ServerSettings.RCONPort = s.RCONPort
} else {
s.RCONPort = s.GameUserSettings.ServerSettings.RCONPort
}

if s.GameUserSettings.ServerSettings.ServerAdminPassword == "" {
/*ps, err := password.Generate(18, 9, 0, false, false)
if err != nil {
return err
}
s.AdminPassword = ps
s.GameUserSettings.ServerSettings.ServerAdminPassword = ps*/
s.GameUserSettings.ServerSettings.ServerAdminPassword = s.AdminPassword
} else {
s.AdminPassword = s.GameUserSettings.ServerSettings.ServerAdminPassword
}

if s.GameUserSettings.SessionSettings.MultiHome == "" {
/*s.IpAddress = "0.0.0.0"
s.GameUserSettings.SessionSettings.MultiHome = "0.0.0.0"*/
s.GameUserSettings.SessionSettings.MultiHome = s.IpAddress
} else {
s.IpAddress = s.GameUserSettings.SessionSettings.MultiHome
}

if s.GameUserSettings.SessionSettings.Port == 0 {
/*s.ServerPort = 7777
s.GameUserSettings.SessionSettings.Port = 7777*/
s.GameUserSettings.SessionSettings.Port = s.ServerPort
} else {
s.ServerPort = s.GameUserSettings.SessionSettings.Port
}

if s.GameUserSettings.SessionSettings.QueryPort == 0 {
/*s.QueryPort = 27015
s.GameUserSettings.SessionSettings.QueryPort = 27015*/
s.GameUserSettings.SessionSettings.QueryPort = s.QueryPort
} else {
s.QueryPort = s.GameUserSettings.SessionSettings.QueryPort
}

if s.GameUserSettings.SessionSettings.SessionName == "" {
/*s.ServerName = "A server managed by ArkAscendedServerManager"
s.GameUserSettings.SessionSettings.SessionName = "A server managed by ArkAscendedServerManager"*/
s.GameUserSettings.SessionSettings.SessionName = s.ServerName
} else {
s.ServerName = s.GameUserSettings.SessionSettings.SessionName
}

s.GameUserSettings.MultiHome.MultiHome = true

if s.GameUserSettings.ScriptEngineGameSession.MaxPlayers == 0 {
/*s.MaxPlayers = 70
s.GameUserSettings.ScriptEngineGameSession.MaxPlayers = 70*/
s.GameUserSettings.ScriptEngineGameSession.MaxPlayers = s.MaxPlayers
} else {
s.MaxPlayers = s.GameUserSettings.ScriptEngineGameSession.MaxPlayers
}
}

err := gusIni.SaveTo(filepath.Join(s.ServerPath, "ShooterGame\\Saved\\Config\\WindowsServer\\GameUserSettings.ini"))
if err != nil {
return err
}

runtime.EventsEmit(s.ctx, "reloadServers")
} else {

err = gusIni.ReflectFrom(&s.GameUserSettings)
s.GameUserSettings.ServerSettings.RCONEnabled = true
s.GameUserSettings.ServerSettings.RCONPort = s.RCONPort
s.GameUserSettings.ServerSettings.ServerAdminPassword = s.AdminPassword

s.GameUserSettings.SessionSettings.MultiHome = s.IpAddress
s.GameUserSettings.SessionSettings.Port = s.ServerPort
s.GameUserSettings.SessionSettings.QueryPort = s.QueryPort
s.GameUserSettings.SessionSettings.SessionName = s.ServerName
s.GameUserSettings.MultiHome.MultiHome = true
s.GameUserSettings.ScriptEngineGameSession.MaxPlayers = s.MaxPlayers
if err != nil {
return err
}
Expand Down
98 changes: 55 additions & 43 deletions server/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,26 +3,31 @@ package server
import (
"context"
"fmt"
"github.com/JensvandeWiel/ArkAscendedServerManager/helpers"
"github.com/keybase/go-ps"
"github.com/wailsapp/wails/v2/pkg/runtime"
"os/exec"
"path"
"path/filepath"
"strconv"
"strings"
"time"
)

// Server contains the server "stuff"

type Server struct {
Command *exec.Cmd `json:"-"`
ctx context.Context
helpers *helpers.HelpersController

//PREFERENCES

DisableUpdateOnStart bool `json:"disableUpdateOnStart"`
RestartOnServerQuit bool `json:"restartOnServerQuit"`
UseIniConfig bool `json:"useIniConfig"`
DisableUpdateOnStart bool `json:"disableUpdateOnStart"`
RestartOnServerQuit bool `json:"restartOnServerQuit"`
UseIniConfig bool `json:"useIniConfig"`
DiscordWebHook string `json:"discordWebHook"`
DiscordWebHookEnabled bool `json:"discordWebHookEnabled"`

//CONFIGURATION VARIABLES

Expand Down Expand Up @@ -76,47 +81,14 @@ func (s *Server) UpdateConfig() error {
return err
}

if s.UseIniConfig {
err = s.SaveGameIni()
if err != nil {
return err
}

err = s.SaveGameUserSettingsIni()
if err != nil {
return err
}
s.GameUserSettings.ServerSettings.RCONEnabled = true
s.RCONPort = s.GameUserSettings.ServerSettings.RCONPort
s.AdminPassword = s.GameUserSettings.ServerSettings.ServerAdminPassword
s.IpAddress = s.GameUserSettings.SessionSettings.MultiHome
s.ServerPort = s.GameUserSettings.SessionSettings.Port
s.QueryPort = s.GameUserSettings.SessionSettings.QueryPort
s.ServerName = s.GameUserSettings.SessionSettings.SessionName
s.GameUserSettings.MultiHome.MultiHome = true
s.MaxPlayers = s.GameUserSettings.ScriptEngineGameSession.MaxPlayers
runtime.EventsEmit(s.ctx, "reloadServers")

} else {
err = s.SaveGameIni()
if err != nil {
return err
}
err = s.SaveGameIni()
if err != nil {
return err
}

err = s.SaveGameUserSettingsIni()
if err != nil {
return err
}
s.GameUserSettings.ServerSettings.RCONEnabled = true
s.GameUserSettings.ServerSettings.RCONPort = s.RCONPort
s.GameUserSettings.ServerSettings.ServerAdminPassword = s.AdminPassword

s.GameUserSettings.SessionSettings.MultiHome = s.IpAddress
s.GameUserSettings.SessionSettings.Port = s.ServerPort
s.GameUserSettings.SessionSettings.QueryPort = s.QueryPort
s.GameUserSettings.SessionSettings.SessionName = s.ServerName
s.GameUserSettings.MultiHome.MultiHome = true
s.GameUserSettings.ScriptEngineGameSession.MaxPlayers = s.MaxPlayers
err = s.SaveGameUserSettingsIni()
if err != nil {
return err
}

return nil
Expand All @@ -141,10 +113,22 @@ func (s *Server) Start() error {
return fmt.Errorf("error starting server: %v", err)
}
runtime.EventsEmit(s.ctx, "onServerStart", s.Id)
if s.DiscordWebHookEnabled {
err := helpers.SendToDiscord(time.Now().Format(time.RFC822)+" ("+s.ServerAlias+") Server has started", s.DiscordWebHook)
if err != nil {
runtime.LogError(s.ctx, "Error sending message to discord: "+err.Error())
}
}
go func() {
_ = s.Command.Wait()

runtime.EventsEmit(s.ctx, "onServerExit", s.Id)
if s.DiscordWebHookEnabled {
err := helpers.SendToDiscord(time.Now().Format(time.RFC822)+" ("+s.ServerAlias+") Server has stopped", s.DiscordWebHook)
if err != nil {
runtime.LogError(s.ctx, "Error sending message to discord: "+err.Error())
}
}

/*//restart server on crash
if err != nil && s.RestartOnServerQuit {
Expand Down Expand Up @@ -189,6 +173,34 @@ func (s *Server) ForceStop() error {
return fmt.Errorf("error stopping server: %v", err)
}

if s.DiscordWebHookEnabled {
err := helpers.SendToDiscord(time.Now().Format(time.RFC822)+" ("+s.ServerAlias+") Initiated force stop", s.DiscordWebHook)
if err != nil {
runtime.LogError(s.ctx, "Error sending message to discord: "+err.Error())
}
}

return nil
}

func (s *Server) Stop() error {

if s.DiscordWebHookEnabled {
err := helpers.SendToDiscord(time.Now().Format(time.RFC822)+" ("+s.ServerAlias+") Initiated stop", s.DiscordWebHook)
if err != nil {
runtime.LogError(s.ctx, "Error sending message to discord: "+err.Error())
}
}

_, err := s.helpers.SendRconCommand("saveworld", s.IpAddress, s.RCONPort, s.AdminPassword)
if err != nil {
return err
}
_, err = s.helpers.SendRconCommand("doexit", s.IpAddress, s.RCONPort, s.AdminPassword)
if err != nil {
return err
}

return nil
}

Expand Down
23 changes: 22 additions & 1 deletion server/server_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import (
"context"
"encoding/json"
"fmt"
"github.com/JensvandeWiel/ArkAscendedServerManager/helpers"
"github.com/adrg/xdg"
"github.com/wailsapp/wails/v2/pkg/runtime"
"os"
Expand All @@ -30,13 +31,14 @@ const (
type ServerController struct {
ctx context.Context
Servers map[int]*Server
helpers *helpers.HelpersController
serverDir string
}

//region Struct Initialization and Creation

// NewServerController creates a new ServerController application struct
func NewServerController() *ServerController {
func NewServerController(hc *helpers.HelpersController) *ServerController {
return &ServerController{
Servers: make(map[int]*Server),
}
Expand Down Expand Up @@ -270,6 +272,25 @@ func (c *ServerController) ForceStopServer(id int) error {
return nil
}

func (c *ServerController) StopServer(id int) error {

server, exists := c.Servers[id]
if !exists {
err := fmt.Errorf("error stopping server " + strconv.Itoa(id) + ": server does not exist in map")
runtime.LogError(c.ctx, err.Error())
return err
}

err := server.Stop()
if err != nil {
err := fmt.Errorf("error stopping server " + strconv.Itoa(id) + ": " + err.Error())
runtime.LogError(c.ctx, err.Error())
return err
}

return nil
}

func (c *ServerController) GetServerStatus(id int) (bool, error) {
server, exists := c.Servers[id]
if !exists {
Expand Down
13 changes: 12 additions & 1 deletion server/server_controller_werr.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,22 @@ func (c *ServerController) CreateServerWithError(saveToConfig bool) (int, *Serve

// SaveServerWithError saves the server, and returns an error if it fails
func (c *ServerController) SaveServerWithError(server *Server) error {

server.GameUserSettings.ServerSettings.RCONEnabled = true
server.GameUserSettings.ServerSettings.RCONPort = server.RCONPort
server.GameUserSettings.ServerSettings.ServerAdminPassword = server.AdminPassword

server.GameUserSettings.SessionSettings.MultiHome = server.IpAddress
server.GameUserSettings.SessionSettings.Port = server.ServerPort
server.GameUserSettings.SessionSettings.QueryPort = server.QueryPort
server.GameUserSettings.SessionSettings.SessionName = server.ServerName
server.GameUserSettings.MultiHome.MultiHome = true
server.GameUserSettings.ScriptEngineGameSession.MaxPlayers = server.MaxPlayers

// Check if server is correct.
if err := CheckIfServerCorrect(*server); err != nil {
return fmt.Errorf("Parsing server instance failed: " + err.Error())
}

c.Servers[server.Id] = server
serverDir := path.Join(c.serverDir, strconv.Itoa(server.Id))

Expand Down

0 comments on commit 7a9762e

Please sign in to comment.