Download src/workflow/problem-framing/problem-framing.ts from Bin29/ManimCat: direct link, hf CLI and curl.
- Browser
- Download file 5.88 kB
-
https://huggingface.co/spaces/Bin29/ManimCat/resolve/main/src/workflow/problem-framing/problem-framing.ts
- Command line
-
hf download hf://spaces/Bin29/ManimCat/src/workflow/problem-framing/problem-framing.ts
-
curl -L -o problem-framing.ts https://huggingface.co/spaces/Bin29/ManimCat/resolve/main/src/workflow/problem-framing/problem-framing.ts
5.88 kB
| import { createCustomOpenAIClient } from '../../infrastructure/ai-provider/provider-client-factory' | |
| import { createChatCompletionText } from '../openai-stream' | |
| import { buildCompletionParams, readMaxCompletionTokens } from '../../infrastructure/ai-provider/completion-policy' | |
| import { createLogger } from '../../shared/logging/logger' | |
| import { getRoleSystemPrompt, getRoleUserPrompt } from '../../prompts' | |
| import { buildVisionUserMessage } from '../generation/multimodal-input' | |
| import type { ConceptInput, CustomApiConfig, PromptLocale, PromptOverrides } from '../../types' | |
| import { ServiceUnavailableError } from '../../shared/errors/errors' | |
| import { ProblemFramingFormatError, type ProblemFramingPlan } from './parser' | |
| import { parseProblemFramingWithRepair } from './format-repair' | |
| const logger = createLogger('ProblemFraming') | |
| const PLANNER_TEMPERATURE = parseFloat(process.env.PROBLEM_FRAMING_TEMPERATURE || '0.7') | |
| const PLANNER_MAX_TOKENS = readMaxCompletionTokens('PROBLEM_FRAMING') | |
| const PLANNER_FORMAT_RETRIES = parseInt(process.env.PROBLEM_FRAMING_FORMAT_RETRIES || '2', 10) | |
| const FORMAT_REPAIR_INPUT_LIMIT = 16_000 | |
| export type { ProblemFramingPlan } from './parser' | |
| interface ProblemFramingParams extends ConceptInput { | |
| feedback?: string | |
| feedbackHistory?: string[] | |
| currentPlan?: ProblemFramingPlan | |
| customApiConfig: CustomApiConfig | |
| locale?: PromptLocale | |
| promptOverrides?: PromptOverrides | |
| } | |
| export async function generateProblemFramingPlan(params: ProblemFramingParams): Promise<ProblemFramingPlan> { | |
| const locale = params.locale === 'en-US' ? 'en-US' : 'zh-CN' | |
| const client = createCustomOpenAIClient(params.customApiConfig) | |
| const model = (params.customApiConfig.model || '').trim() | |
| if (!model) { | |
| throw new Error('No model available') | |
| } | |
| logger.info('Problem framing started', { | |
| locale, | |
| conceptLength: params.concept.length, | |
| hasFeedback: !!params.feedback, | |
| hasCurrentPlan: !!params.currentPlan, | |
| hasImages: !!params.referenceImages?.length | |
| }) | |
| const promptOverrides: PromptOverrides = { ...params.promptOverrides, locale } | |
| const systemPrompt = getRoleSystemPrompt('problemFraming', promptOverrides) | |
| const userPrompt = getRoleUserPrompt( | |
| 'problemFraming', | |
| { | |
| concept: params.concept, | |
| instructions: params.feedback, | |
| feedbackHistory: params.feedbackHistory?.length ? params.feedbackHistory.map((item, index) => `${index + 1}. ${item}`).join('\n') : undefined, | |
| sceneDesign: params.currentPlan ? JSON.stringify(params.currentPlan, null, 2) : undefined | |
| }, | |
| promptOverrides | |
| ) | |
| const response = await createChatCompletionText( | |
| client, | |
| { | |
| model, | |
| messages: [ | |
| { role: 'system', content: systemPrompt }, | |
| { role: 'user', content: buildVisionUserMessage(userPrompt, params.referenceImages) } | |
| ], | |
| temperature: PLANNER_TEMPERATURE, | |
| ...buildCompletionParams(PLANNER_MAX_TOKENS, 'PROBLEM_FRAMING', client) | |
| }, | |
| { fallbackToNonStream: true, usageLabel: 'problem-framing' } | |
| ) | |
| let plan: ProblemFramingPlan | |
| try { | |
| plan = await parseProblemFramingWithRepair({ | |
| content: response.content, | |
| locale, | |
| maxRepairAttempts: Math.max(0, PLANNER_FORMAT_RETRIES), | |
| requireDesignFields: !promptOverrides.roles?.problemFraming?.system, | |
| repair: async ({ content, error, attempt }) => { | |
| logger.warn('Problem framing format invalid, requesting format repair', { | |
| attempt, | |
| error, | |
| contentLength: content.length, | |
| }) | |
| const repairResponse = await createChatCompletionText( | |
| client, | |
| { | |
| model, | |
| messages: [ | |
| { | |
| role: 'system', | |
| content: locale === 'en-US' | |
| ? 'Repair formatting only; preserve every decision. Output one complete plan with mode/headline/summary/question/answer/audience/background_rules/selected_route/alternative_routes/out_of_scope/special_cases/visual_motif/designer_hint, and 3–12 repeated step blocks with phase/title/content. phase is background, phenomenon, derivation, or closing. Never truncate later steps or erase fields. No other text.' | |
| : '只修复格式,保留全部决定。输出完整plan,包含mode/headline/summary/question/answer/audience/background_rules/selected_route/alternative_routes/out_of_scope/special_cases/visual_motif/designer_hint,以及3–12个含phase/title/content的step;phase为background、phenomenon、derivation或closing。不得截掉后续步骤或删字段,标签外零文字。', | |
| }, | |
| { role: 'user', content: buildVisionUserMessage(userPrompt, params.referenceImages) }, | |
| { | |
| role: 'user', | |
| content: `Parser error: ${error}\n\nModel output:\n${content.slice(0, FORMAT_REPAIR_INPUT_LIMIT)}`, | |
| }, | |
| ], | |
| temperature: 0, | |
| ...buildCompletionParams(PLANNER_MAX_TOKENS, 'PROBLEM_FRAMING', client), | |
| }, | |
| { | |
| fallbackToNonStream: true, | |
| usageLabel: `problem-framing-format-repair-${attempt}`, | |
| }, | |
| ) | |
| return repairResponse.content | |
| }, | |
| }) | |
| } catch (error) { | |
| if (!(error instanceof ProblemFramingFormatError)) { | |
| throw error | |
| } | |
| logger.error('Problem framing format repair exhausted', { | |
| error: error instanceof Error ? error.message : String(error), | |
| }) | |
| throw new ServiceUnavailableError( | |
| locale === 'en-US' | |
| ? 'The planning card format could not be recovered. Please retry.' | |
| : '规划卡格式修复失败,请重试。', | |
| { code: 'PLAN_FORMAT_INVALID', retryable: true }, | |
| ) | |
| } | |
| logger.info('Problem framing completed', { | |
| mode: plan.mode, | |
| headline: plan.headline, | |
| stepCount: plan.steps.length | |
| }) | |
| return plan | |
| } | |