public void Dispose() { foreach (var m in _monitors) { m.Dispose(); } _monitors.Clear(); if (_starbound != null) { _starbound.Dispose(); _starbound = null; } }
public void Dispose() { //Dispose all the monitors foreach (var m in _monitors) { m.Dispose(); } _monitors.Clear(); //Force the server to close. if (_starbound != null) { _starbound.Dispose(); _starbound = null; } }
/// <summary> /// Runs the server, reading its input until its closed. /// </summary> /// <returns></returns> public async Task Run(System.Threading.CancellationToken cancellationToken) { //Make sure path exists string path = Path.Combine(WorkingDirectory, ExecutableName); if (!File.Exists(path)) { Logger.LogError("Cannot start server as the executable '{0}' does not exist", path); return; } //Load the settings Logger.Log("Loading Settings..."); //Make sure the configuration is valid if (!await Configurator.TryLoadAsync()) { Logger.LogError("Cannot start server as the configuration is invalid, make sure you -import before use. see documentation for reference.", ConfigurationFile); return; } //Update the start time statistics. StartTime = DateTime.UtcNow; //Invoke the start event foreach (var m in _monitors) { try { Logger.Log("OnServerPreStart :: {0}", m.Name); await m.OnServerPreStart(); } catch (Exception e) { Logger.LogError(e, "OnServerStart ERR :: " + m.Name + " :: {0}"); } } //Saving the settings Logger.Log("Saving Settings before launch..."); await SaveConfigurationAsync(); #region Process Handling //Destroy the rcon reference. We will replace it with a new one later. Rcon = null; if (_starbound != null) { Logger.Log("Cleaning up old process"); await _starbound.StopAsync(); _starbound.Dispose(); } //Start the process _terminate = false; _starbound = new SBProcess(path, WorkingDirectory, Logger.Child("SB")); _starbound.Exited += async() => { Logger.Log("SB Process has exited!"); //Tell us to terminate _terminate = true; //Validate the shutdown message, setting default if there isnt one LastShutdownReason = LastShutdownReason ?? "Server closed for unkown reason"; foreach (var m in _monitors) { try { Logger.Log("OnServerExit {0}", m.Name); await m.OnServerExit(LastShutdownReason); } catch (Exception e) { Logger.LogError(e, "OnServerExit ERR - " + m.Name + ": {0}"); } } }; Logger.Log("Staring Starbound Process"); LastShutdownReason = null; _starbound.Start(); //Try and initialize the rcon. if (Configurator.RconServerPort > 0) { Rcon = new Rcon.StarboundRconClient(this); OnRconClientCreated?.Invoke(this, Rcon); Logger.Log("Created RCON Client."); } #region Invoke the start event foreach (var m in _monitors) { try { Logger.Log("OnServerStart :: {0}", m.Name); await m.OnServerStart(); } catch (Exception e) { Logger.LogError(e, "OnServerStart ERR :: " + m.Name + " :: {0}"); } } #endregion try { //Handle the messages Logger.Log("Handling Messages"); while (!_terminate && !cancellationToken.IsCancellationRequested) { string[] logs = await _starbound.ReadStandardOutputAsync(); foreach (var l in logs) { _terminate = await ProcessLine(l); if (_terminate) { break; } } //wait some tiny amount of time await Task.Delay(100, cancellationToken); } //We have exited the loop, probably because we have been terminated Logger.Log("Left the read loop"); } catch (Exception e) { Logger.LogError(e, "CRITICAL ERROR IN RUNTIME: {0}"); LastShutdownReason = "Critical Error: " + e.Message + "\n" + e.StackTrace; } #endregion //We have terminated, so dispose of us properly Logger.Log("Attempting to terminate process just in case of internal error."); await _starbound.StopAsync(); Logger.Log("Terminated Succesfully, disposing"); _starbound.Dispose(); _starbound = null; }