79 lines
4.2 KiB
Go
79 lines
4.2 KiB
Go
package domain
|
|
|
|
import (
|
|
"testing"
|
|
"time"
|
|
)
|
|
|
|
func TestSCUMCapabilityGateDefaultsClosedWithoutProbeEvidence(t *testing.T) {
|
|
active := scumGateBinding()
|
|
requirement := SCUMCapabilityRequirement{Capability: SCUMDataCapabilityPlayerRead, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1", AssetDigests: []string{"sha256:query"}}
|
|
|
|
gate := EvaluateSCUMCapabilityGate(requirement, SCUMCapabilityEvidence{}, active, true, time.Now())
|
|
|
|
if gate.Enabled || gate.State != SCUMCapabilityGateDisabled || gate.ReasonCode != SCUMSafeErrorProbeMissing {
|
|
t.Fatalf("expected closed gate without evidence, got %#v", gate)
|
|
}
|
|
}
|
|
|
|
func TestSCUMCapabilityGateDefaultsClosedWhenProbeExecutorUnavailable(t *testing.T) {
|
|
active := scumGateBinding()
|
|
requirement := SCUMCapabilityRequirement{Capability: SCUMDataCapabilityPlayerRead, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1"}
|
|
evidence := SCUMCapabilityEvidence{Capability: SCUMDataCapabilityPlayerRead, Status: SCUMCapabilityEvidenceCompatible, Binding: active, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1"}
|
|
|
|
gate := EvaluateSCUMCapabilityGate(requirement, evidence, active, false, time.Now())
|
|
|
|
if gate.Enabled || gate.ReasonCode != SCUMSafeErrorProbeExecutorAbsent {
|
|
t.Fatalf("expected executor gate failure, got %#v", gate)
|
|
}
|
|
}
|
|
|
|
func TestSCUMCapabilityGateEnablesOnlyMatchingEvidence(t *testing.T) {
|
|
now := time.Date(2026, 8, 11, 12, 0, 0, 0, time.UTC)
|
|
active := scumGateBinding()
|
|
requirement := SCUMCapabilityRequirement{Capability: SCUMDataCapabilityVehicleRead, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1", AssetDigests: []string{"sha256:vehicle-query"}}
|
|
evidence := SCUMCapabilityEvidence{Capability: SCUMDataCapabilityVehicleRead, Status: SCUMCapabilityEvidenceCompatible, Binding: active, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1", AssetDigests: []string{"sha256:vehicle-query", "sha256:result-schema"}, ExpiresAt: now.Add(time.Hour)}
|
|
|
|
gate := EvaluateSCUMCapabilityGate(requirement, evidence, active, true, now)
|
|
|
|
if !gate.Enabled || gate.State != SCUMCapabilityGateEnabled || gate.ReasonCode != SCUMSafeErrorNone {
|
|
t.Fatalf("expected enabled gate, got %#v", gate)
|
|
}
|
|
}
|
|
|
|
func TestSCUMCapabilityGateRejectsMismatchedCurrentServiceEvidence(t *testing.T) {
|
|
now := time.Date(2026, 8, 11, 12, 0, 0, 0, time.UTC)
|
|
active := scumGateBinding()
|
|
requirement := SCUMCapabilityRequirement{Capability: SCUMDataCapabilityPositionRead, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1", AssetDigests: []string{"sha256:positions"}}
|
|
evidence := SCUMCapabilityEvidence{Capability: SCUMDataCapabilityPositionRead, Status: SCUMCapabilityEvidenceCompatible, Binding: active, AdapterVersion: "adapter-1", SchemaFingerprint: "schema-1", AssetDigests: []string{"sha256:positions"}, ExpiresAt: now.Add(time.Hour)}
|
|
|
|
changedBinding := evidence
|
|
changedBinding.Binding.DatabaseIdentity = "db-other"
|
|
if gate := EvaluateSCUMCapabilityGate(requirement, changedBinding, active, true, now); gate.Enabled || gate.ReasonCode != SCUMSafeErrorBindingMismatch {
|
|
t.Fatalf("expected binding mismatch, got %#v", gate)
|
|
}
|
|
|
|
changedFingerprint := evidence
|
|
changedFingerprint.SchemaFingerprint = "schema-other"
|
|
if gate := EvaluateSCUMCapabilityGate(requirement, changedFingerprint, active, true, now); gate.Enabled || gate.ReasonCode != SCUMSafeErrorFingerprintMismatch {
|
|
t.Fatalf("expected fingerprint mismatch, got %#v", gate)
|
|
}
|
|
|
|
changedDigest := evidence
|
|
changedDigest.AssetDigests = []string{"sha256:different"}
|
|
if gate := EvaluateSCUMCapabilityGate(requirement, changedDigest, active, true, now); gate.Enabled || gate.ReasonCode != SCUMSafeErrorDigestMismatch {
|
|
t.Fatalf("expected digest mismatch, got %#v", gate)
|
|
}
|
|
}
|
|
|
|
func TestDefaultSCUMSchemaProbeBoundsAreBoundedAndDiagnosticOnly(t *testing.T) {
|
|
bounds := DefaultSCUMSchemaProbeBounds()
|
|
if bounds.MaxObjects <= 0 || bounds.MaxSampleRows > 3 || bounds.TimeoutMS > 5000 || bounds.MaxResultBytes > 512*1024 {
|
|
t.Fatalf("unexpected unsafe default probe bounds: %#v", bounds)
|
|
}
|
|
}
|
|
|
|
func scumGateBinding() SCUMBindingIdentity {
|
|
return SCUMBindingIdentity{ServerInstanceID: "server-1", RunBindingID: "binding-1", RunEndpointID: "run-1", PluginID: "game.scum", PluginVersion: "0.1.6", AdapterVersion: "adapter-1", GameVersion: "scum-1", DatabaseIdentity: "db-current"}
|
|
}
|