Files
Servers/MoonlightServers.Daemon/ServerSystem/Handlers/StartupHandler.cs

86 lines
2.7 KiB
C#

using MoonlightServers.Daemon.ServerSystem.Enums;
using MoonlightServers.Daemon.ServerSystem.Interfaces;
using MoonlightServers.Daemon.ServerSystem.Models;
using Stateless;
namespace MoonlightServers.Daemon.ServerSystem.Handlers;
public class StartupHandler : IServerStateHandler
{
private IAsyncDisposable? ExitSubscription;
private readonly ServerContext Context;
private Server Server => Context.Server;
public StartupHandler(ServerContext context)
{
Context = context;
}
public async Task ExecuteAsync(StateMachine<ServerState, ServerTrigger>.Transition transition)
{
// Filter
if (transition is not {Source: ServerState.Offline, Destination: ServerState.Starting, Trigger: ServerTrigger.Start})
return;
// Plan:
// 1. Fetch latest configuration
// 2. Check if file system exists
// 3. Check if file system is mounted
// 4. Run file system checks
// 5. Create runtime
// 6. Attach console
// 7. Start runtime
// 1. Fetch latest configuration
// TODO
// Consider moving it out of the startup handler, as other handlers might need
// the updated config as well or add sorting into the handler registration to ensure they are executing in the correct order.
// Sort when building server, not when executing handlers
// 2. Check if file system exists
if (!await Server.RuntimeFileSystem.CheckExistsAsync())
await Server.RuntimeFileSystem.CreateAsync();
// 3. Check if file system is mounted
if (!await Server.RuntimeFileSystem.CheckMountedAsync())
await Server.RuntimeFileSystem.CheckMountedAsync();
// 4. Run file system checks
await Server.RuntimeFileSystem.PerformChecksAsync();
// 5. Create runtime
var hostPath = await Server.RuntimeFileSystem.GetPathAsync();
if (await Server.Runtime.CheckExistsAsync())
await Server.Runtime.DestroyAsync();
await Server.Runtime.CreateAsync(hostPath);
if (ExitSubscription == null)
{
ExitSubscription = await Server.Runtime.SubscribeExited(OnRuntimeExited);
}
// 6. Attach console
await Server.Console.AttachRuntimeAsync();
// 7. Start runtime
await Server.Runtime.StartAsync();
}
private async ValueTask OnRuntimeExited(int exitCode)
{
// TODO: Notify the crash handler component of the exit code
await Server.StateMachine.FireAsync(ServerTrigger.Exited);
}
public async ValueTask DisposeAsync()
{
if (ExitSubscription != null)
await ExitSubscription.DisposeAsync();
}
}