mirror of
https://git.mirrors.martin98.com/https://github.com/infiniflow/ragflow.git
synced 2025-08-13 12:58:59 +08:00
feat: add description text to operators and extract the useFetchModelId to logicHooks.ts and drag the operator to the canvas and initialize the form data #918 (#1379)
### What problem does this PR solve? feat: add description text to operators #918 feat: drag the operator to the canvas and initialize the form data #918 feat: extract the useFetchModelId to logicHooks.ts ### Type of change - [x] New Feature (non-breaking change which adds functionality)
This commit is contained in:
parent
306108fe0e
commit
25a8c076bf
@ -1,40 +1,40 @@
|
||||
import { defineConfig } from 'umi';
|
||||
import { appName } from './src/conf.json';
|
||||
import routes from './src/routes';
|
||||
|
||||
export default defineConfig({
|
||||
title: appName,
|
||||
outputPath: 'dist',
|
||||
// alias: { '@': './src' },
|
||||
npmClient: 'npm',
|
||||
base: '/',
|
||||
routes,
|
||||
publicPath: '/',
|
||||
esbuildMinifyIIFE: true,
|
||||
icons: {},
|
||||
hash: true,
|
||||
favicons: ['/logo.svg'],
|
||||
clickToComponent: {},
|
||||
history: {
|
||||
type: 'browser',
|
||||
},
|
||||
plugins: ['@react-dev-inspector/umi4-plugin', '@umijs/plugins/dist/dva'],
|
||||
dva: {},
|
||||
|
||||
lessLoader: {
|
||||
modifyVars: {
|
||||
hack: `true; @import "~@/less/index.less";`,
|
||||
},
|
||||
},
|
||||
devtool: 'source-map',
|
||||
copy: ['src/conf.json'],
|
||||
proxy: {
|
||||
'/v1': {
|
||||
target: '',
|
||||
changeOrigin: true,
|
||||
ws: true,
|
||||
logger: console,
|
||||
// pathRewrite: { '^/v1': '/v1' },
|
||||
},
|
||||
},
|
||||
});
|
||||
import { defineConfig } from 'umi';
|
||||
import { appName } from './src/conf.json';
|
||||
import routes from './src/routes';
|
||||
|
||||
export default defineConfig({
|
||||
title: appName,
|
||||
outputPath: 'dist',
|
||||
// alias: { '@': './src' },
|
||||
npmClient: 'npm',
|
||||
base: '/',
|
||||
routes,
|
||||
publicPath: '/',
|
||||
esbuildMinifyIIFE: true,
|
||||
icons: {},
|
||||
hash: true,
|
||||
favicons: ['/logo.svg'],
|
||||
clickToComponent: {},
|
||||
history: {
|
||||
type: 'browser',
|
||||
},
|
||||
plugins: ['@react-dev-inspector/umi4-plugin', '@umijs/plugins/dist/dva'],
|
||||
dva: {},
|
||||
|
||||
lessLoader: {
|
||||
modifyVars: {
|
||||
hack: `true; @import "~@/less/index.less";`,
|
||||
},
|
||||
},
|
||||
devtool: 'source-map',
|
||||
copy: ['src/conf.json'],
|
||||
proxy: {
|
||||
'/v1': {
|
||||
target: '',
|
||||
changeOrigin: true,
|
||||
ws: true,
|
||||
logger: console,
|
||||
// pathRewrite: { '^/v1': '/v1' },
|
||||
},
|
||||
},
|
||||
});
|
||||
|
@ -4,10 +4,10 @@
|
||||
display: inline-block;
|
||||
}
|
||||
.messageItemSectionLeft {
|
||||
width: 70%;
|
||||
width: 80%;
|
||||
}
|
||||
.messageItemSectionRight {
|
||||
width: 40%;
|
||||
width: 80%;
|
||||
}
|
||||
.messageItemContent {
|
||||
display: inline-flex;
|
||||
|
@ -22,8 +22,13 @@ import { useTranslation } from 'react-i18next';
|
||||
import { useDispatch } from 'umi';
|
||||
import { useSetModalState, useTranslate } from './commonHooks';
|
||||
import { useSetDocumentParser } from './documentHooks';
|
||||
import { useFetchLlmList } from './llmHooks';
|
||||
import { useOneNamespaceEffectsLoading } from './storeHooks';
|
||||
import { useSaveSetting } from './userSettingHook';
|
||||
import {
|
||||
useFetchTenantInfo,
|
||||
useSaveSetting,
|
||||
useSelectTenantInfo,
|
||||
} from './userSettingHook';
|
||||
|
||||
export const useChangeDocumentParser = (documentId: string) => {
|
||||
const setDocumentParser = useSetDocumentParser();
|
||||
@ -269,3 +274,26 @@ export const useSelectItem = (defaultId?: string) => {
|
||||
|
||||
return { selectedId, handleItemClick };
|
||||
};
|
||||
|
||||
export const useFetchModelId = (visible: boolean) => {
|
||||
const fetchTenantInfo = useFetchTenantInfo(false);
|
||||
const tenantInfo = useSelectTenantInfo();
|
||||
|
||||
useEffect(() => {
|
||||
if (visible) {
|
||||
fetchTenantInfo();
|
||||
}
|
||||
}, [visible, fetchTenantInfo]);
|
||||
|
||||
return tenantInfo?.llm_id ?? '';
|
||||
};
|
||||
|
||||
export const useFetchLlmModelOnVisible = (visible: boolean) => {
|
||||
const fetchLlmList = useFetchLlmList();
|
||||
|
||||
useEffect(() => {
|
||||
if (visible) {
|
||||
fetchLlmList();
|
||||
}
|
||||
}, [fetchLlmList, visible]);
|
||||
};
|
||||
|
@ -565,6 +565,17 @@ The above is the content you need to summarize.`,
|
||||
componentId: 'component id',
|
||||
add: 'Add',
|
||||
operation: 'operation',
|
||||
beginDescription: 'This is where the flow begin',
|
||||
answerDescription: `This component is used as an interface between bot and human. It receives input of user and display the result of the computation of the bot.`,
|
||||
retrievalDescription: `This component is for the process of retrieving relevent information from knowledge base. So, knowledgebases should be selected. If there's nothing retrieved, the 'Empty response' will be returned.`,
|
||||
generateDescription: `This component is used to call LLM to generate text. Be careful about the prompt setting.`,
|
||||
categorizeDescription: `This component is used to categorize text. Please specify the name, description and examples of the category. Every single category leads to different downstream components.`,
|
||||
relevantDescription: `This component is used to judge if the retrieved information is relevent to user's question. 'Yes' represents that they're relevant. 'No' represents they're irrelevant.`,
|
||||
rewriteQuestionDescription: `This component is used to refine user's quesion. Typically, when a user's original question can't retrieve relevant information from knowledge base, this component help you change the question into a proper one which might be more consistant with the expressions in knowledge base. Only 'Retrieval' can be its downstreams.`,
|
||||
messageDescription:
|
||||
'This component is used to send user static information.',
|
||||
keywordDescription:
|
||||
'This component is used to send user static information.',
|
||||
},
|
||||
footer: {
|
||||
profile: 'All rights reserved @ React',
|
||||
|
@ -1,29 +0,0 @@
|
||||
import { useFetchLlmList } from '@/hooks/llmHooks';
|
||||
import {
|
||||
useFetchTenantInfo,
|
||||
useSelectTenantInfo,
|
||||
} from '@/hooks/userSettingHook';
|
||||
import { useEffect } from 'react';
|
||||
|
||||
export const useFetchModelId = (visible: boolean) => {
|
||||
const fetchTenantInfo = useFetchTenantInfo(false);
|
||||
const tenantInfo = useSelectTenantInfo();
|
||||
|
||||
useEffect(() => {
|
||||
if (visible) {
|
||||
fetchTenantInfo();
|
||||
}
|
||||
}, [visible, fetchTenantInfo]);
|
||||
|
||||
return tenantInfo?.llm_id ?? '';
|
||||
};
|
||||
|
||||
export const useFetchLlmModelOnVisible = (visible: boolean) => {
|
||||
const fetchLlmList = useFetchLlmList();
|
||||
|
||||
useEffect(() => {
|
||||
if (visible) {
|
||||
fetchLlmList();
|
||||
}
|
||||
}, [fetchLlmList, visible]);
|
||||
};
|
@ -11,11 +11,11 @@ import camelCase from 'lodash/camelCase';
|
||||
import { useEffect, useRef, useState } from 'react';
|
||||
import { IPromptConfigParameters } from '../interface';
|
||||
import AssistantSetting from './assistant-setting';
|
||||
import { useFetchLlmModelOnVisible, useFetchModelId } from './hooks';
|
||||
import ModelSetting from './model-setting';
|
||||
import PromptEngine from './prompt-engine';
|
||||
|
||||
import { useTranslate } from '@/hooks/commonHooks';
|
||||
import { useFetchLlmModelOnVisible, useFetchModelId } from '@/hooks/logicHooks';
|
||||
import { getBase64FromUploadFileList } from '@/utils/fileUtil';
|
||||
import { removeUselessFieldsFromValues } from '@/utils/form';
|
||||
import styles from './index.less';
|
||||
|
@ -1,16 +1,19 @@
|
||||
import { useFetchFlow } from '@/hooks/flow-hooks';
|
||||
import { IModalProps } from '@/interfaces/common';
|
||||
import { Drawer } from 'antd';
|
||||
import FlowChatBox from './box';
|
||||
|
||||
const ChatDrawer = ({ visible, hideModal }: IModalProps<any>) => {
|
||||
const { data } = useFetchFlow();
|
||||
|
||||
return (
|
||||
<Drawer
|
||||
title="Debug"
|
||||
title={data.title}
|
||||
placement="right"
|
||||
onClose={hideModal}
|
||||
open={visible}
|
||||
getContainer={false}
|
||||
width={window.innerWidth > 1278 ? '30%' : 470}
|
||||
width={window.innerWidth > 1278 ? '40%' : 470}
|
||||
mask={false}
|
||||
// zIndex={10000}
|
||||
>
|
||||
|
@ -1,3 +1,4 @@
|
||||
import { variableEnabledFieldMap } from '@/constants/chat';
|
||||
import {
|
||||
BranchesOutlined,
|
||||
DatabaseOutlined,
|
||||
@ -33,7 +34,7 @@ export const operatorIconMap = {
|
||||
|
||||
export const operatorMap = {
|
||||
[Operator.Retrieval]: {
|
||||
description: 'Retrieval description drjlftglrthjftl',
|
||||
description: 'This is where the flow begin',
|
||||
backgroundColor: '#cad6e0',
|
||||
color: '#385974',
|
||||
},
|
||||
@ -47,7 +48,8 @@ export const operatorMap = {
|
||||
color: '#996464',
|
||||
},
|
||||
[Operator.Answer]: {
|
||||
description: 'Answer description',
|
||||
description:
|
||||
'This component is used as an interface between bot and human. It receives input of user and display the result of the computation of the bot.',
|
||||
backgroundColor: '#f4816d',
|
||||
color: 'white',
|
||||
},
|
||||
@ -126,7 +128,15 @@ export const initialBeginValues = {
|
||||
prologue: `Hi! I'm your assistant, what can I do for you?`,
|
||||
};
|
||||
|
||||
export const variableCheckBoxFieldMap = Object.keys(
|
||||
variableEnabledFieldMap,
|
||||
).reduce<Record<string, boolean>>((pre, cur) => {
|
||||
pre[cur] = true;
|
||||
return pre;
|
||||
}, {});
|
||||
|
||||
const initialLlmBaseValues = {
|
||||
...variableCheckBoxFieldMap,
|
||||
temperature: 0.1,
|
||||
top_p: 0.3,
|
||||
frequency_penalty: 0.7,
|
||||
@ -196,7 +206,14 @@ export const RestrictedUpstreamMap = {
|
||||
[Operator.Answer]: [],
|
||||
[Operator.Retrieval]: [],
|
||||
[Operator.Generate]: [],
|
||||
[Operator.Message]: [],
|
||||
[Operator.Message]: [
|
||||
Operator.Begin,
|
||||
Operator.Message,
|
||||
Operator.Generate,
|
||||
Operator.Retrieval,
|
||||
Operator.RewriteQuestion,
|
||||
Operator.Categorize,
|
||||
],
|
||||
[Operator.Relevant]: [],
|
||||
[Operator.RewriteQuestion]: [],
|
||||
};
|
||||
|
@ -1,6 +1,7 @@
|
||||
import { Card, Flex, Layout, Space, Typography } from 'antd';
|
||||
import { useTranslate } from '@/hooks/commonHooks';
|
||||
import { Card, Flex, Layout, Space, Tooltip } from 'antd';
|
||||
import classNames from 'classnames';
|
||||
|
||||
import lowerFirst from 'lodash/lowerFirst';
|
||||
import { componentMenuList } from '../constant';
|
||||
import { useHandleDrag } from '../hooks';
|
||||
import OperatorIcon from '../operator-icon';
|
||||
@ -8,8 +9,6 @@ import styles from './index.less';
|
||||
|
||||
const { Sider } = Layout;
|
||||
|
||||
const { Text } = Typography;
|
||||
|
||||
interface IProps {
|
||||
setCollapsed: (width: boolean) => void;
|
||||
collapsed: boolean;
|
||||
@ -17,6 +16,7 @@ interface IProps {
|
||||
|
||||
const FlowSide = ({ setCollapsed, collapsed }: IProps) => {
|
||||
const { handleDragStart } = useHandleDrag();
|
||||
const { t } = useTranslate('flow');
|
||||
|
||||
return (
|
||||
<Sider
|
||||
@ -40,13 +40,9 @@ const FlowSide = ({ setCollapsed, collapsed }: IProps) => {
|
||||
<Space size={15}>
|
||||
<OperatorIcon name={x.name}></OperatorIcon>
|
||||
<section>
|
||||
<b>{x.name}</b>
|
||||
<Text
|
||||
ellipsis={{ tooltip: x.description }}
|
||||
style={{ width: 130 }}
|
||||
>
|
||||
{x.description}
|
||||
</Text>
|
||||
<Tooltip title={t(`${lowerFirst(x.name)}Description`)}>
|
||||
<b>{x.name}</b>
|
||||
</Tooltip>
|
||||
</section>
|
||||
</Space>
|
||||
</Flex>
|
||||
|
@ -17,13 +17,25 @@ import {
|
||||
ModelVariableType,
|
||||
settledModelVariableMap,
|
||||
} from '@/constants/knowledge';
|
||||
import { useFetchModelId } from '@/hooks/logicHooks';
|
||||
import { Variable } from '@/interfaces/database/chat';
|
||||
import { useDebounceEffect } from 'ahooks';
|
||||
import { FormInstance, message } from 'antd';
|
||||
import { humanId } from 'human-id';
|
||||
import trim from 'lodash/trim';
|
||||
import { useParams } from 'umi';
|
||||
import { NodeMap, Operator, RestrictedUpstreamMap } from './constant';
|
||||
import {
|
||||
NodeMap,
|
||||
Operator,
|
||||
RestrictedUpstreamMap,
|
||||
initialBeginValues,
|
||||
initialCategorizeValues,
|
||||
initialGenerateValues,
|
||||
initialMessageValues,
|
||||
initialRelevantValues,
|
||||
initialRetrievalValues,
|
||||
initialRewriteQuestionValues,
|
||||
} from './constant';
|
||||
import useGraphStore, { RFState } from './store';
|
||||
import { buildDslComponentsByGraph } from './utils';
|
||||
|
||||
@ -43,6 +55,32 @@ export const useSelectCanvasData = () => {
|
||||
return useGraphStore(selector);
|
||||
};
|
||||
|
||||
export const useInitializeOperatorParams = () => {
|
||||
const llmId = useFetchModelId(true);
|
||||
|
||||
const initializeOperatorParams = useCallback(
|
||||
(operatorName: Operator) => {
|
||||
const initialFormValuesMap = {
|
||||
[Operator.Begin]: initialBeginValues,
|
||||
[Operator.Retrieval]: initialRetrievalValues,
|
||||
[Operator.Generate]: { ...initialGenerateValues, llm_id: llmId },
|
||||
[Operator.Answer]: {},
|
||||
[Operator.Categorize]: { ...initialCategorizeValues, llm_id: llmId },
|
||||
[Operator.Relevant]: { ...initialRelevantValues, llm_id: llmId },
|
||||
[Operator.RewriteQuestion]: {
|
||||
...initialRewriteQuestionValues,
|
||||
llm_id: llmId,
|
||||
},
|
||||
[Operator.Message]: initialMessageValues,
|
||||
};
|
||||
return initialFormValuesMap[operatorName];
|
||||
},
|
||||
[llmId],
|
||||
);
|
||||
|
||||
return initializeOperatorParams;
|
||||
};
|
||||
|
||||
export const useHandleDrag = () => {
|
||||
const handleDragStart = useCallback(
|
||||
(operatorId: string) => (ev: React.DragEvent<HTMLDivElement>) => {
|
||||
@ -59,6 +97,7 @@ export const useHandleDrop = () => {
|
||||
const addNode = useGraphStore((state) => state.addNode);
|
||||
const [reactFlowInstance, setReactFlowInstance] =
|
||||
useState<ReactFlowInstance<any, any>>();
|
||||
const initializeOperatorParams = useInitializeOperatorParams();
|
||||
|
||||
const onDragOver = useCallback((event: React.DragEvent<HTMLDivElement>) => {
|
||||
event.preventDefault();
|
||||
@ -93,6 +132,7 @@ export const useHandleDrop = () => {
|
||||
data: {
|
||||
label: `${type}`,
|
||||
name: humanId(),
|
||||
form: initializeOperatorParams(type as Operator),
|
||||
},
|
||||
sourcePosition: Position.Right,
|
||||
targetPosition: Position.Left,
|
||||
@ -100,7 +140,7 @@ export const useHandleDrop = () => {
|
||||
|
||||
addNode(newNode);
|
||||
},
|
||||
[reactFlowInstance, addNode],
|
||||
[reactFlowInstance, addNode, initializeOperatorParams],
|
||||
);
|
||||
|
||||
return { onDrop, onDragOver, setReactFlowInstance };
|
||||
@ -244,7 +284,10 @@ export const useSetLlmSetting = (form?: FormInstance) => {
|
||||
return pre;
|
||||
}, {});
|
||||
const otherValues = settledModelVariableMap[ModelVariableType.Precise];
|
||||
form?.setFieldsValue({ ...switchBoxValues, ...otherValues });
|
||||
form?.setFieldsValue({
|
||||
...switchBoxValues,
|
||||
...otherValues,
|
||||
});
|
||||
}, [form, initialLlmSetting]);
|
||||
};
|
||||
|
||||
|
@ -56,6 +56,6 @@
|
||||
}
|
||||
|
||||
.templatesBox {
|
||||
max-height: 500px;
|
||||
// max-height: 500px;
|
||||
overflow: auto;
|
||||
}
|
||||
|
@ -2,11 +2,11 @@ import { DSLComponents } from '@/interfaces/database/flow';
|
||||
import { removeUselessFieldsFromValues } from '@/utils/form';
|
||||
import dagre from 'dagre';
|
||||
import { humanId } from 'human-id';
|
||||
import { curry, isEmpty } from 'lodash';
|
||||
import { curry } from 'lodash';
|
||||
import pipe from 'lodash/fp/pipe';
|
||||
import { Edge, Node, Position } from 'reactflow';
|
||||
import { v4 as uuidv4 } from 'uuid';
|
||||
import { NodeMap, Operator, initialFormValuesMap } from './constant';
|
||||
import { NodeMap, Operator } from './constant';
|
||||
import { ICategorizeItemResult, NodeData } from './interface';
|
||||
|
||||
const buildEdges = (
|
||||
@ -143,17 +143,17 @@ const removeUselessDataInTheOperator = curry(
|
||||
},
|
||||
);
|
||||
// initialize data for operators without parameters
|
||||
const initializeOperatorParams = curry((operatorName: string, values: any) => {
|
||||
if (isEmpty(values)) {
|
||||
return initialFormValuesMap[operatorName as Operator];
|
||||
}
|
||||
return values;
|
||||
});
|
||||
// const initializeOperatorParams = curry((operatorName: string, values: any) => {
|
||||
// if (isEmpty(values)) {
|
||||
// return initialFormValuesMap[operatorName as Operator];
|
||||
// }
|
||||
// return values;
|
||||
// });
|
||||
|
||||
const buildOperatorParams = (operatorName: string) =>
|
||||
pipe(
|
||||
removeUselessDataInTheOperator(operatorName),
|
||||
initializeOperatorParams(operatorName), // Final processing, for guarantee
|
||||
// initializeOperatorParams(operatorName), // Final processing, for guarantee
|
||||
);
|
||||
|
||||
// construct a dsl based on the node information of the graph
|
||||
|
Loading…
x
Reference in New Issue
Block a user