fix: can remove struct

This commit is contained in:
Joel 2024-03-22 14:35:12 +08:00
parent 4f3872277c
commit 66cf787755
6 changed files with 147 additions and 9 deletions

View File

@ -88,7 +88,7 @@ const ModelParameterModal: FC<ModelParameterModalProps> = ({
}) => {
const { t } = useTranslation()
const { hasSettedApiKey } = useProviderContext()
const [open, setOpen] = useState(true)
const [open, setOpen] = useState(false)
const { data: parameterRulesData, isLoading } = useSWR((provider && modelId) ? `/workspaces/current/model-providers/${provider}/models/parameter-rules?model=${modelId}` : null, fetchModelParameterRules)
const {
currentProvider,

View File

@ -42,7 +42,7 @@ import {
START_INITIAL_POSITION,
SUPPORT_OUTPUT_VARS_NODE,
} from '../constants'
import { findUsedVarNodes, updateNodeVars } from '../nodes/_base/components/variable/utils'
import { findUsedVarNodes, getNodeOutputVars, updateNodeVars } from '../nodes/_base/components/variable/utils'
import {
useNodesExtraData,
useNodesInitialData,
@ -233,6 +233,35 @@ export const useWorkflow = () => {
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [store])
const isVarUsedInNodes = useCallback((nodeId: string, varSelector: ValueSelector) => {
const afterNodes = getAfterNodesInSameBranch(nodeId)
const effectNodes = findUsedVarNodes(varSelector, afterNodes)
return effectNodes.length > 0
}, [getAfterNodesInSameBranch])
const removeUsedVarInNodes = useCallback((nodeId: string, varSelector: ValueSelector) => {
const { getNodes, setNodes } = store.getState()
const afterNodes = getAfterNodesInSameBranch(nodeId)
const effectNodes = findUsedVarNodes(varSelector, afterNodes)
if (effectNodes.length > 0) {
const newNodes = getNodes().map((node) => {
if (effectNodes.find(n => n.id === node.id))
return updateNodeVars(node, varSelector, [])
return node
})
setNodes(newNodes)
}
}, [getAfterNodesInSameBranch, store])
const isNodeVarsUsedInNodes = useCallback((node: Node, isChatMode: boolean) => {
const outputVars = getNodeOutputVars(node, isChatMode)
const isUsed = outputVars.some((varSelector) => {
return isVarUsedInNodes(node.id, varSelector)
})
return isUsed
}, [isVarUsedInNodes])
const isValidConnection = useCallback(({ source, target }: Connection) => {
const { getNodes } = store.getState()
const nodes = getNodes()
@ -317,6 +346,9 @@ export const useWorkflow = () => {
getBeforeNodesInSameBranch,
getAfterNodesInSameBranch,
handleOutVarRenameChange,
isVarUsedInNodes,
removeUsedVarInNodes,
isNodeVarsUsedInNodes,
isValidConnection,
formatTimeFromNow,
getValidTreeNodes,

View File

@ -211,7 +211,7 @@ export const getVarType = (value: ValueSelector, availableNodes: any[], isChatMo
}
}
const getNodeUsedVars = (node: Node): ValueSelector[] => {
export const getNodeUsedVars = (node: Node): ValueSelector[] => {
const { data } = node
const { type } = data
let res: ValueSelector[] = []
@ -421,3 +421,98 @@ export const updateNodeVars = (oldNode: Node, oldVarSelector: ValueSelector, new
})
return newNode
}
const varToValueSelectorList = (v: Var, parentValueSelector: ValueSelector, res: ValueSelector[]) => {
if (!v.variable)
return
res.push([...parentValueSelector, v.variable])
if (v.children && v.children.length > 0) {
v.children.forEach((child) => {
varToValueSelectorList(child, [...parentValueSelector, v.variable], res)
})
}
}
const varsToValueSelectorList = (vars: Var | Var[], parentValueSelector: ValueSelector, res: ValueSelector[]) => {
if (Array.isArray(vars)) {
vars.forEach((v) => {
varToValueSelectorList(v, parentValueSelector, res)
})
}
varToValueSelectorList(vars as Var, parentValueSelector, res)
}
// const test: ValueSelector[] = []
// varsToValueSelectorList(LLM_OUTPUT_STRUCT, ['ttt'], test)
// console.log(test)
export const getNodeOutputVars = (node: Node, isChatMode: boolean): ValueSelector[] => {
const { data, id } = node
const { type } = data
let res: ValueSelector[] = []
switch (type) {
case BlockEnum.Start: {
const {
variables,
} = data as StartNodeType
res = variables.map((v) => {
return [id, v.variable]
})
if (isChatMode) {
res.push([id, 'sys', 'query'])
res.push([id, 'sys', 'files'])
}
break
}
case BlockEnum.LLM: {
varsToValueSelectorList(LLM_OUTPUT_STRUCT, [id], res)
break
}
case BlockEnum.KnowledgeRetrieval: {
varsToValueSelectorList(KNOWLEDGE_RETRIEVAL_OUTPUT_STRUCT, [id], res)
break
}
case BlockEnum.Code: {
const {
outputs,
} = data as CodeNodeType
Object.keys(outputs).forEach((key) => {
res.push([id, key])
})
break
}
case BlockEnum.TemplateTransform: {
varsToValueSelectorList(TEMPLATE_TRANSFORM_OUTPUT_STRUCT, [id], res)
break
}
case BlockEnum.QuestionClassifier: {
varsToValueSelectorList(isChatMode ? CHAT_QUESTION_CLASSIFIER_OUTPUT_STRUCT : COMPLETION_QUESTION_CLASSIFIER_OUTPUT_STRUCT, [id], res)
break
}
case BlockEnum.HttpRequest: {
varsToValueSelectorList(HTTP_REQUEST_OUTPUT_STRUCT, [id], res)
break
}
case BlockEnum.VariableAssigner: {
res.push([id, 'output'])
break
}
case BlockEnum.Tool: {
varsToValueSelectorList(TOOL_OUTPUT_STRUCT, [id], res)
break
}
}
return res
}

View File

@ -4,7 +4,7 @@ import React, { useCallback } from 'react'
import produce from 'immer'
import { useTranslation } from 'react-i18next'
import VarItem from './var-item'
import type { InputVar, MoreInfo } from '@/app/components/workflow/types'
import { ChangeType, type InputVar, type MoreInfo } from '@/app/components/workflow/types'
type Props = {
readonly: boolean
list: InputVar[]
@ -32,7 +32,15 @@ const VarList: FC<Props> = ({
const newList = produce(list, (draft) => {
draft.splice(index, 1)
})
onChange(newList)
onChange(newList, {
index,
payload: {
type: ChangeType.remove,
payload: {
beforeKey: list[index].variable,
},
},
})
}
}, [list, onChange])

View File

@ -2,7 +2,7 @@ import { useCallback } from 'react'
import produce from 'immer'
import { useBoolean } from 'ahooks'
import type { StartNodeType } from './types'
import type { InputVar, MoreInfo } from '@/app/components/workflow/types'
import { ChangeType, type InputVar, type MoreInfo } from '@/app/components/workflow/types'
import useNodeCrud from '@/app/components/workflow/nodes/_base/hooks/use-node-crud'
import {
useIsChatMode,
@ -12,7 +12,7 @@ import {
const useConfig = (id: string, payload: StartNodeType) => {
const { nodesReadOnly: readOnly } = useNodesReadOnly()
const { handleOutVarRenameChange } = useWorkflow()
const { handleOutVarRenameChange, removeUsedVarInNodes } = useWorkflow()
const isChatMode = useIsChatMode()
const { inputs, setInputs } = useNodeCrud<StartNodeType>(id, payload)
@ -27,10 +27,12 @@ const useConfig = (id: string, payload: StartNodeType) => {
draft.variables = newList
})
setInputs(newInputs)
if (moreInfo) {
if (moreInfo?.payload?.type === ChangeType.changeVarName) {
const changedVar = newList[moreInfo.index]
handleOutVarRenameChange(id, [id, inputs.variables[moreInfo.index].variable], [id, changedVar.variable])
}
if (moreInfo?.payload?.type === ChangeType.remove)
removeUsedVarInNodes(id, [id, moreInfo?.payload?.payload?.beforeKey || ''])
}, [handleOutVarRenameChange, id, inputs, setInputs])
const handleAddVariable = useCallback((payload: InputVar) => {

View File

@ -255,13 +255,14 @@ export type HistoryWorkflowData = {
export enum ChangeType {
changeVarName = 'changeVarName',
remove = 'remove',
}
export type MoreInfo = {
type: ChangeType
payload?: {
beforeKey: string
afterKey: string
afterKey?: string
}
}