diff options
| author | Paul Buetow <paul@buetow.org> | 2026-04-22 08:48:10 +0300 |
|---|---|---|
| committer | Paul Buetow <paul@buetow.org> | 2026-04-22 08:48:10 +0300 |
| commit | 24dd98eaa9759884b17f18c729d498af6ec70e9e (patch) | |
| tree | 6e1d5b29fac20d1f412ced27bdbd52a5cee9e3a2 | |
| parent | f9baad3a11e48a6d438d3e614e1ca1ee45c1547d (diff) | |
Fix prompt mode validation and readiness
| -rw-r--r-- | internal/comic/artist.go | 2 | ||||
| -rw-r--r-- | internal/comic/comic_test.go | 71 | ||||
| -rw-r--r-- | internal/comic/runner.go | 3 |
3 files changed, 75 insertions, 1 deletions
diff --git a/internal/comic/artist.go b/internal/comic/artist.go index 7ccf084..e1717d3 100644 --- a/internal/comic/artist.go +++ b/internal/comic/artist.go @@ -218,7 +218,7 @@ func (a *Artist) generatePromptImage(ctx context.Context, prompt, outputFile str if err != nil { return fmt.Errorf("render manual prompt: %w", err) } - return a.generateWithRetryAndValidation(ctx, renderedPrompt, outputFile, "manual prompt image", nil, nil) + return a.generateWithRetryAndValidation(ctx, renderedPrompt, outputFile, "manual prompt image", nil, validateImagePromptLeakageFn) } type imageOutputValidator func(context.Context, string, string, string) error diff --git a/internal/comic/comic_test.go b/internal/comic/comic_test.go index 866df64..65343e6 100644 --- a/internal/comic/comic_test.go +++ b/internal/comic/comic_test.go @@ -373,6 +373,12 @@ func TestDrawComicPagesReturnsErrorWhenRenderFails(t *testing.T) { func TestArtistAndRunnerEndToEndWithFakes(t *testing.T) { t.Parallel() + originalSleep := sleep + sleep = func(time.Duration) {} + t.Cleanup(func() { + sleep = originalSleep + }) + originalLeakValidation := validateImagePromptLeakageFn validateImagePromptLeakageFn = func(context.Context, string, string, string) error { return nil } t.Cleanup(func() { @@ -471,6 +477,50 @@ func TestRunnerRunPromptWritesSingleAsset(t *testing.T) { } } +func TestRunnerRunPromptValidatesImageOutput(t *testing.T) { + originalLeakValidation := validateImagePromptLeakageFn + defer func() { + validateImagePromptLeakageFn = originalLeakValidation + }() + + var calls int + var gotLabel string + var gotScript string + validateImagePromptLeakageFn = func(_ context.Context, outputFile, label, script string) error { + calls++ + if outputFile == "" { + t.Fatal("validator received empty output file") + } + gotLabel = label + gotScript = script + return nil + } + + tmpDir := t.TempDir() + runner := NewRunner(&RunnerConfig{ + ImageProvider: fakeImageProvider{t: t}, + Prompts: fakePromptRenderer{}, + OutputDir: tmpDir, + Slug: "manual-robot", + UltraRealistic: boolPtr(false), + PageMaxRetries: 1, + PageRetryBase: time.Second, + }) + + if err := runner.RunPrompt(context.Background(), "a robot reading a newspaper"); err != nil { + t.Fatalf("RunPrompt() error = %v", err) + } + if calls != 1 { + t.Fatalf("validator calls = %d, want 1", calls) + } + if gotLabel != "manual prompt image" { + t.Fatalf("validator label = %q, want %q", gotLabel, "manual prompt image") + } + if gotScript == "" { + t.Fatal("validator script was empty") + } +} + func TestRunnerRunPromptRejectsEmptyPrompt(t *testing.T) { t.Parallel() @@ -486,6 +536,27 @@ func TestRunnerRunPromptRejectsEmptyPrompt(t *testing.T) { } } +func TestRunnerRunPromptReturnsErrorWhenPromptRendererMissing(t *testing.T) { + runner := NewRunner(&RunnerConfig{ + ImageProvider: fakeImageProvider{t: t}, + OutputDir: t.TempDir(), + Slug: "manual-robot", + UltraRealistic: boolPtr(false), + PageMaxRetries: 1, + PageRetryBase: time.Second, + }) + + defer func() { + if r := recover(); r != nil { + t.Fatalf("RunPrompt() panicked: %v", r) + } + }() + + if err := runner.RunPrompt(context.Background(), "a robot reading a newspaper"); err == nil { + t.Fatal("RunPrompt() error = nil, want readiness failure") + } +} + func TestRunnerRunPromptAppliesStyleThemeAndUltraContext(t *testing.T) { t.Parallel() diff --git a/internal/comic/runner.go b/internal/comic/runner.go index a9411ef..a5d89e6 100644 --- a/internal/comic/runner.go +++ b/internal/comic/runner.go @@ -200,6 +200,9 @@ func (r *Runner) RunPrompt(ctx context.Context, prompt string) error { if r.artist == nil { return fmt.Errorf("runner providers are not configured") } + if err := r.artist.ready(); err != nil { + return err + } if ctx == nil { ctx = context.Background() } |
