package domain import ( "strings" "testing" ) func TestValidateTaskInputRequiresTitleSKUImageAndPositiveQuantity(t *testing.T) { err := ValidateTaskInput( " ", nil, "", "", "", "", 0, ) var validation *TaskValidationError if !asTaskValidationError(err, &validation) { t.Fatalf("ValidateTaskInput() error = %v", err) } for _, field := range []string{ "creator_subject", "title", "sku", "image_asset_id", "quantity", } { if validation.Fields[field] == "" { t.Fatalf("missing validation for %s", field) } } } func TestValidateTaskInputEnforcesUTF8AndCharacterLimits(t *testing.T) { sourceRef := strings.Repeat("a", MaxSourceRefBytes+1) err := ValidateTaskInput( "local-admin", &sourceRef, strings.Repeat("商", MaxTitleRunes+1), strings.Repeat("a", MaxDescriptionBytes+1), strings.Repeat("货", MaxSKUBytes/3+1), "00000000-0000-4000-8000-000000000001", 1, ) var validation *TaskValidationError if !asTaskValidationError(err, &validation) { t.Fatalf("ValidateTaskInput() error = %v", err) } for _, field := range []string{ "source_ref", "title", "description", "sku", } { if validation.Fields[field] == "" { t.Fatalf("missing limit validation for %s", field) } } } func TestParseOptionalCNYUsesExactCents(t *testing.T) { tests := []struct { input string want int64 }{ {input: "0.01", want: 1}, {input: "1", want: 100}, {input: "19.9", want: 1990}, {input: "200.00", want: 20000}, } for _, test := range tests { t.Run(test.input, func(t *testing.T) { got, err := ParseOptionalCNY(&test.input) if err != nil { t.Fatalf("ParseOptionalCNY() error = %v", err) } if got == nil || *got != test.want { t.Fatalf("ParseOptionalCNY() = %v, want %d", got, test.want) } formatted := FormatOptionalCNY(got) if formatted == nil { t.Fatal("FormatOptionalCNY() = nil") } }) } } func TestParseOptionalCNYRejectsInvalidAndOverflow(t *testing.T) { for _, value := range []string{ "", "0", "0.00", "-1", "+1", ".5", "1.", "1.001", "1e2", "99999999999999999.99", } { t.Run(value, func(t *testing.T) { if _, err := ParseOptionalCNY(&value); err == nil { t.Fatalf("ParseOptionalCNY(%q) error = nil", value) } }) } } func TestCanCancelOnlyNonTerminalTask(t *testing.T) { for _, status := range []TaskStatus{ TaskStatusSucceeded, TaskStatusFailed, TaskStatusCanceled, } { if CanCancel(status) { t.Fatalf("CanCancel(%s) = true", status) } } for _, status := range []TaskStatus{ TaskStatusPending, TaskStatusClaimed, TaskStatusRunning, TaskStatusWaitingConfirmation, } { if !CanCancel(status) { t.Fatalf("CanCancel(%s) = false", status) } } } func asTaskValidationError( err error, target **TaskValidationError, ) bool { value, ok := err.(*TaskValidationError) if ok { *target = value } return ok }