From 9dd26145b3b5a8eb526e8d0f12f5a9c333f5715a Mon Sep 17 00:00:00 2001 From: liangxu Date: Wed, 8 Jul 2026 22:31:56 +0800 Subject: [PATCH] fix(desktop-client): treat title-length validation as definitive publish failure MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Extract the definitive-failure regex into a named constant and add title length/count validation patterns so submit-phase failures like "标题长度应该在2-30字之间" stay non-retryable instead of being classified as uncertain. Co-Authored-By: Claude Opus 4.8 (1M context) --- .../src/main/publish-result-classification.ts | 7 ++++--- .../main/runtime-controller-publish-retry.test.ts | 14 ++++++++++++++ 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/apps/desktop-client/src/main/publish-result-classification.ts b/apps/desktop-client/src/main/publish-result-classification.ts index 8d9ee3b..7dd26fd 100644 --- a/apps/desktop-client/src/main/publish-result-classification.ts +++ b/apps/desktop-client/src/main/publish-result-classification.ts @@ -2,6 +2,9 @@ import type { JsonValue } from '@geo/shared-types' import type { AdapterExecutionResult } from './adapters/base' +const definitivePublishFailurePattern = + /(?:csrf|forbidden|\b403\b|not_logged_in|login_required|token_missing|cookie_missing|challenge_required|risk_control|captcha|验证码|滑块|人机验证|安全验证|风控|风险|参数错误|内容为空|标题.{0,12}(?:长度|字数|过长|太长|超过|不能超过)|title[_\s-]*(?:length|too[_\s-]*long|too[_\s-]*short|max)|image_fetch_failed|cover_fetch_failed|upload_failed|signature_failed)/i + export function markAuthorizationFailureNonRetryable( error: Record, category: 'ai_platform_authorization' | 'media_account_authorization', @@ -49,9 +52,7 @@ export function isDefinitivePublishFailure(result: AdapterExecutionResult): bool return true } - return /(?:csrf|forbidden|\b403\b|not_logged_in|login_required|token_missing|cookie_missing|challenge_required|risk_control|captcha|验证码|滑块|人机验证|安全验证|风控|风险|参数错误|内容为空|image_fetch_failed|cover_fetch_failed|upload_failed|signature_failed)/i.test( - combined, - ) + return definitivePublishFailurePattern.test(combined) } export function asSubmitUncertainExecution(result: AdapterExecutionResult): AdapterExecutionResult { diff --git a/apps/desktop-client/src/main/runtime-controller-publish-retry.test.ts b/apps/desktop-client/src/main/runtime-controller-publish-retry.test.ts index 5b05b6b..83f154d 100644 --- a/apps/desktop-client/src/main/runtime-controller-publish-retry.test.ts +++ b/apps/desktop-client/src/main/runtime-controller-publish-retry.test.ts @@ -21,6 +21,20 @@ describe('publish retry result classification', () => { expect(asSubmitUncertainExecution(result).status).toBe('failed') }) + it('keeps title length validation failures definitive after submit started', () => { + const result: AdapterExecutionResult = { + status: 'failed', + summary: '标题长度应该在2-30字之间', + error: { + code: 'toutiaohao_publish_failed', + message: '标题长度应该在2-30字之间', + }, + } + + expect(isDefinitivePublishFailure(result)).toBe(true) + expect(asSubmitUncertainExecution(result).status).toBe('failed') + }) + it('marks ambiguous submit-phase publish failures as unknown', () => { const result: AdapterExecutionResult = { status: 'failed',