From 2345da106a7b3ee5adc3102a42564b1e4e7ae087 Mon Sep 17 00:00:00 2001 From: Eric Rakestraw Date: Wed, 5 Aug 2026 00:42:22 +0000 Subject: [PATCH] Centralize location LLM assets --- .../prompts/dnd.location_occurrences.yaml | 0 .../prompts/instructions.md | 0 .../prompts/locations.md | 0 .../dnd/location-occurrences}/prompts/task.md | 0 .../dnd_location_occurrences_llm.v1.json | 0 .../extract}/prompts/dnd.locations.yaml | 0 .../extract}/prompts/instructions.md | 0 .../dnd/locations/extract}/prompts/task.md | 0 .../schemas/dnd_locations_llm.v1.json | 0 .../normalize}/prompts/candidates.md | 0 .../prompts/dnd.locations.normalize.yaml | 0 .../dnd/locations/normalize}/prompts/task.md | 0 .../dnd/extract/locationoccurrences/assets.go | 6 --- .../locationoccurrences/prompt_assets.go | 37 +++++++++++++++---- .../dnd/extract/locationoccurrences/schema.go | 8 +++- .../modules/dnd/extract/locations/assets.go | 6 --- .../dnd/extract/locations/prompt_assets.go | 35 +++++++++++++++--- .../modules/dnd/extract/locations/schema.go | 8 +++- .../modules/dnd/normalize/locations/assets.go | 6 --- .../dnd/normalize/locations/prompt_assets.go | 31 +++++++++++++--- 20 files changed, 97 insertions(+), 40 deletions(-) rename {internal/modules/dnd/extract/locationoccurrences/assets => assets/dnd/location-occurrences}/prompts/dnd.location_occurrences.yaml (100%) rename {internal/modules/dnd/extract/locationoccurrences/assets => assets/dnd/location-occurrences}/prompts/instructions.md (100%) rename {internal/modules/dnd/extract/locationoccurrences/assets => assets/dnd/location-occurrences}/prompts/locations.md (100%) rename {internal/modules/dnd/extract/locationoccurrences/assets => assets/dnd/location-occurrences}/prompts/task.md (100%) rename {internal/modules/dnd/extract/locationoccurrences/assets => assets/dnd/location-occurrences}/schemas/dnd_location_occurrences_llm.v1.json (100%) rename {internal/modules/dnd/extract/locations/assets => assets/dnd/locations/extract}/prompts/dnd.locations.yaml (100%) rename {internal/modules/dnd/extract/locations/assets => assets/dnd/locations/extract}/prompts/instructions.md (100%) rename {internal/modules/dnd/extract/locations/assets => assets/dnd/locations/extract}/prompts/task.md (100%) rename {internal/modules/dnd/extract/locations/assets => assets/dnd/locations/extract}/schemas/dnd_locations_llm.v1.json (100%) rename {internal/modules/dnd/normalize/locations/assets => assets/dnd/locations/normalize}/prompts/candidates.md (100%) rename {internal/modules/dnd/normalize/locations/assets => assets/dnd/locations/normalize}/prompts/dnd.locations.normalize.yaml (100%) rename {internal/modules/dnd/normalize/locations/assets => assets/dnd/locations/normalize}/prompts/task.md (100%) delete mode 100644 internal/modules/dnd/extract/locationoccurrences/assets.go delete mode 100644 internal/modules/dnd/extract/locations/assets.go delete mode 100644 internal/modules/dnd/normalize/locations/assets.go diff --git a/internal/modules/dnd/extract/locationoccurrences/assets/prompts/dnd.location_occurrences.yaml b/assets/dnd/location-occurrences/prompts/dnd.location_occurrences.yaml similarity index 100% rename from internal/modules/dnd/extract/locationoccurrences/assets/prompts/dnd.location_occurrences.yaml rename to assets/dnd/location-occurrences/prompts/dnd.location_occurrences.yaml diff --git a/internal/modules/dnd/extract/locationoccurrences/assets/prompts/instructions.md b/assets/dnd/location-occurrences/prompts/instructions.md similarity index 100% rename from internal/modules/dnd/extract/locationoccurrences/assets/prompts/instructions.md rename to assets/dnd/location-occurrences/prompts/instructions.md diff --git a/internal/modules/dnd/extract/locationoccurrences/assets/prompts/locations.md b/assets/dnd/location-occurrences/prompts/locations.md similarity index 100% rename from internal/modules/dnd/extract/locationoccurrences/assets/prompts/locations.md rename to assets/dnd/location-occurrences/prompts/locations.md diff --git a/internal/modules/dnd/extract/locationoccurrences/assets/prompts/task.md b/assets/dnd/location-occurrences/prompts/task.md similarity index 100% rename from internal/modules/dnd/extract/locationoccurrences/assets/prompts/task.md rename to assets/dnd/location-occurrences/prompts/task.md diff --git a/internal/modules/dnd/extract/locationoccurrences/assets/schemas/dnd_location_occurrences_llm.v1.json b/assets/dnd/location-occurrences/schemas/dnd_location_occurrences_llm.v1.json similarity index 100% rename from internal/modules/dnd/extract/locationoccurrences/assets/schemas/dnd_location_occurrences_llm.v1.json rename to assets/dnd/location-occurrences/schemas/dnd_location_occurrences_llm.v1.json diff --git a/internal/modules/dnd/extract/locations/assets/prompts/dnd.locations.yaml b/assets/dnd/locations/extract/prompts/dnd.locations.yaml similarity index 100% rename from internal/modules/dnd/extract/locations/assets/prompts/dnd.locations.yaml rename to assets/dnd/locations/extract/prompts/dnd.locations.yaml diff --git a/internal/modules/dnd/extract/locations/assets/prompts/instructions.md b/assets/dnd/locations/extract/prompts/instructions.md similarity index 100% rename from internal/modules/dnd/extract/locations/assets/prompts/instructions.md rename to assets/dnd/locations/extract/prompts/instructions.md diff --git a/internal/modules/dnd/extract/locations/assets/prompts/task.md b/assets/dnd/locations/extract/prompts/task.md similarity index 100% rename from internal/modules/dnd/extract/locations/assets/prompts/task.md rename to assets/dnd/locations/extract/prompts/task.md diff --git a/internal/modules/dnd/extract/locations/assets/schemas/dnd_locations_llm.v1.json b/assets/dnd/locations/extract/schemas/dnd_locations_llm.v1.json similarity index 100% rename from internal/modules/dnd/extract/locations/assets/schemas/dnd_locations_llm.v1.json rename to assets/dnd/locations/extract/schemas/dnd_locations_llm.v1.json diff --git a/internal/modules/dnd/normalize/locations/assets/prompts/candidates.md b/assets/dnd/locations/normalize/prompts/candidates.md similarity index 100% rename from internal/modules/dnd/normalize/locations/assets/prompts/candidates.md rename to assets/dnd/locations/normalize/prompts/candidates.md diff --git a/internal/modules/dnd/normalize/locations/assets/prompts/dnd.locations.normalize.yaml b/assets/dnd/locations/normalize/prompts/dnd.locations.normalize.yaml similarity index 100% rename from internal/modules/dnd/normalize/locations/assets/prompts/dnd.locations.normalize.yaml rename to assets/dnd/locations/normalize/prompts/dnd.locations.normalize.yaml diff --git a/internal/modules/dnd/normalize/locations/assets/prompts/task.md b/assets/dnd/locations/normalize/prompts/task.md similarity index 100% rename from internal/modules/dnd/normalize/locations/assets/prompts/task.md rename to assets/dnd/locations/normalize/prompts/task.md diff --git a/internal/modules/dnd/extract/locationoccurrences/assets.go b/internal/modules/dnd/extract/locationoccurrences/assets.go deleted file mode 100644 index b0e0b03..0000000 --- a/internal/modules/dnd/extract/locationoccurrences/assets.go +++ /dev/null @@ -1,6 +0,0 @@ -package locationoccurrences - -import "embed" - -//go:embed assets/prompts/*.yaml assets/prompts/*.md assets/schemas/*.json -var embeddedAssets embed.FS diff --git a/internal/modules/dnd/extract/locationoccurrences/prompt_assets.go b/internal/modules/dnd/extract/locationoccurrences/prompt_assets.go index 692a026..4864c13 100644 --- a/internal/modules/dnd/extract/locationoccurrences/prompt_assets.go +++ b/internal/modules/dnd/extract/locationoccurrences/prompt_assets.go @@ -2,8 +2,10 @@ package locationoccurrences import ( "fmt" + "io/fs" "sync" + rootassets "gitea.maximumdirect.net/eric/notarius/assets" "gitea.maximumdirect.net/eric/notarius/internal/framework/llm" "gitea.maximumdirect.net/eric/notarius/internal/framework/promptfs" "gitea.maximumdirect.net/eric/notarius/internal/modules/dnd/shared" @@ -14,10 +16,10 @@ const promptAssetRoot = "assets/prompts" var promptAssetManifest = shared.PromptAssetManifest{ ModuleDir: PromptID, ModuleFiles: []promptfs.ModulePromptFile{ - {Name: "dnd.location_occurrences.yaml", Path: "assets/prompts/dnd.location_occurrences.yaml"}, - {Name: "locations.md", Path: "assets/prompts/locations.md"}, - {Name: "task.md", Path: "assets/prompts/task.md"}, - {Name: "instructions.md", Path: "assets/prompts/instructions.md"}, + {Name: "dnd.location_occurrences.yaml", Path: "prompts/dnd.location_occurrences.yaml"}, + {Name: "locations.md", Path: "prompts/locations.md"}, + {Name: "task.md", Path: "prompts/task.md"}, + {Name: "instructions.md", Path: "prompts/instructions.md"}, }, SharedFiles: []string{ "common-dnd-system.md", @@ -28,20 +30,41 @@ var promptAssetManifest = shared.PromptAssetManifest{ }, } +func moduleAssetFS() (fs.FS, error) { + assets, err := fs.Sub(rootassets.FS(), "dnd/location-occurrences") + if err != nil { + return nil, fmt.Errorf("scope location-occurrence assets: %w", err) + } + return assets, nil +} + func RegisterPromptAssets(registry *llm.AssetRegistry) error { - promptFS, err := promptAssetManifest.PromptFS(embeddedAssets) + assets, err := moduleAssetFS() + if err != nil { + return err + } + promptFS, err := promptAssetManifest.PromptFS(assets) if err != nil { return fmt.Errorf("prepare location-occurrence prompt assets: %w", err) } if err := registry.RegisterPromptFS(promptFS, promptAssetRoot); err != nil { return err } - return registry.RegisterSchemaFS(embeddedAssets, "assets/schemas") + schemas, err := fs.Sub(assets, "schemas") + if err != nil { + return fmt.Errorf("scope location-occurrence schemas: %w", err) + } + return registry.RegisterSchemaFS(schemas, ".") } func promptAssetMetadata() (string, error) { promptAssetHashOnce.Do(func() { - promptAssetHash, promptAssetHashErr = promptAssetManifest.Hash(embeddedAssets) + assets, err := moduleAssetFS() + if err != nil { + promptAssetHashErr = err + return + } + promptAssetHash, promptAssetHashErr = promptAssetManifest.Hash(assets) }) return promptAssetHash, promptAssetHashErr } diff --git a/internal/modules/dnd/extract/locationoccurrences/schema.go b/internal/modules/dnd/extract/locationoccurrences/schema.go index 7bfbdc1..b62da94 100644 --- a/internal/modules/dnd/extract/locationoccurrences/schema.go +++ b/internal/modules/dnd/extract/locationoccurrences/schema.go @@ -11,11 +11,15 @@ const ( ) func loadResponseSchema() (llm.ResponseSchema, error) { - return llm.LoadResponseSchema(embeddedAssets, llm.ResponseSchemaDefinition{ + assets, err := moduleAssetFS() + if err != nil { + return llm.ResponseSchema{}, err + } + return llm.LoadResponseSchema(assets, llm.ResponseSchemaDefinition{ Key: ResponseSchemaKey, ID: ResponseSchemaID, Version: SchemaVersion, Name: ResponseSchemaName, - AssetPath: "assets/schemas/dnd_location_occurrences_llm.v1.json", + AssetPath: "schemas/dnd_location_occurrences_llm.v1.json", }) } diff --git a/internal/modules/dnd/extract/locations/assets.go b/internal/modules/dnd/extract/locations/assets.go deleted file mode 100644 index 306b349..0000000 --- a/internal/modules/dnd/extract/locations/assets.go +++ /dev/null @@ -1,6 +0,0 @@ -package locations - -import "embed" - -//go:embed assets/prompts/*.yaml assets/prompts/*.md assets/schemas/*.json -var embeddedAssets embed.FS diff --git a/internal/modules/dnd/extract/locations/prompt_assets.go b/internal/modules/dnd/extract/locations/prompt_assets.go index 18a360e..e7a97e8 100644 --- a/internal/modules/dnd/extract/locations/prompt_assets.go +++ b/internal/modules/dnd/extract/locations/prompt_assets.go @@ -2,8 +2,10 @@ package locations import ( "fmt" + "io/fs" "sync" + rootassets "gitea.maximumdirect.net/eric/notarius/assets" "gitea.maximumdirect.net/eric/notarius/internal/framework/llm" "gitea.maximumdirect.net/eric/notarius/internal/framework/promptfs" "gitea.maximumdirect.net/eric/notarius/internal/modules/dnd/shared" @@ -14,9 +16,9 @@ const promptAssetRoot = "assets/prompts" var promptAssetManifest = shared.PromptAssetManifest{ ModuleDir: PromptID, ModuleFiles: []promptfs.ModulePromptFile{ - {Name: "dnd.locations.yaml", Path: "assets/prompts/dnd.locations.yaml"}, - {Name: "task.md", Path: "assets/prompts/task.md"}, - {Name: "instructions.md", Path: "assets/prompts/instructions.md"}, + {Name: "dnd.locations.yaml", Path: "prompts/dnd.locations.yaml"}, + {Name: "task.md", Path: "prompts/task.md"}, + {Name: "instructions.md", Path: "prompts/instructions.md"}, }, SharedFiles: []string{ "common-dnd-system.md", @@ -27,20 +29,41 @@ var promptAssetManifest = shared.PromptAssetManifest{ }, } +func moduleAssetFS() (fs.FS, error) { + assets, err := fs.Sub(rootassets.FS(), "dnd/locations/extract") + if err != nil { + return nil, fmt.Errorf("scope location extraction assets: %w", err) + } + return assets, nil +} + func RegisterPromptAssets(registry *llm.AssetRegistry) error { - promptFS, err := promptAssetManifest.PromptFS(embeddedAssets) + assets, err := moduleAssetFS() + if err != nil { + return err + } + promptFS, err := promptAssetManifest.PromptFS(assets) if err != nil { return fmt.Errorf("prepare location prompt assets: %w", err) } if err := registry.RegisterPromptFS(promptFS, promptAssetRoot); err != nil { return err } - return registry.RegisterSchemaFS(embeddedAssets, "assets/schemas") + schemas, err := fs.Sub(assets, "schemas") + if err != nil { + return fmt.Errorf("scope location extraction schemas: %w", err) + } + return registry.RegisterSchemaFS(schemas, ".") } func promptAssetMetadata() (string, error) { promptAssetHashOnce.Do(func() { - promptAssetHash, promptAssetHashErr = promptAssetManifest.Hash(embeddedAssets) + assets, err := moduleAssetFS() + if err != nil { + promptAssetHashErr = err + return + } + promptAssetHash, promptAssetHashErr = promptAssetManifest.Hash(assets) }) return promptAssetHash, promptAssetHashErr } diff --git a/internal/modules/dnd/extract/locations/schema.go b/internal/modules/dnd/extract/locations/schema.go index a6529d8..85abcb0 100644 --- a/internal/modules/dnd/extract/locations/schema.go +++ b/internal/modules/dnd/extract/locations/schema.go @@ -11,11 +11,15 @@ const ( ) func loadResponseSchema() (llm.ResponseSchema, error) { - return llm.LoadResponseSchema(embeddedAssets, llm.ResponseSchemaDefinition{ + assets, err := moduleAssetFS() + if err != nil { + return llm.ResponseSchema{}, err + } + return llm.LoadResponseSchema(assets, llm.ResponseSchemaDefinition{ Key: ResponseSchemaKey, ID: ResponseSchemaID, Version: SchemaVersion, Name: ResponseSchemaName, - AssetPath: "assets/schemas/dnd_locations_llm.v1.json", + AssetPath: "schemas/dnd_locations_llm.v1.json", }) } diff --git a/internal/modules/dnd/normalize/locations/assets.go b/internal/modules/dnd/normalize/locations/assets.go deleted file mode 100644 index 4283674..0000000 --- a/internal/modules/dnd/normalize/locations/assets.go +++ /dev/null @@ -1,6 +0,0 @@ -package locations - -import "embed" - -//go:embed assets/prompts/*.yaml assets/prompts/*.md -var embeddedAssets embed.FS diff --git a/internal/modules/dnd/normalize/locations/prompt_assets.go b/internal/modules/dnd/normalize/locations/prompt_assets.go index 2f7e40e..9efa015 100644 --- a/internal/modules/dnd/normalize/locations/prompt_assets.go +++ b/internal/modules/dnd/normalize/locations/prompt_assets.go @@ -2,8 +2,10 @@ package locations import ( "fmt" + "io/fs" "sync" + rootassets "gitea.maximumdirect.net/eric/notarius/assets" "gitea.maximumdirect.net/eric/notarius/internal/framework/llm" "gitea.maximumdirect.net/eric/notarius/internal/framework/promptfs" "gitea.maximumdirect.net/eric/notarius/internal/modules/dnd/shared" @@ -14,15 +16,27 @@ const promptAssetRoot = "assets/prompts" var promptAssetManifest = shared.PromptAssetManifest{ ModuleDir: PromptID, ModuleFiles: []promptfs.ModulePromptFile{ - {Name: "dnd.locations.normalize.yaml", Path: "assets/prompts/dnd.locations.normalize.yaml"}, - {Name: "task.md", Path: "assets/prompts/task.md"}, - {Name: "candidates.md", Path: "assets/prompts/candidates.md"}, + {Name: "dnd.locations.normalize.yaml", Path: "prompts/dnd.locations.normalize.yaml"}, + {Name: "task.md", Path: "prompts/task.md"}, + {Name: "candidates.md", Path: "prompts/candidates.md"}, }, SharedFiles: []string{"common-dnd-system.md", "common-dnd-entity-reconciliation.md", "common-dnd-transcript.md"}, } +func moduleAssetFS() (fs.FS, error) { + assets, err := fs.Sub(rootassets.FS(), "dnd/locations/normalize") + if err != nil { + return nil, fmt.Errorf("scope location normalization assets: %w", err) + } + return assets, nil +} + func RegisterPromptAssets(registry *llm.AssetRegistry) error { - promptFS, err := promptAssetManifest.PromptFS(embeddedAssets) + assets, err := moduleAssetFS() + if err != nil { + return err + } + promptFS, err := promptAssetManifest.PromptFS(assets) if err != nil { return fmt.Errorf("prepare location normalization prompt assets: %w", err) } @@ -30,7 +44,14 @@ func RegisterPromptAssets(registry *llm.AssetRegistry) error { } func promptAssetMetadata() (string, error) { - promptAssetHashOnce.Do(func() { promptAssetHash, promptAssetHashErr = promptAssetManifest.Hash(embeddedAssets) }) + promptAssetHashOnce.Do(func() { + assets, err := moduleAssetFS() + if err != nil { + promptAssetHashErr = err + return + } + promptAssetHash, promptAssetHashErr = promptAssetManifest.Hash(assets) + }) return promptAssetHash, promptAssetHashErr }