From ba4db85241c73e7c836c46f7164009505359c767 Mon Sep 17 00:00:00 2001 From: liangxu Date: Wed, 8 Jul 2026 16:17:59 +0800 Subject: [PATCH] fix(logic): ignore reference directives when checking for prompt text Strip inline image tokens and reference directive URLs before deciding whether a prompt carries real user text, so a reference-only prompt is still treated as empty while text around references counts. Co-Authored-By: Claude Opus 4.8 (1M context) --- server/internal/logic/prompt_validation.go | 8 +++++++ .../internal/logic/prompt_validation_test.go | 24 +++++++++++++++++++ 2 files changed, 32 insertions(+) create mode 100644 server/internal/logic/prompt_validation_test.go diff --git a/server/internal/logic/prompt_validation.go b/server/internal/logic/prompt_validation.go index eb4899c..c7296ad 100644 --- a/server/internal/logic/prompt_validation.go +++ b/server/internal/logic/prompt_validation.go @@ -2,11 +2,17 @@ package logic import ( "fmt" + "regexp" "strings" "img_infinite_canvas/internal/domain/design" ) +var ( + promptReferenceDirectivePattern = regexp.MustCompile(`(?i)(?:参考图|reference image)\s*\d*\s*(?:[((][^))\n]+[))])?\s*[::]\s*(?:https?://[^\s\],。]+|data:image/[^\s\],。]+|/[^\s\],。]+)`) + promptImageTokenPattern = regexp.MustCompile(`\[@image:#\d+:[^:\]]+:(?:\[[^\]]+\]\((?:[^)]+)\)|[^\]]+)\]`) +) + func validateRequiredPrompt(prompt string, allowEmpty bool) error { if allowEmpty { return nil @@ -18,6 +24,8 @@ func validateRequiredPrompt(prompt string, allowEmpty bool) error { } func hasRequiredPromptText(prompt string) bool { + prompt = promptImageTokenPattern.ReplaceAllString(prompt, " ") + prompt = promptReferenceDirectivePattern.ReplaceAllString(prompt, " ") for _, line := range strings.Split(prompt, "\n") { line = strings.TrimSpace(strings.ReplaceAll(line, "\u00a0", " ")) if line == "" || isPromptReferenceDirective(line) { diff --git a/server/internal/logic/prompt_validation_test.go b/server/internal/logic/prompt_validation_test.go new file mode 100644 index 0000000..05f8146 --- /dev/null +++ b/server/internal/logic/prompt_validation_test.go @@ -0,0 +1,24 @@ +package logic + +import "testing" + +func TestHasRequiredPromptTextAllowsInlineReferenceContext(t *testing.T) { + prompt := "参考图 1(0.jpg):http://localhost:19000/canvas-assets/a.webp 为服装品牌 stillday 创建情绪板 logo 设计 参考图 2(image.png):http://localhost:19000/canvas-assets/b.png ,包含材质、色彩、摄影姿态。" + if !hasRequiredPromptText(prompt) { + t.Fatalf("expected inline text around reference directives to count as prompt text") + } +} + +func TestHasRequiredPromptTextRejectsReferenceOnlyPrompt(t *testing.T) { + prompt := "参考图 1(0.jpg):http://localhost:19000/canvas-assets/a.webp\nReference image 2 (image.png): https://example.com/b.png" + if hasRequiredPromptText(prompt) { + t.Fatalf("expected reference-only prompt to be treated as empty") + } +} + +func TestHasRequiredPromptTextHandlesChinesePunctuationAfterReference(t *testing.T) { + prompt := "参考图 1(image.png):https://example.com/reference.png,参考它的字体做 logo。" + if !hasRequiredPromptText(prompt) { + t.Fatalf("expected text after Chinese punctuation to count as prompt text") + } +}