Write prompt data packages as YAML
This commit is contained in:
@@ -522,7 +522,19 @@ func GenerateReport(ctx context.Context, req ReportRequest) (*ReportResult, erro
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
dataPackage, err := promptinput.BuildWithRecentChanges(briefingPackage, recentChanges)
|
||||
metadata := state.BuildMetadata(req.Resolved, briefingPackage, state.ArtifactPaths{
|
||||
Briefing: briefingPath,
|
||||
ModuleSnapshot: moduleSnapshotPath,
|
||||
Metadata: paths.Metadata,
|
||||
DataPackage: paths.DataPackage,
|
||||
Preflight: paths.Preflight,
|
||||
RenderedReport: paths.RenderedReport,
|
||||
})
|
||||
dataPackage, err := promptinput.Build(promptinput.BuildRequest{
|
||||
Metadata: promptMetadata(metadata),
|
||||
Modules: moduleSnapshot,
|
||||
RecentChanges: recentChanges,
|
||||
})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@@ -530,6 +542,7 @@ func GenerateReport(ctx context.Context, req ReportRequest) (*ReportResult, erro
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
metadata.DataPackagePath = dataPackagePath
|
||||
|
||||
renderer := req.Renderer
|
||||
if renderer == nil {
|
||||
@@ -554,14 +567,7 @@ func GenerateReport(ctx context.Context, req ReportRequest) (*ReportResult, erro
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
metadata := state.BuildMetadata(req.Resolved, briefingPackage, state.ArtifactPaths{
|
||||
Briefing: briefingPath,
|
||||
ModuleSnapshot: moduleSnapshotPath,
|
||||
Metadata: paths.Metadata,
|
||||
DataPackage: dataPackagePath,
|
||||
Preflight: preflightPath,
|
||||
RenderedReport: paths.RenderedReport,
|
||||
})
|
||||
metadata.PreflightPath = preflightPath
|
||||
metadataPath, metadataErr := store.SaveMetadata(ctx, metadata)
|
||||
if metadataErr != nil {
|
||||
return nil, metadataErr
|
||||
@@ -894,6 +900,19 @@ func BuildModuleSnapshot(req ModuleSnapshotRequest, bundle *weatherdata.Bundle)
|
||||
return module.NewSnapshot(outputs)
|
||||
}
|
||||
|
||||
func promptMetadata(metadata state.Metadata) promptinput.Metadata {
|
||||
return promptinput.Metadata{
|
||||
RunID: metadata.RunID,
|
||||
ReportID: metadata.ReportID,
|
||||
Variant: metadata.Variant,
|
||||
PromptID: metadata.PromptID,
|
||||
GeneratedAt: metadata.GeneratedAt,
|
||||
Timezone: metadata.Timezone,
|
||||
ValidPeriod: metadata.ValidPeriod,
|
||||
SourceWarnings: metadata.SourceWarnings,
|
||||
}
|
||||
}
|
||||
|
||||
func buildDerivedFacts(cfg config.Config, resolved report.Resolved, collected facts.CollectedFacts) (facts.DerivedFacts, error) {
|
||||
dayparts := make([]forecast.DaypartDefinition, 0, len(cfg.Dayparts))
|
||||
for _, daypart := range cfg.Dayparts {
|
||||
|
||||
@@ -17,6 +17,7 @@ import (
|
||||
"gitea.maximumdirect.net/eric/weatherreporter/internal/config"
|
||||
"gitea.maximumdirect.net/eric/weatherreporter/internal/forecast"
|
||||
"gitea.maximumdirect.net/eric/weatherreporter/internal/module"
|
||||
"gitea.maximumdirect.net/eric/weatherreporter/internal/promptinput"
|
||||
"gitea.maximumdirect.net/eric/weatherreporter/internal/report"
|
||||
"gitea.maximumdirect.net/eric/weatherreporter/internal/state"
|
||||
)
|
||||
@@ -206,31 +207,32 @@ func TestGenerateReportWritesReportAndPreflight(t *testing.T) {
|
||||
if err != nil {
|
||||
t.Fatalf("read data package: %v", err)
|
||||
}
|
||||
if !strings.Contains(string(data), `"recentChanges"`) || !strings.Contains(string(data), `data_package.v1`) {
|
||||
if !strings.HasSuffix(result.DataPackagePath, ".data_package.yaml") {
|
||||
t.Fatalf("DataPackagePath = %q, want YAML data package path", result.DataPackagePath)
|
||||
}
|
||||
if !strings.Contains(string(data), "schema_version: weatherreporter.data_package.v2") ||
|
||||
!strings.Contains(string(data), "recent_changes:") ||
|
||||
!strings.Contains(string(data), "current_conditions:") ||
|
||||
!strings.Contains(string(data), "area_forecast_discussion:") {
|
||||
t.Fatalf("data package missing expected content:\n%s", string(data))
|
||||
}
|
||||
var savedDataPackage struct {
|
||||
Report struct {
|
||||
CurrentLocalDate string `json:"currentLocalDate"`
|
||||
} `json:"report"`
|
||||
Briefing briefing.Package `json:"briefing"`
|
||||
}
|
||||
if err := json.Unmarshal(data, &savedDataPackage); err != nil {
|
||||
savedDataPackage, err := promptinput.LoadYAML(data)
|
||||
if err != nil {
|
||||
t.Fatalf("decode data package: %v", err)
|
||||
}
|
||||
if savedDataPackage.Report.CurrentLocalDate != "2026-05-29" {
|
||||
t.Fatalf("data package currentLocalDate = %q, want 2026-05-29", savedDataPackage.Report.CurrentLocalDate)
|
||||
}
|
||||
location := savedDataPackage.Briefing.Metadata.Location
|
||||
if location == nil || location.ID != "home" || location.Name != "Brentwood" || location.Region != "St. Louis Metro" || location.Timezone != "America/Chicago" {
|
||||
t.Fatalf("data package location = %#v, want configured prompt location", location)
|
||||
if _, ok := savedDataPackage.Briefing.Values["metadata"]; !ok {
|
||||
t.Fatal("data package metadata stanza missing")
|
||||
}
|
||||
current := savedDataPackage.Briefing.CurrentConditions
|
||||
if current == nil || current.ConditionText != "Clear" || current.TemperatureF == nil || *current.TemperatureF != 75 {
|
||||
t.Fatalf("data package current conditions = %#v, want current conditions", current)
|
||||
current, ok := savedDataPackage.Briefing.Values["current_conditions"].(map[string]any)
|
||||
if !ok || current["condition_text"] != "Clear" {
|
||||
t.Fatalf("data package current conditions = %#v, want current conditions", savedDataPackage.Briefing.Values["current_conditions"])
|
||||
}
|
||||
if savedDataPackage.Briefing.Daily == nil || savedDataPackage.Briefing.Daily.WeatherStory == nil || savedDataPackage.Briefing.Daily.WeatherStory.Title != "Several Chances for Rain Through Monday" {
|
||||
t.Fatalf("data package weather story = %#v, want weather story title", savedDataPackage.Briefing.Daily)
|
||||
story, ok := savedDataPackage.Briefing.Values["weather_story"].(map[string]any)
|
||||
if !ok || story["title"] != "Several Chances for Rain Through Monday" {
|
||||
t.Fatalf("data package weather story = %#v, want weather story title", savedDataPackage.Briefing.Values["weather_story"])
|
||||
}
|
||||
if !strings.Contains(string(data), "Short-term AFD narrative for generated report.") || !strings.Contains(string(data), "Long-term AFD narrative for generated report.") {
|
||||
t.Fatalf("data package missing AFD short/long-term discussion:\n%s", string(data))
|
||||
@@ -1012,7 +1014,7 @@ func TestGenerateStormReportWritesReport(t *testing.T) {
|
||||
if err != nil {
|
||||
t.Fatalf("read data package: %v", err)
|
||||
}
|
||||
if !strings.Contains(string(data), `"storm"`) || !strings.Contains(string(data), `"weather.storm_report"`) {
|
||||
if !strings.Contains(string(data), "id: storm") || !strings.Contains(string(data), "prompt_id: weather.storm_report") || !strings.Contains(string(data), "precip_timing:") {
|
||||
t.Fatalf("data package missing storm content:\n%s", string(data))
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user