mirror of https://github.com/langgenius/dify.git
add human input node
This commit is contained in:
parent
cff6a488f8
commit
6485adae35
|
|
@ -0,0 +1,5 @@
|
|||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M3.66634 2.66675C3.66634 2.29856 3.36787 2.00008 2.99967 2.00008C2.63149 2.00008 2.33301 2.29855 2.33301 2.66675L3.66634 2.66675ZM2.99967 5.33341H2.33301C2.33301 5.51023 2.40325 5.6798 2.52827 5.80482C2.65329 5.92984 2.82286 6.00008 2.99967 6.00008V5.33341ZM5.66641 6.00008C6.03459 6.00008 6.33307 5.7016 6.33307 5.33341C6.33307 4.96523 6.03459 4.66675 5.66641 4.66675L5.66641 6.00008ZM2.41183 5.01659C2.23816 5.34125 2.36056 5.74523 2.68522 5.91889C3.00988 6.09256 3.41385 5.97016 3.58752 5.6455L2.41183 5.01659ZM3.03395 8.58915C2.99109 8.22348 2.6599 7.96175 2.29421 8.00461C1.92853 8.04748 1.66682 8.37868 1.70967 8.74435L3.03395 8.58915ZM12.0439 5.05931C12.2607 5.3569 12.6777 5.42238 12.9753 5.20557C13.2729 4.98876 13.3383 4.57176 13.1215 4.27417L12.0439 5.05931ZM5.02145 13.5907C5.34627 13.7641 5.75013 13.6413 5.92349 13.3165C6.09685 12.9917 5.97407 12.5878 5.64925 12.4145L5.02145 13.5907ZM2.33301 2.66675L2.33301 5.33341H3.66634L3.66634 2.66675L2.33301 2.66675ZM2.99967 6.00008L5.66641 6.00008L5.66641 4.66675H2.99967L2.99967 6.00008ZM3.58752 5.6455C4.43045 4.06972 6.09066 3.00008 7.99968 3.00008V1.66675C5.57951 1.66675 3.47747 3.02445 2.41183 5.01659L3.58752 5.6455ZM7.99968 3.00008C9.66128 3.00008 11.1336 3.80991 12.0439 5.05931L13.1215 4.27417C11.9711 2.69513 10.1055 1.66675 7.99968 1.66675V3.00008ZM5.64925 12.4145C4.23557 11.6599 3.22828 10.2474 3.03395 8.58915L1.70967 8.74435C1.95639 10.8495 3.23403 12.6367 5.02145 13.5907L5.64925 12.4145Z" fill="white"/>
|
||||
<path fill-rule="evenodd" clip-rule="evenodd" d="M13.1946 8.13826C12.9027 7.84637 12.4294 7.84638 12.1375 8.13829L9.11842 11.1574C9.01642 11.2594 8.95025 11.3917 8.92985 11.5345C8.92985 11.5345 8.92985 11.5345 8.92985 11.5345L8.78508 12.5479L9.79846 12.4031C9.94127 12.3827 10.0736 12.3165 10.1756 12.2145L13.1947 9.19548C13.4866 8.90359 13.4866 8.43027 13.1946 8.13826C13.1947 8.13827 13.1946 8.13825 13.1946 8.13826ZM11.1947 7.19548C12.0073 6.38286 13.3249 6.38286 14.1375 7.19548C14.95 8.00814 14.9501 9.32565 14.1375 10.1383L11.1184 13.1574C10.8124 13.4633 10.4154 13.6618 9.98703 13.723L8.09369 13.9935C7.88596 14.0232 7.67639 13.9533 7.52801 13.805C7.37963 13.6566 7.30977 13.447 7.33945 13.2393L7.60991 11.3459C7.67111 10.9175 7.86961 10.5205 8.17561 10.2145L11.1947 7.19548Z" fill="white"/>
|
||||
<path fill-rule="evenodd" clip-rule="evenodd" d="M12.528 10.8048L10.528 8.80482L11.4708 7.86201L13.4708 9.86201L12.528 10.8048Z" fill="white"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 2.5 KiB |
|
|
@ -0,0 +1,48 @@
|
|||
{
|
||||
"icon": {
|
||||
"type": "element",
|
||||
"isRootNode": true,
|
||||
"name": "svg",
|
||||
"attributes": {
|
||||
"width": "16",
|
||||
"height": "16",
|
||||
"viewBox": "0 0 16 16",
|
||||
"fill": "none",
|
||||
"xmlns": "http://www.w3.org/2000/svg"
|
||||
},
|
||||
"children": [
|
||||
{
|
||||
"type": "element",
|
||||
"name": "path",
|
||||
"attributes": {
|
||||
"d": "M3.66634 2.66675C3.66634 2.29856 3.36787 2.00008 2.99967 2.00008C2.63149 2.00008 2.33301 2.29855 2.33301 2.66675L3.66634 2.66675ZM2.99967 5.33341H2.33301C2.33301 5.51023 2.40325 5.6798 2.52827 5.80482C2.65329 5.92984 2.82286 6.00008 2.99967 6.00008V5.33341ZM5.66641 6.00008C6.03459 6.00008 6.33307 5.7016 6.33307 5.33341C6.33307 4.96523 6.03459 4.66675 5.66641 4.66675L5.66641 6.00008ZM2.41183 5.01659C2.23816 5.34125 2.36056 5.74523 2.68522 5.91889C3.00988 6.09256 3.41385 5.97016 3.58752 5.6455L2.41183 5.01659ZM3.03395 8.58915C2.99109 8.22348 2.6599 7.96175 2.29421 8.00461C1.92853 8.04748 1.66682 8.37868 1.70967 8.74435L3.03395 8.58915ZM12.0439 5.05931C12.2607 5.3569 12.6777 5.42238 12.9753 5.20557C13.2729 4.98876 13.3383 4.57176 13.1215 4.27417L12.0439 5.05931ZM5.02145 13.5907C5.34627 13.7641 5.75013 13.6413 5.92349 13.3165C6.09685 12.9917 5.97407 12.5878 5.64925 12.4145L5.02145 13.5907ZM2.33301 2.66675L2.33301 5.33341H3.66634L3.66634 2.66675L2.33301 2.66675ZM2.99967 6.00008L5.66641 6.00008L5.66641 4.66675H2.99967L2.99967 6.00008ZM3.58752 5.6455C4.43045 4.06972 6.09066 3.00008 7.99968 3.00008V1.66675C5.57951 1.66675 3.47747 3.02445 2.41183 5.01659L3.58752 5.6455ZM7.99968 3.00008C9.66128 3.00008 11.1336 3.80991 12.0439 5.05931L13.1215 4.27417C11.9711 2.69513 10.1055 1.66675 7.99968 1.66675V3.00008ZM5.64925 12.4145C4.23557 11.6599 3.22828 10.2474 3.03395 8.58915L1.70967 8.74435C1.95639 10.8495 3.23403 12.6367 5.02145 13.5907L5.64925 12.4145Z",
|
||||
"fill": "currentColor"
|
||||
},
|
||||
"children": []
|
||||
},
|
||||
{
|
||||
"type": "element",
|
||||
"name": "path",
|
||||
"attributes": {
|
||||
"fill-rule": "evenodd",
|
||||
"clip-rule": "evenodd",
|
||||
"d": "M13.1946 8.13826C12.9027 7.84637 12.4294 7.84638 12.1375 8.13829L9.11842 11.1574C9.01642 11.2594 8.95025 11.3917 8.92985 11.5345C8.92985 11.5345 8.92985 11.5345 8.92985 11.5345L8.78508 12.5479L9.79846 12.4031C9.94127 12.3827 10.0736 12.3165 10.1756 12.2145L13.1947 9.19548C13.4866 8.90359 13.4866 8.43027 13.1946 8.13826C13.1947 8.13827 13.1946 8.13825 13.1946 8.13826ZM11.1947 7.19548C12.0073 6.38286 13.3249 6.38286 14.1375 7.19548C14.95 8.00814 14.9501 9.32565 14.1375 10.1383L11.1184 13.1574C10.8124 13.4633 10.4154 13.6618 9.98703 13.723L8.09369 13.9935C7.88596 14.0232 7.67639 13.9533 7.52801 13.805C7.37963 13.6566 7.30977 13.447 7.33945 13.2393L7.60991 11.3459C7.67111 10.9175 7.86961 10.5205 8.17561 10.2145L11.1947 7.19548Z",
|
||||
"fill": "currentColor"
|
||||
},
|
||||
"children": []
|
||||
},
|
||||
{
|
||||
"type": "element",
|
||||
"name": "path",
|
||||
"attributes": {
|
||||
"fill-rule": "evenodd",
|
||||
"clip-rule": "evenodd",
|
||||
"d": "M12.528 10.8048L10.528 8.80482L11.4708 7.86201L13.4708 9.86201L12.528 10.8048Z",
|
||||
"fill": "currentColor"
|
||||
},
|
||||
"children": []
|
||||
}
|
||||
]
|
||||
},
|
||||
"name": "HumanInLoop"
|
||||
}
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
// GENERATE BY script
|
||||
// DON NOT EDIT IT MANUALLY
|
||||
|
||||
import * as React from 'react'
|
||||
import data from './HumanInLoop.json'
|
||||
import IconBase from '@/app/components/base/icons/IconBase'
|
||||
import type { IconData } from '@/app/components/base/icons/IconBase'
|
||||
|
||||
const Icon = (
|
||||
{
|
||||
ref,
|
||||
...props
|
||||
}: React.SVGProps<SVGSVGElement> & {
|
||||
ref?: React.RefObject<React.MutableRefObject<HTMLOrSVGElement>>;
|
||||
},
|
||||
) => <IconBase {...props} ref={ref} data={data as IconData} />
|
||||
|
||||
Icon.displayName = 'HumanInLoop'
|
||||
|
||||
export default Icon
|
||||
|
|
@ -6,6 +6,7 @@ export { default as DocsExtractor } from './DocsExtractor'
|
|||
export { default as End } from './End'
|
||||
export { default as Home } from './Home'
|
||||
export { default as Http } from './Http'
|
||||
export { default as HumanInLoop } from './HumanInLoop'
|
||||
export { default as IfElse } from './IfElse'
|
||||
export { default as IterationStart } from './IterationStart'
|
||||
export { default as Iteration } from './Iteration'
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ import {
|
|||
End,
|
||||
Home,
|
||||
Http,
|
||||
HumanInLoop,
|
||||
IfElse,
|
||||
Iteration,
|
||||
KnowledgeRetrieval,
|
||||
|
|
@ -60,6 +61,7 @@ const getIcon = (type: BlockEnum, className: string) => {
|
|||
[BlockEnum.DocExtractor]: <DocsExtractor className={className} />,
|
||||
[BlockEnum.ListFilter]: <ListFilter className={className} />,
|
||||
[BlockEnum.Agent]: <Agent className={className} />,
|
||||
[BlockEnum.HumanInput]: <HumanInLoop className={className} />,
|
||||
}[type]
|
||||
}
|
||||
const ICON_CONTAINER_BG_COLOR_MAP: Record<string, string> = {
|
||||
|
|
@ -83,6 +85,7 @@ const ICON_CONTAINER_BG_COLOR_MAP: Record<string, string> = {
|
|||
[BlockEnum.DocExtractor]: 'bg-util-colors-green-green-500',
|
||||
[BlockEnum.ListFilter]: 'bg-util-colors-cyan-cyan-500',
|
||||
[BlockEnum.Agent]: 'bg-util-colors-indigo-indigo-500',
|
||||
[BlockEnum.HumanInput]: 'bg-util-colors-cyan-cyan-500',
|
||||
}
|
||||
const BlockIcon: FC<BlockIconProps> = ({
|
||||
type,
|
||||
|
|
|
|||
|
|
@ -100,6 +100,11 @@ export const BLOCKS: Block[] = [
|
|||
type: BlockEnum.Agent,
|
||||
title: 'Agent',
|
||||
},
|
||||
{
|
||||
classification: BlockClassificationEnum.Default,
|
||||
type: BlockEnum.HumanInput,
|
||||
title: 'Human Input',
|
||||
},
|
||||
]
|
||||
|
||||
export const BLOCK_CLASSIFICATIONS: string[] = [
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@ import IterationStartDefault from './nodes/iteration-start/default'
|
|||
import AgentDefault from './nodes/agent/default'
|
||||
import LoopStartDefault from './nodes/loop-start/default'
|
||||
import LoopEndDefault from './nodes/loop-end/default'
|
||||
import HumanInputDefault from './nodes/human-input/default'
|
||||
|
||||
type NodesExtraData = {
|
||||
author: string
|
||||
|
|
@ -242,6 +243,15 @@ export const NODES_EXTRA_DATA: Record<BlockEnum, NodesExtraData> = {
|
|||
getAvailableNextNodes: ListFilterDefault.getAvailableNextNodes,
|
||||
checkValid: AgentDefault.checkValid,
|
||||
},
|
||||
[BlockEnum.HumanInput]: {
|
||||
author: 'Dify',
|
||||
about: '',
|
||||
availablePrevNodes: [],
|
||||
availableNextNodes: [],
|
||||
getAvailablePrevNodes: HumanInputDefault.getAvailablePrevNodes,
|
||||
getAvailableNextNodes: HumanInputDefault.getAvailableNextNodes,
|
||||
checkValid: HumanInputDefault.checkValid,
|
||||
},
|
||||
}
|
||||
|
||||
export const NODES_INITIAL_DATA = {
|
||||
|
|
@ -401,6 +411,12 @@ export const NODES_INITIAL_DATA = {
|
|||
desc: '',
|
||||
...AgentDefault.defaultValue,
|
||||
},
|
||||
[BlockEnum.HumanInput]: {
|
||||
type: BlockEnum.HumanInput,
|
||||
title: '',
|
||||
desc: '',
|
||||
...HumanInputDefault.defaultValue,
|
||||
},
|
||||
}
|
||||
export const MAX_ITERATION_PARALLEL_NUM = 10
|
||||
export const MIN_ITERATION_PARALLEL_NUM = 1
|
||||
|
|
|
|||
|
|
@ -20,6 +20,8 @@ import TemplateTransformNode from './template-transform/node'
|
|||
import TemplateTransformPanel from './template-transform/panel'
|
||||
import HttpNode from './http/node'
|
||||
import HttpPanel from './http/panel'
|
||||
import HumanInputNode from './human-input/node'
|
||||
import HumanInputPanel from './human-input/panel'
|
||||
import ToolNode from './tool/node'
|
||||
import ToolPanel from './tool/panel'
|
||||
import VariableAssignerNode from './variable-assigner/node'
|
||||
|
|
@ -61,6 +63,7 @@ export const NodeComponentMap: Record<string, ComponentType<any>> = {
|
|||
[BlockEnum.DocExtractor]: DocExtractorNode,
|
||||
[BlockEnum.ListFilter]: ListFilterNode,
|
||||
[BlockEnum.Agent]: AgentNode,
|
||||
[BlockEnum.HumanInput]: HumanInputNode,
|
||||
}
|
||||
|
||||
export const PanelComponentMap: Record<string, ComponentType<any>> = {
|
||||
|
|
@ -84,6 +87,7 @@ export const PanelComponentMap: Record<string, ComponentType<any>> = {
|
|||
[BlockEnum.DocExtractor]: DocExtractorPanel,
|
||||
[BlockEnum.ListFilter]: ListFilterPanel,
|
||||
[BlockEnum.Agent]: AgentPanel,
|
||||
[BlockEnum.HumanInput]: HumanInputPanel,
|
||||
}
|
||||
|
||||
export const CUSTOM_NODE_TYPE = 'custom'
|
||||
|
|
|
|||
|
|
@ -0,0 +1,28 @@
|
|||
import type { NodeDefault } from '../../types'
|
||||
import type { HumanInputNodeType } from './types'
|
||||
import { ALL_CHAT_AVAILABLE_BLOCKS } from '@/app/components/workflow/blocks'
|
||||
|
||||
const nodeDefault: NodeDefault<HumanInputNodeType> = {
|
||||
defaultValue: {
|
||||
deliveryMethod: [],
|
||||
userActions: [],
|
||||
},
|
||||
getAvailablePrevNodes(isChatMode: boolean) {
|
||||
const nodes = isChatMode
|
||||
? ALL_CHAT_AVAILABLE_BLOCKS
|
||||
: []
|
||||
return nodes
|
||||
},
|
||||
getAvailableNextNodes() {
|
||||
const nodes = ALL_CHAT_AVAILABLE_BLOCKS
|
||||
return nodes
|
||||
},
|
||||
checkValid() {
|
||||
return {
|
||||
isValid: true,
|
||||
errorMessage: '',
|
||||
}
|
||||
},
|
||||
}
|
||||
|
||||
export default nodeDefault
|
||||
|
|
@ -0,0 +1,34 @@
|
|||
import type { FC } from 'react'
|
||||
import React from 'react'
|
||||
import type { HumanInputNodeType } from './types'
|
||||
import type { NodeProps } from '@/app/components/workflow/types'
|
||||
// import { isConversationVar, isENV, isSystemVar } from '@/app/components/workflow/nodes/_base/components/variable/utils'
|
||||
import {
|
||||
useIsChatMode,
|
||||
useWorkflow,
|
||||
useWorkflowVariables,
|
||||
} from '@/app/components/workflow/hooks'
|
||||
// import { VarBlockIcon } from '@/app/components/workflow/block-icon'
|
||||
// import { Line3 } from '@/app/components/base/icons/src/public/common'
|
||||
// import { Variable02 } from '@/app/components/base/icons/src/vender/solid/development'
|
||||
// import { BubbleX, Env } from '@/app/components/base/icons/src/vender/line/others'
|
||||
// import { BlockEnum } from '@/app/components/workflow/types'
|
||||
// import cn from 'classnames'
|
||||
|
||||
const Node: FC<NodeProps<HumanInputNodeType>> = ({
|
||||
id,
|
||||
data,
|
||||
}) => {
|
||||
const { getBeforeNodesInSameBranch } = useWorkflow()
|
||||
const availableNodes = getBeforeNodesInSameBranch(id)
|
||||
const { getCurrentVariableType } = useWorkflowVariables()
|
||||
const isChatMode = useIsChatMode()
|
||||
|
||||
return (
|
||||
<div className='mb-1 space-y-0.5 px-3 py-1'>
|
||||
TODO
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
export default React.memo(Node)
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
import type { FC } from 'react'
|
||||
import React from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import type { HumanInputNodeType } from './types'
|
||||
import type { NodePanelProps } from '@/app/components/workflow/types'
|
||||
|
||||
const i18nPrefix = 'workflow.nodes.humanInput'
|
||||
|
||||
const Panel: FC<NodePanelProps<HumanInputNodeType>> = ({
|
||||
id,
|
||||
data,
|
||||
}) => {
|
||||
const { t } = useTranslation()
|
||||
|
||||
return (
|
||||
<div className='mt-2'>
|
||||
<div className='space-y-4 px-4 pb-4'>
|
||||
TODO
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
export default React.memo(Panel)
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
import type { CommonNodeType, Variable } from '@/app/components/workflow/types'
|
||||
|
||||
export type HumanInputNodeType = CommonNodeType & {
|
||||
deliveryMethod: any[]
|
||||
formContent: any
|
||||
userActions: any[]
|
||||
timeout: any
|
||||
outputs: Variable[]
|
||||
}
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
import useVarList from '../_base/hooks/use-var-list'
|
||||
import type { HumanInputNodeType } from './types'
|
||||
import useNodeCrud from '@/app/components/workflow/nodes/_base/hooks/use-node-crud'
|
||||
import {
|
||||
useNodesReadOnly,
|
||||
} from '@/app/components/workflow/hooks'
|
||||
const useConfig = (id: string, payload: HumanInputNodeType) => {
|
||||
const { nodesReadOnly: readOnly } = useNodesReadOnly()
|
||||
const { inputs, setInputs } = useNodeCrud<HumanInputNodeType>(id, payload)
|
||||
|
||||
const { handleVarListChange, handleAddVariable } = useVarList<HumanInputNodeType>({
|
||||
inputs,
|
||||
setInputs: (newInputs) => {
|
||||
setInputs(newInputs)
|
||||
},
|
||||
varKey: 'outputs',
|
||||
})
|
||||
|
||||
return {
|
||||
readOnly,
|
||||
inputs,
|
||||
handleVarListChange,
|
||||
handleAddVariable,
|
||||
}
|
||||
}
|
||||
|
||||
export default useConfig
|
||||
|
|
@ -42,6 +42,7 @@ export enum BlockEnum {
|
|||
Loop = 'loop',
|
||||
LoopStart = 'loop-start',
|
||||
LoopEnd = 'loop-end',
|
||||
HumanInput = 'human-input',
|
||||
}
|
||||
|
||||
export enum ControlMode {
|
||||
|
|
|
|||
|
|
@ -258,6 +258,7 @@ const translation = {
|
|||
'loop-start': 'Loop Start',
|
||||
'loop': 'Loop',
|
||||
'loop-end': 'Exit Loop',
|
||||
'human-input': 'Human Input',
|
||||
},
|
||||
blocksAbout: {
|
||||
'start': 'Define the initial parameters for launching a workflow',
|
||||
|
|
@ -280,6 +281,7 @@ const translation = {
|
|||
'document-extractor': 'Used to parse uploaded documents into text content that is easily understandable by LLM.',
|
||||
'list-operator': 'Used to filter or sort array content.',
|
||||
'agent': 'Invoking large language models to answer questions or process natural language',
|
||||
'human-input': 'Ask for human to confirm before generating the next step',
|
||||
},
|
||||
operator: {
|
||||
zoomIn: 'Zoom In',
|
||||
|
|
@ -902,6 +904,11 @@ const translation = {
|
|||
clickToViewParameterSchema: 'Click to view parameter schema',
|
||||
parameterSchema: 'Parameter Schema',
|
||||
},
|
||||
humanInput: {
|
||||
deliveryMethod: 'delivery method',
|
||||
formContent: 'form content',
|
||||
userActions: 'user actions',
|
||||
},
|
||||
},
|
||||
tracing: {
|
||||
stopBy: 'Stop by {{user}}',
|
||||
|
|
|
|||
|
|
@ -259,6 +259,7 @@ const translation = {
|
|||
'loop-start': '循环开始',
|
||||
'loop': '循环',
|
||||
'loop-end': '退出循环',
|
||||
'human-input': '人类输入',
|
||||
},
|
||||
blocksAbout: {
|
||||
'start': '定义一个 workflow 流程启动的初始参数',
|
||||
|
|
@ -281,6 +282,7 @@ const translation = {
|
|||
'document-extractor': '用于将用户上传的文档解析为 LLM 便于理解的文本内容。',
|
||||
'list-operator': '用于过滤或排序数组内容。',
|
||||
'agent': '调用大型语言模型回答问题或处理自然语言',
|
||||
'human-input': '人工输入,确认后生成下一步',
|
||||
},
|
||||
operator: {
|
||||
zoomIn: '放大',
|
||||
|
|
@ -903,6 +905,11 @@ const translation = {
|
|||
clickToViewParameterSchema: '点击查看参数 schema',
|
||||
parameterSchema: '参数 Schema',
|
||||
},
|
||||
humanInput: {
|
||||
deliveryMethod: '提交方式',
|
||||
formContent: '表单内容',
|
||||
userActions: '用户操作',
|
||||
},
|
||||
},
|
||||
tracing: {
|
||||
stopBy: '由{{user}}终止',
|
||||
|
|
|
|||
Loading…
Reference in New Issue