mirror of
https://github.com/langgenius/dify.git
synced 2026-06-07 16:32:01 +08:00
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com> Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com> Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
192 lines
6.0 KiB
TypeScript
192 lines
6.0 KiB
TypeScript
import type { Viewport } from 'reactflow'
|
|
import type { IOnCompleted, IOnData, IOnError, IOnMessageReplace } from './base'
|
|
import type { Edge, Node } from '@/app/components/workflow/types'
|
|
import type { ChatPromptConfig, CompletionPromptConfig } from '@/models/debug'
|
|
import type { AppModeEnum, ModelModeType } from '@/types/app'
|
|
import { get, post, ssePost } from './base'
|
|
|
|
type BasicAppFirstRes = {
|
|
prompt: string
|
|
variables: string[]
|
|
opening_statement: string
|
|
error?: string
|
|
}
|
|
|
|
export type GenRes = {
|
|
modified: string
|
|
message?: string // tip for human
|
|
variables?: string[] // only for basic app first time rule
|
|
opening_statement?: string // only for basic app first time rule
|
|
error?: string
|
|
}
|
|
|
|
export const stopChatMessageResponding = async (appId: string, taskId: string) => {
|
|
return post(`apps/${appId}/chat-messages/${taskId}/stop`)
|
|
}
|
|
|
|
export const sendCompletionMessage = async (appId: string, body: Record<string, any>, { onData, onCompleted, onError, onMessageReplace }: {
|
|
onData: IOnData
|
|
onCompleted: IOnCompleted
|
|
onError: IOnError
|
|
onMessageReplace: IOnMessageReplace
|
|
}) => {
|
|
return ssePost(`apps/${appId}/completion-messages`, {
|
|
body: {
|
|
...body,
|
|
response_mode: 'streaming',
|
|
},
|
|
}, { onData, onCompleted, onError, onMessageReplace })
|
|
}
|
|
|
|
export const fetchSuggestedQuestions = (appId: string, messageId: string, getAbortController?: any) => {
|
|
return get(
|
|
`apps/${appId}/chat-messages/${messageId}/suggested-questions`,
|
|
{},
|
|
{
|
|
getAbortController,
|
|
},
|
|
)
|
|
}
|
|
|
|
export const fetchConversationMessages = (appId: string, conversation_id: string, getAbortController?: any) => {
|
|
return get(`apps/${appId}/chat-messages`, {
|
|
params: {
|
|
conversation_id,
|
|
},
|
|
}, {
|
|
getAbortController,
|
|
})
|
|
}
|
|
|
|
export const generateBasicAppFirstTimeRule = (body: Record<string, any>) => {
|
|
return post<BasicAppFirstRes>('/rule-generate', {
|
|
body,
|
|
})
|
|
}
|
|
|
|
export const generateRule = (body: Record<string, any>) => {
|
|
return post<GenRes>('/instruction-generate', {
|
|
body,
|
|
})
|
|
}
|
|
|
|
/**
|
|
* One structured error from the workflow generator backend. ``code`` is a
|
|
* stable machine-readable identifier the frontend maps to localised copy
|
|
* via the ``workflowGenerator.errors.<code>`` i18n keys; ``detail`` is the
|
|
* raw English diagnostic; ``node_id`` is set when the error is tied to a
|
|
* specific node (the preview canvas can highlight it).
|
|
*
|
|
* Stable codes — adding a new one without updating the i18n map will fall
|
|
* back to ``detail`` and that's fine, but every value listed here MUST
|
|
* exist in both en-US and zh-Hans.
|
|
*/
|
|
// Not exported: knip flags unused exports and the modal looks codes up by
|
|
// string interpolation (``workflowGenerator.errors.${code}``) rather than
|
|
// importing the union. Kept here so the ``GenerateWorkflowResponse``
|
|
// definition below documents the contract in one place.
|
|
type GenerateWorkflowErrorCode
|
|
= | 'INVALID_JSON'
|
|
| 'INVALID_SCHEMA'
|
|
| 'EMPTY_INSTRUCTION'
|
|
| 'EMPTY_PLAN'
|
|
| 'UNKNOWN_NODE_REFERENCE'
|
|
| 'INVALID_CONTAINER'
|
|
| 'UNRESOLVED_REFERENCE'
|
|
| 'UNKNOWN_TOOL'
|
|
| 'MISSING_TERMINAL'
|
|
| 'MISSING_START'
|
|
| 'DANGLING_EDGE'
|
|
| 'MODEL_ERROR'
|
|
|
|
type GenerateWorkflowError = {
|
|
code: GenerateWorkflowErrorCode | string
|
|
detail: string
|
|
node_id?: string
|
|
}
|
|
|
|
export type GenerateWorkflowResponse = {
|
|
graph: {
|
|
nodes: Node[]
|
|
edges: Edge[]
|
|
viewport: Viewport
|
|
}
|
|
message?: string
|
|
/**
|
|
* Planner-picked product-style name (e.g. "URL Summarizer"). Empty when
|
|
* the planner omits it; the caller (applyToNewApp) supplies a fallback.
|
|
*/
|
|
app_name?: string
|
|
/**
|
|
* Planner-picked emoji that captures the workflow's purpose. Empty when
|
|
* the planner omits it; the caller supplies a 🤖 fallback.
|
|
*/
|
|
icon?: string
|
|
/** Human-readable concatenation of ``errors[].detail``. "" on success. */
|
|
error?: string
|
|
/** Structured errors with stable codes for FE-localised mapping. [] on success. */
|
|
errors?: GenerateWorkflowError[]
|
|
}
|
|
|
|
export type GenerateWorkflowBody = {
|
|
mode: 'workflow' | 'advanced-chat'
|
|
instruction: string
|
|
ideal_output?: string
|
|
model_config: { provider: string, name: string, mode: string, completion_params?: Record<string, unknown> }
|
|
/**
|
|
* Existing draft graph for the cmd+k `/refine` flow. When present the
|
|
* backend refines this graph instead of generating from scratch. Omitted
|
|
* for `/create`.
|
|
*/
|
|
current_graph?: {
|
|
nodes: Node[]
|
|
edges: Edge[]
|
|
viewport?: Viewport
|
|
}
|
|
}
|
|
|
|
export type GenerateWorkflowOptions = {
|
|
/**
|
|
* Callback receiving the ``AbortController`` for the in-flight request.
|
|
* The caller stores it and aborts on modal close / second submit / hard
|
|
* timeout. Pattern mirrors ``fetchSuggestedQuestions`` / ``fetchConversationMessages``
|
|
* which already thread this through ``base.ts``.
|
|
*/
|
|
getAbortController?: (controller: AbortController) => void
|
|
}
|
|
|
|
export const generateWorkflow = (body: GenerateWorkflowBody, options?: GenerateWorkflowOptions) => {
|
|
// Only pass the third argument when the caller actually supplied one —
|
|
// otherwise the shared ``post()`` wrapper sees ``undefined`` and that
|
|
// breaks tests asserting the 2-arg call shape, with no behaviour upside.
|
|
if (options?.getAbortController) {
|
|
return post<GenerateWorkflowResponse>('/workflow-generate', { body }, {
|
|
getAbortController: options.getAbortController,
|
|
})
|
|
}
|
|
return post<GenerateWorkflowResponse>('/workflow-generate', { body })
|
|
}
|
|
|
|
export const fetchPromptTemplate = ({
|
|
appMode,
|
|
mode,
|
|
modelName,
|
|
hasSetDataSet,
|
|
}: { appMode: AppModeEnum, mode: ModelModeType, modelName: string, hasSetDataSet: boolean }) => {
|
|
return get<Promise<{ chat_prompt_config: ChatPromptConfig, completion_prompt_config: CompletionPromptConfig, stop: [] }>>('/app/prompt-templates', {
|
|
params: {
|
|
app_mode: appMode,
|
|
model_mode: mode,
|
|
model_name: modelName,
|
|
has_context: hasSetDataSet,
|
|
},
|
|
})
|
|
}
|
|
|
|
export const fetchTextGenerationMessage = ({
|
|
appId,
|
|
messageId,
|
|
}: { appId: string, messageId: string }) => {
|
|
return get<Promise<any>>(`/apps/${appId}/messages/${messageId}`)
|
|
}
|