Complete SCUM controlled deployment lifecycle
This commit is contained in:
@@ -0,0 +1,103 @@
|
||||
package service
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"browser.local/platform/domain"
|
||||
)
|
||||
|
||||
func scumDeploymentTestPlugin() domain.GamePlugin {
|
||||
return domain.GamePlugin{
|
||||
ID: "game.scum",
|
||||
CreateFields: []domain.PluginCreateField{
|
||||
{Key: "serverName", Type: "text", DefaultValue: "SCUM Test"},
|
||||
{Key: "gamePort", Type: "port", DefaultValue: "7777"},
|
||||
{Key: "queryPort", Type: "port", DefaultValue: "27015"},
|
||||
{Key: "maxPlayers", Type: "number", DefaultValue: "64"},
|
||||
},
|
||||
RuntimeProfiles: domain.GamePluginRuntimeProfiles{ServerDeployments: []domain.RuntimeServerDeploymentProfile{{
|
||||
Key: "scum-steamcmd-windows", Version: "1.0.0", SteamAppID: "3792580", ExecutableKey: "scum/server-executable", InstallRootKey: "server/install-root", ConfigKey: "scum/server-settings", ConfigFormat: "ini",
|
||||
ConfigMappings: []domain.RuntimeServerConfigMapping{{FieldKey: "serverName", ConfigKey: "server-settings.server-name", ValueType: "text", Required: true}, {FieldKey: "gamePort", ConfigKey: "server-settings.game-port", ValueType: "port", Required: true}, {FieldKey: "queryPort", ConfigKey: "server-settings.query-port", ValueType: "port", Required: true}, {FieldKey: "maxPlayers", ConfigKey: "server-settings.max-players", ValueType: "integer", Required: true}},
|
||||
VerificationChecks: []domain.RuntimeServerVerificationCheck{{Key: "executable", Kind: "executable.present", TargetKey: "scum/server-executable", Required: true}, {Key: "version", Kind: "version.matches", TargetKey: "scum/server-executable", Required: true}, {Key: "game-port", Kind: "port.bound", TargetKey: "game-port", Required: true}, {Key: "config", Kind: "config.readable", TargetKey: "scum/server-settings", Required: true}, {Key: "process", Kind: "process.healthy", TargetKey: "scum/server-executable", Required: true}},
|
||||
}}},
|
||||
}
|
||||
}
|
||||
|
||||
func TestSCUMDeploymentPlanSeparatesInstallAndAdopt(t *testing.T) {
|
||||
plugin := scumDeploymentTestPlugin()
|
||||
definition := domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeGuided, CreateInputs: map[string]string{"serverName": "Alpha", "gamePort": "7777", "queryPort": "27015", "maxPlayers": "64"}}
|
||||
plan, err := scumDeploymentPlan(plugin, definition, "install")
|
||||
if err != nil || plan == nil || plan.Operation != "install" || plan.SteamAppID != "3792580" {
|
||||
t.Fatalf("unexpected install plan: %+v, %v", plan, err)
|
||||
}
|
||||
definition.Mode = domain.ServerDeploymentModeExisting
|
||||
plan, err = scumDeploymentPlan(plugin, definition, "adopt")
|
||||
if err != nil || plan == nil || plan.Operation != "adopt" {
|
||||
t.Fatalf("unexpected adopt plan: %+v, %v", plan, err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestSCUMDeploymentEvidenceRequiresAllRequiredChecks(t *testing.T) {
|
||||
plugin := scumDeploymentTestPlugin()
|
||||
plan, err := scumDeploymentPlan(plugin, domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeGuided}, "install")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
result := domain.RunJobResult{State: domain.JobStateSucceeded, ExecutionResult: domain.JobExecutionResult{Kind: "scum.install.completed", ServerDeploymentEvidence: &domain.ServerDeploymentEvidence{TemplateKey: plan.TemplateKey, TemplateVersion: plan.TemplateVersion, PreflightState: "passed", DiscoveryState: "passed", MappingState: "applied", VerificationState: "passed", MappingResults: map[string]string{"serverName": "applied", "gamePort": "applied", "queryPort": "applied", "maxPlayers": "applied"}, VerificationResults: map[string]string{"executable": "passed", "version": "passed", "game-port": "passed", "config": "passed", "process": "passed"}}}}
|
||||
if err := validateSCUMDeploymentEvidence(plan, result); err != nil {
|
||||
t.Fatalf("valid evidence rejected: %v", err)
|
||||
}
|
||||
delete(result.ExecutionResult.ServerDeploymentEvidence.VerificationResults, "process")
|
||||
if err := validateSCUMDeploymentEvidence(plan, result); err == nil {
|
||||
t.Fatal("missing required process check was accepted")
|
||||
}
|
||||
}
|
||||
|
||||
func TestSCUMAdoptionMaySkipConfigurationMappingAfterDiscovery(t *testing.T) {
|
||||
plugin := scumDeploymentTestPlugin()
|
||||
plan, err := scumDeploymentPlan(plugin, domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeExisting, ServerRoot: `C:\\scum`}, "adopt")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
result := domain.RunJobResult{State: domain.JobStateSucceeded, ExecutionResult: domain.JobExecutionResult{Kind: "scum.adopt.completed", ServerDeploymentEvidence: &domain.ServerDeploymentEvidence{
|
||||
TemplateKey: plan.TemplateKey, TemplateVersion: plan.TemplateVersion, PreflightState: "passed", DiscoveryState: "passed", MappingState: "skipped", VerificationState: "passed",
|
||||
VerificationResults: map[string]string{"executable": "passed", "version": "passed", "game-port": "passed", "config": "passed", "process": "passed"},
|
||||
}}}
|
||||
if err := validateSCUMDeploymentEvidence(plan, result); err != nil {
|
||||
t.Fatalf("valid adoption evidence rejected: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestSCUMInstallRequiresDirectoryButAdoptionDoesNotRequireCreateInputs(t *testing.T) {
|
||||
plugin := scumDeploymentTestPlugin()
|
||||
install := domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeGuided, CreateInputs: map[string]string{"serverName": "Alpha"}}
|
||||
if err := validateScumDeploymentInputs(plugin, install); err == nil {
|
||||
t.Fatal("SCUM install without a directory was accepted")
|
||||
}
|
||||
install.ServerRoot = `C:\\scum`
|
||||
if err := validateScumDeploymentInputs(plugin, install); err != nil {
|
||||
t.Fatalf("SCUM install with defaults was rejected: %v", err)
|
||||
}
|
||||
adopt := domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeExisting, ServerRoot: `C:\\scum`}
|
||||
if err := validateScumDeploymentInputs(plugin, adopt); err != nil {
|
||||
t.Fatalf("SCUM adoption without create inputs was rejected: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestSCUMDeploymentFailureRequiresStableCode(t *testing.T) {
|
||||
plugin := scumDeploymentTestPlugin()
|
||||
plan, _ := scumDeploymentPlan(plugin, domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeExisting}, "adopt")
|
||||
result := domain.RunJobResult{State: domain.JobStateFailed, ExecutionResult: domain.JobExecutionResult{Kind: "scum.adopt.failed", ServerDeploymentEvidence: &domain.ServerDeploymentEvidence{TemplateKey: plan.TemplateKey, TemplateVersion: plan.TemplateVersion}}}
|
||||
if err := validateSCUMDeploymentEvidence(plan, result); err == nil {
|
||||
t.Fatal("failed deployment without failure code was accepted")
|
||||
}
|
||||
}
|
||||
|
||||
func TestSCUMDeploymentTargetMustMatchTemplate(t *testing.T) {
|
||||
plugin := scumDeploymentTestPlugin()
|
||||
plugin.RuntimeProfiles.ServerDeployments[0].SupportedTargets = []domain.RuntimeTarget{{OS: "windows", Arch: "amd64"}}
|
||||
definition := domain.ServerDeploymentDefinition{Mode: domain.ServerDeploymentModeGuided}
|
||||
if err := validateSCUMDeploymentTarget(plugin, definition, domain.RunEndpoint{Platform: "linux", Architecture: "amd64"}); err == nil {
|
||||
t.Fatal("linux Run target was accepted for the Windows-only SCUM template")
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user