summaryrefslogtreecommitdiff
path: root/internal/storage/seed_test.go
diff options
context:
space:
mode:
Diffstat (limited to 'internal/storage/seed_test.go')
-rw-r--r--internal/storage/seed_test.go97
1 files changed, 97 insertions, 0 deletions
diff --git a/internal/storage/seed_test.go b/internal/storage/seed_test.go
new file mode 100644
index 0000000..cd7c8e7
--- /dev/null
+++ b/internal/storage/seed_test.go
@@ -0,0 +1,97 @@
+package storage
+
+import (
+ "encoding/json"
+ "testing"
+
+ "github.com/thepeterstone/claudomator/internal/role"
+)
+
+func TestSeedRoleConfigs_CreatesAndActivatesBuilder(t *testing.T) {
+ db := testDB(t)
+
+ if err := db.SeedRoleConfigs(); err != nil {
+ t.Fatalf("SeedRoleConfigs: %v", err)
+ }
+
+ row, err := db.GetActiveRoleConfig("builder")
+ if err != nil {
+ t.Fatalf("GetActiveRoleConfig(builder): %v", err)
+ }
+ if row.Version != 1 {
+ t.Errorf("expected version 1, got %d", row.Version)
+ }
+ if row.ProposedBy != "seed" {
+ t.Errorf("expected proposed_by 'seed', got %q", row.ProposedBy)
+ }
+
+ var cfg role.RoleConfig
+ if err := json.Unmarshal([]byte(row.ConfigJSON), &cfg); err != nil {
+ t.Fatalf("unmarshal seeded config: %v", err)
+ }
+ if cfg.Role != "builder" {
+ t.Errorf("cfg.Role = %q, want builder", cfg.Role)
+ }
+ if cfg.SystemPrompt == "" {
+ t.Error("cfg.SystemPrompt is empty, want the decompose-or-implement guidance")
+ }
+ if len(cfg.EscalationLadder) != 2 {
+ t.Fatalf("expected 2 escalation tiers, got %d", len(cfg.EscalationLadder))
+ }
+ if cfg.EscalationLadder[0].Candidates[0].Provider != "claude" {
+ t.Errorf("tier 0 provider = %q, want claude", cfg.EscalationLadder[0].Candidates[0].Provider)
+ }
+}
+
+func TestSeedRoleConfigs_Idempotent_DoesNotDuplicateOrOverwrite(t *testing.T) {
+ db := testDB(t)
+
+ if err := db.SeedRoleConfigs(); err != nil {
+ t.Fatalf("first SeedRoleConfigs: %v", err)
+ }
+ if err := db.SeedRoleConfigs(); err != nil {
+ t.Fatalf("second SeedRoleConfigs: %v", err)
+ }
+
+ versions, err := db.ListRoleConfigVersions("builder")
+ if err != nil {
+ t.Fatalf("ListRoleConfigVersions: %v", err)
+ }
+ if len(versions) != 1 {
+ t.Fatalf("expected exactly 1 version after calling SeedRoleConfigs twice, got %d", len(versions))
+ }
+}
+
+func TestSeedRoleConfigs_DoesNotOverwriteHumanCustomizedVersion(t *testing.T) {
+ db := testDB(t)
+
+ // A human (or the retro role's propose_role_config tool) already
+ // created and activated their own version before the seed ever ran.
+ custom, err := db.CreateRoleConfig("builder", `{"role":"builder","system_prompt":"custom prompt"}`, "human")
+ if err != nil {
+ t.Fatalf("CreateRoleConfig: %v", err)
+ }
+ if err := db.ActivateRoleConfigVersion("builder", custom.Version); err != nil {
+ t.Fatalf("ActivateRoleConfigVersion: %v", err)
+ }
+
+ if err := db.SeedRoleConfigs(); err != nil {
+ t.Fatalf("SeedRoleConfigs: %v", err)
+ }
+
+ row, err := db.GetActiveRoleConfig("builder")
+ if err != nil {
+ t.Fatalf("GetActiveRoleConfig: %v", err)
+ }
+ if row.ProposedBy != "human" {
+ t.Errorf("active role config proposed_by = %q, want unchanged 'human' -- seed must not overwrite a human-authored active version", row.ProposedBy)
+ }
+
+ versions, err := db.ListRoleConfigVersions("builder")
+ if err != nil {
+ t.Fatalf("ListRoleConfigVersions: %v", err)
+ }
+ if len(versions) != 1 {
+ t.Fatalf("expected exactly 1 version (seed must not create a competing draft), got %d", len(versions))
+ }
+}