mirror of
https://github.com/infiniflow/ragflow.git
synced 2025-12-08 12:32:30 +08:00
### What problem does this PR solve? Feat: Add TavilyExtract operator #3221 ### Type of change - [x] New Feature (non-breaking change which adds functionality)
This commit is contained in:
@ -1291,6 +1291,7 @@ This delimiter is used to split the input text into several text pieces echo of
|
||||
agent: 'Agent',
|
||||
agentDescription:
|
||||
'Builds agent components equipped with reasoning, tool usage, and multi-agent collaboration. ',
|
||||
maxRecords: 'Max records',
|
||||
},
|
||||
llmTools: {
|
||||
bad_calculator: {
|
||||
|
||||
@ -1244,6 +1244,7 @@ General:实体和关系提取提示来自 GitHub - microsoft/graphrag:基于
|
||||
query: '查询变量',
|
||||
agent: 'Agent',
|
||||
agentDescription: '构建具备推理、工具调用和多智能体协同的智能体组件。',
|
||||
maxRecords: '最大记录数',
|
||||
},
|
||||
footer: {
|
||||
profile: 'All rights reserved @ React',
|
||||
|
||||
@ -1,112 +0,0 @@
|
||||
import { SideDown } from '@/assets/icon/Icon';
|
||||
import { Card, CardContent } from '@/components/ui/card';
|
||||
import {
|
||||
Collapsible,
|
||||
CollapsibleContent,
|
||||
CollapsibleTrigger,
|
||||
} from '@/components/ui/collapsible';
|
||||
import {
|
||||
Sidebar,
|
||||
SidebarContent,
|
||||
SidebarGroup,
|
||||
SidebarGroupContent,
|
||||
SidebarGroupLabel,
|
||||
SidebarHeader,
|
||||
SidebarMenu,
|
||||
} from '@/components/ui/sidebar';
|
||||
import { memo, useMemo } from 'react';
|
||||
import {
|
||||
AgentOperatorList,
|
||||
Operator,
|
||||
componentMenuList,
|
||||
operatorMap,
|
||||
} from './constant';
|
||||
import { useHandleDrag } from './hooks';
|
||||
import OperatorIcon from './operator-icon';
|
||||
|
||||
type OperatorItem = {
|
||||
name: Operator;
|
||||
};
|
||||
|
||||
function OperatorCard({ name }: OperatorItem) {
|
||||
const { handleDragStart } = useHandleDrag();
|
||||
|
||||
return (
|
||||
<Card
|
||||
draggable
|
||||
onDragStart={handleDragStart(name)}
|
||||
className="bg-colors-background-inverse-weak border-colors-outline-neutral-standard cursor-pointer"
|
||||
>
|
||||
<CardContent className="p-2 flex items-center gap-2">
|
||||
<OperatorIcon
|
||||
name={name}
|
||||
color={operatorMap[name].color}
|
||||
></OperatorIcon>
|
||||
{name}
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
||||
|
||||
type OperatorCollapsibleProps = { operatorList: OperatorItem[]; title: string };
|
||||
|
||||
function OperatorCollapsible({
|
||||
operatorList,
|
||||
title,
|
||||
}: OperatorCollapsibleProps) {
|
||||
return (
|
||||
<Collapsible defaultOpen className="group/collapsible">
|
||||
<SidebarGroup>
|
||||
<SidebarGroupLabel asChild className="mb-1">
|
||||
<CollapsibleTrigger>
|
||||
<span className="font-bold text-base">{title}</span>
|
||||
<SideDown className="ml-auto" />
|
||||
</CollapsibleTrigger>
|
||||
</SidebarGroupLabel>
|
||||
<CollapsibleContent className="px-2">
|
||||
<SidebarGroupContent>
|
||||
<SidebarMenu className="gap-2">
|
||||
{operatorList.map((item) => (
|
||||
<OperatorCard key={item.name} name={item.name}></OperatorCard>
|
||||
))}
|
||||
</SidebarMenu>
|
||||
</SidebarGroupContent>
|
||||
</CollapsibleContent>
|
||||
</SidebarGroup>
|
||||
</Collapsible>
|
||||
);
|
||||
}
|
||||
|
||||
function InnerAgentSidebar() {
|
||||
const agentOperatorList = useMemo(() => {
|
||||
return componentMenuList.filter((x) =>
|
||||
AgentOperatorList.some((y) => y === x.name),
|
||||
);
|
||||
}, []);
|
||||
|
||||
const thirdOperatorList = useMemo(() => {
|
||||
return componentMenuList.filter(
|
||||
(x) => !AgentOperatorList.some((y) => y === x.name),
|
||||
);
|
||||
}, []);
|
||||
|
||||
return (
|
||||
<Sidebar variant={'floating'} className="top-16">
|
||||
<SidebarHeader>
|
||||
<p className="font-bold text-2xl">All nodes</p>
|
||||
</SidebarHeader>
|
||||
<SidebarContent>
|
||||
<OperatorCollapsible
|
||||
title="Agent operator"
|
||||
operatorList={agentOperatorList}
|
||||
></OperatorCollapsible>
|
||||
<OperatorCollapsible
|
||||
title="Third-party tools"
|
||||
operatorList={thirdOperatorList}
|
||||
></OperatorCollapsible>
|
||||
</SidebarContent>
|
||||
</Sidebar>
|
||||
);
|
||||
}
|
||||
|
||||
export const AgentSidebar = memo(InnerAgentSidebar);
|
||||
@ -100,7 +100,7 @@ function AccordionOperators() {
|
||||
<OperatorItemList
|
||||
operators={[
|
||||
Operator.TavilySearch,
|
||||
Operator.Crawler,
|
||||
Operator.TavilyExtract,
|
||||
Operator.ExeSQL,
|
||||
Operator.Bing,
|
||||
]}
|
||||
|
||||
@ -87,6 +87,7 @@ export enum Operator {
|
||||
Agent = 'Agent',
|
||||
Tool = 'Tool',
|
||||
TavilySearch = 'TavilySearch',
|
||||
TavilyExtract = 'TavilyExtract',
|
||||
UserFillUp = 'UserFillUp',
|
||||
StringTransform = 'StringTransform',
|
||||
}
|
||||
@ -114,148 +115,6 @@ export const AgentOperatorList = [
|
||||
Operator.Agent,
|
||||
];
|
||||
|
||||
export const operatorMap: Record<
|
||||
Operator,
|
||||
{
|
||||
backgroundColor?: string;
|
||||
color?: string;
|
||||
width?: number;
|
||||
height?: number;
|
||||
fontSize?: number;
|
||||
iconFontSize?: number;
|
||||
iconWidth?: number;
|
||||
moreIconColor?: string;
|
||||
}
|
||||
> = {
|
||||
[Operator.Retrieval]: {
|
||||
backgroundColor: '#cad6e0',
|
||||
color: '#385974',
|
||||
},
|
||||
[Operator.Generate]: {
|
||||
backgroundColor: '#ebd6d6',
|
||||
width: 150,
|
||||
height: 150,
|
||||
fontSize: 20,
|
||||
iconFontSize: 30,
|
||||
color: '#996464',
|
||||
},
|
||||
[Operator.Answer]: {
|
||||
backgroundColor: '#f4816d',
|
||||
color: '#f4816d',
|
||||
},
|
||||
[Operator.Begin]: {
|
||||
backgroundColor: '#4f51d6',
|
||||
},
|
||||
[Operator.Categorize]: {
|
||||
backgroundColor: '#ffebcd',
|
||||
color: '#cc8a26',
|
||||
},
|
||||
[Operator.Message]: {
|
||||
backgroundColor: '#c5ddc7',
|
||||
color: 'green',
|
||||
},
|
||||
[Operator.Relevant]: {
|
||||
backgroundColor: '#9fd94d',
|
||||
color: '#8ef005',
|
||||
width: 70,
|
||||
height: 70,
|
||||
fontSize: 12,
|
||||
iconFontSize: 16,
|
||||
},
|
||||
[Operator.RewriteQuestion]: {
|
||||
backgroundColor: '#f8c7f8',
|
||||
color: '#f32bf3',
|
||||
width: 70,
|
||||
height: 70,
|
||||
fontSize: 12,
|
||||
iconFontSize: 16,
|
||||
},
|
||||
[Operator.KeywordExtract]: {
|
||||
width: 70,
|
||||
height: 70,
|
||||
backgroundColor: '#6E5494',
|
||||
color: '#6E5494',
|
||||
fontSize: 12,
|
||||
iconWidth: 16,
|
||||
},
|
||||
[Operator.DuckDuckGo]: {
|
||||
backgroundColor: '#e7e389',
|
||||
color: '#aea00c',
|
||||
},
|
||||
[Operator.Baidu]: {
|
||||
backgroundColor: '#d9e0f8',
|
||||
},
|
||||
[Operator.Wikipedia]: {
|
||||
backgroundColor: '#dee0e2',
|
||||
},
|
||||
[Operator.PubMed]: {
|
||||
backgroundColor: '#a2ccf0',
|
||||
},
|
||||
[Operator.ArXiv]: {
|
||||
width: 70,
|
||||
height: 70,
|
||||
fontSize: 12,
|
||||
iconWidth: 16,
|
||||
iconFontSize: 16,
|
||||
moreIconColor: 'white',
|
||||
backgroundColor: '#b31b1b',
|
||||
color: 'white',
|
||||
},
|
||||
[Operator.Google]: {
|
||||
backgroundColor: 'pink',
|
||||
},
|
||||
[Operator.Bing]: {
|
||||
backgroundColor: '#c0dcc4',
|
||||
},
|
||||
[Operator.GoogleScholar]: {
|
||||
backgroundColor: '#b4e4f6',
|
||||
},
|
||||
[Operator.DeepL]: {
|
||||
backgroundColor: '#f5e8e6',
|
||||
},
|
||||
[Operator.GitHub]: {
|
||||
backgroundColor: 'purple',
|
||||
color: 'purple',
|
||||
},
|
||||
[Operator.BaiduFanyi]: { backgroundColor: '#e5f2d3' },
|
||||
[Operator.QWeather]: {
|
||||
backgroundColor: '#a4bbf3',
|
||||
color: '#a4bbf3',
|
||||
},
|
||||
[Operator.ExeSQL]: { backgroundColor: '#b9efe8' },
|
||||
[Operator.Switch]: { backgroundColor: '#dbaff6', color: '#dbaff6' },
|
||||
[Operator.WenCai]: { backgroundColor: '#faac5b' },
|
||||
[Operator.AkShare]: { backgroundColor: '#8085f5' },
|
||||
[Operator.YahooFinance]: { backgroundColor: '#b474ff' },
|
||||
[Operator.Jin10]: { backgroundColor: '#a0b9f8' },
|
||||
[Operator.Concentrator]: {
|
||||
backgroundColor: '#32d2a3',
|
||||
color: '#32d2a3',
|
||||
width: 70,
|
||||
height: 70,
|
||||
fontSize: 10,
|
||||
iconFontSize: 16,
|
||||
},
|
||||
[Operator.TuShare]: { backgroundColor: '#f8cfa0' },
|
||||
[Operator.Note]: { backgroundColor: '#f8cfa0' },
|
||||
[Operator.Crawler]: {
|
||||
backgroundColor: '#dee0e2',
|
||||
},
|
||||
[Operator.Invoke]: {
|
||||
backgroundColor: '#dee0e2',
|
||||
},
|
||||
[Operator.Template]: {
|
||||
backgroundColor: '#dee0e2',
|
||||
},
|
||||
[Operator.Email]: { backgroundColor: '#e6f7ff' },
|
||||
[Operator.Iteration]: { backgroundColor: '#e6f7ff' },
|
||||
[Operator.IterationStart]: { backgroundColor: '#e6f7ff' },
|
||||
[Operator.Code]: { backgroundColor: '#4c5458' },
|
||||
[Operator.WaitingDialogue]: { backgroundColor: '#a5d65c' },
|
||||
[Operator.Agent]: { backgroundColor: '#a5d65c' },
|
||||
[Operator.TavilySearch]: { backgroundColor: '#a5d65c' },
|
||||
};
|
||||
|
||||
export const componentMenuList = [
|
||||
{
|
||||
name: Operator.Retrieval,
|
||||
@ -552,16 +411,14 @@ export const initialQWeatherValues = {
|
||||
};
|
||||
|
||||
export const initialExeSqlValues = {
|
||||
...initialLlmBaseValues,
|
||||
sql: '',
|
||||
db_type: 'mysql',
|
||||
database: '',
|
||||
username: '',
|
||||
host: '',
|
||||
port: 3306,
|
||||
password: '',
|
||||
loop: 3,
|
||||
top_n: 30,
|
||||
query: '',
|
||||
max_records: 1024,
|
||||
};
|
||||
|
||||
export const initialSwitchValues = {
|
||||
@ -775,8 +632,34 @@ export const initialTavilyValues = {
|
||||
type: 'string',
|
||||
},
|
||||
json: {
|
||||
value: {},
|
||||
type: 'Object',
|
||||
value: [],
|
||||
type: 'Array<Object>',
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
export enum TavilyExtractDepth {
|
||||
Basic = 'basic',
|
||||
Advanced = 'advanced',
|
||||
}
|
||||
|
||||
export enum TavilyExtractFormat {
|
||||
Text = 'text',
|
||||
Markdown = 'markdown',
|
||||
}
|
||||
|
||||
export const initialTavilyExtractValues = {
|
||||
urls: '',
|
||||
extract_depth: TavilyExtractDepth.Basic,
|
||||
format: TavilyExtractFormat.Markdown,
|
||||
outputs: {
|
||||
formalized_content: {
|
||||
value: '',
|
||||
type: 'string',
|
||||
},
|
||||
json: {
|
||||
value: [],
|
||||
type: 'Array<Object>',
|
||||
},
|
||||
},
|
||||
};
|
||||
@ -866,6 +749,7 @@ export const RestrictedUpstreamMap = {
|
||||
[Operator.WaitingDialogue]: [Operator.Begin],
|
||||
[Operator.Agent]: [Operator.Begin],
|
||||
[Operator.TavilySearch]: [Operator.Begin],
|
||||
[Operator.TavilyExtract]: [Operator.Begin],
|
||||
[Operator.StringTransform]: [Operator.Begin],
|
||||
[Operator.UserFillUp]: [Operator.Begin],
|
||||
};
|
||||
@ -914,6 +798,7 @@ export const NodeMap = {
|
||||
[Operator.TavilySearch]: 'ragNode',
|
||||
[Operator.UserFillUp]: 'ragNode',
|
||||
[Operator.StringTransform]: 'ragNode',
|
||||
[Operator.TavilyExtract]: 'ragNode',
|
||||
};
|
||||
|
||||
export enum BeginQueryType {
|
||||
|
||||
182
web/src/pages/agent/form-sheet/form-config-map.tsx
Normal file
182
web/src/pages/agent/form-sheet/form-config-map.tsx
Normal file
@ -0,0 +1,182 @@
|
||||
import { z } from 'zod';
|
||||
import { Operator } from '../constant';
|
||||
import AgentForm from '../form/agent-form';
|
||||
import AkShareForm from '../form/akshare-form';
|
||||
import AnswerForm from '../form/answer-form';
|
||||
import ArXivForm from '../form/arxiv-form';
|
||||
import BaiduFanyiForm from '../form/baidu-fanyi-form';
|
||||
import BaiduForm from '../form/baidu-form';
|
||||
import BeginForm from '../form/begin-form';
|
||||
import BingForm from '../form/bing-form';
|
||||
import CategorizeForm from '../form/categorize-form';
|
||||
import CodeForm from '../form/code-form';
|
||||
import CrawlerForm from '../form/crawler-form';
|
||||
import DeepLForm from '../form/deepl-form';
|
||||
import DuckDuckGoForm from '../form/duckduckgo-form';
|
||||
import EmailForm from '../form/email-form';
|
||||
import ExeSQLForm from '../form/exesql-form';
|
||||
import GenerateForm from '../form/generate-form';
|
||||
import GithubForm from '../form/github-form';
|
||||
import GoogleForm from '../form/google-form';
|
||||
import GoogleScholarForm from '../form/google-scholar-form';
|
||||
import InvokeForm from '../form/invoke-form';
|
||||
import IterationForm from '../form/iteration-form';
|
||||
import IterationStartForm from '../form/iteration-start-from';
|
||||
import Jin10Form from '../form/jin10-form';
|
||||
import KeywordExtractForm from '../form/keyword-extract-form';
|
||||
import MessageForm from '../form/message-form';
|
||||
import PubMedForm from '../form/pubmed-form';
|
||||
import QWeatherForm from '../form/qweather-form';
|
||||
import RelevantForm from '../form/relevant-form';
|
||||
import RetrievalForm from '../form/retrieval-form/next';
|
||||
import RewriteQuestionForm from '../form/rewrite-question-form';
|
||||
import { StringTransformForm } from '../form/string-transform-form';
|
||||
import SwitchForm from '../form/switch-form';
|
||||
import TavilyExtractForm from '../form/tavily-extract-form';
|
||||
import TavilyForm from '../form/tavily-form';
|
||||
import TemplateForm from '../form/template-form';
|
||||
import ToolForm from '../form/tool-form';
|
||||
import TuShareForm from '../form/tushare-form';
|
||||
import UserFillUpForm from '../form/user-fill-up-form';
|
||||
import WenCaiForm from '../form/wencai-form';
|
||||
import WikipediaForm from '../form/wikipedia-form';
|
||||
import YahooFinanceForm from '../form/yahoo-finance-form';
|
||||
|
||||
export const FormConfigMap = {
|
||||
[Operator.Begin]: {
|
||||
component: BeginForm,
|
||||
},
|
||||
[Operator.Retrieval]: {
|
||||
component: RetrievalForm,
|
||||
},
|
||||
[Operator.Generate]: {
|
||||
component: GenerateForm,
|
||||
},
|
||||
[Operator.Answer]: {
|
||||
component: AnswerForm,
|
||||
},
|
||||
[Operator.Categorize]: {
|
||||
component: CategorizeForm,
|
||||
},
|
||||
[Operator.Message]: {
|
||||
component: MessageForm,
|
||||
},
|
||||
[Operator.Relevant]: {
|
||||
component: RelevantForm,
|
||||
},
|
||||
[Operator.RewriteQuestion]: {
|
||||
component: RewriteQuestionForm,
|
||||
},
|
||||
[Operator.Code]: {
|
||||
component: CodeForm,
|
||||
},
|
||||
[Operator.WaitingDialogue]: {
|
||||
component: CodeForm,
|
||||
},
|
||||
[Operator.Agent]: {
|
||||
component: AgentForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Baidu]: {
|
||||
component: BaiduForm,
|
||||
},
|
||||
[Operator.DuckDuckGo]: {
|
||||
component: DuckDuckGoForm,
|
||||
},
|
||||
[Operator.KeywordExtract]: {
|
||||
component: KeywordExtractForm,
|
||||
},
|
||||
[Operator.Wikipedia]: {
|
||||
component: WikipediaForm,
|
||||
},
|
||||
[Operator.PubMed]: {
|
||||
component: PubMedForm,
|
||||
},
|
||||
[Operator.ArXiv]: {
|
||||
component: ArXivForm,
|
||||
},
|
||||
[Operator.Google]: {
|
||||
component: GoogleForm,
|
||||
},
|
||||
[Operator.Bing]: {
|
||||
component: BingForm,
|
||||
},
|
||||
[Operator.GoogleScholar]: {
|
||||
component: GoogleScholarForm,
|
||||
},
|
||||
[Operator.DeepL]: {
|
||||
component: DeepLForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.GitHub]: {
|
||||
component: GithubForm,
|
||||
},
|
||||
[Operator.BaiduFanyi]: {
|
||||
component: BaiduFanyiForm,
|
||||
},
|
||||
[Operator.QWeather]: {
|
||||
component: QWeatherForm,
|
||||
},
|
||||
[Operator.ExeSQL]: {
|
||||
component: ExeSQLForm,
|
||||
},
|
||||
[Operator.Switch]: {
|
||||
component: SwitchForm,
|
||||
},
|
||||
[Operator.WenCai]: {
|
||||
component: WenCaiForm,
|
||||
},
|
||||
[Operator.AkShare]: {
|
||||
component: AkShareForm,
|
||||
},
|
||||
[Operator.YahooFinance]: {
|
||||
component: YahooFinanceForm,
|
||||
},
|
||||
[Operator.Jin10]: {
|
||||
component: Jin10Form,
|
||||
},
|
||||
[Operator.TuShare]: {
|
||||
component: TuShareForm,
|
||||
},
|
||||
[Operator.Crawler]: {
|
||||
component: CrawlerForm,
|
||||
},
|
||||
[Operator.Invoke]: {
|
||||
component: InvokeForm,
|
||||
},
|
||||
[Operator.Concentrator]: {
|
||||
component: () => <></>,
|
||||
},
|
||||
[Operator.Note]: {
|
||||
component: () => <></>,
|
||||
},
|
||||
[Operator.Template]: {
|
||||
component: TemplateForm,
|
||||
},
|
||||
[Operator.Email]: {
|
||||
component: EmailForm,
|
||||
},
|
||||
[Operator.Iteration]: {
|
||||
component: IterationForm,
|
||||
},
|
||||
[Operator.IterationStart]: {
|
||||
component: IterationStartForm,
|
||||
},
|
||||
[Operator.Tool]: {
|
||||
component: ToolForm,
|
||||
},
|
||||
[Operator.TavilySearch]: {
|
||||
component: TavilyForm,
|
||||
},
|
||||
[Operator.UserFillUp]: {
|
||||
component: UserFillUpForm,
|
||||
},
|
||||
[Operator.StringTransform]: {
|
||||
component: StringTransformForm,
|
||||
},
|
||||
[Operator.TavilyExtract]: {
|
||||
component: TavilyExtractForm,
|
||||
},
|
||||
};
|
||||
@ -19,8 +19,8 @@ import { useHandleNodeNameChange } from '../hooks/use-change-node-name';
|
||||
import OperatorIcon from '../operator-icon';
|
||||
import useGraphStore from '../store';
|
||||
import { needsSingleStepDebugging } from '../utils';
|
||||
import { FormConfigMap } from './form-config-map';
|
||||
import SingleDebugDrawer from './single-debug-drawer';
|
||||
import { useFormConfigMap } from './use-form-config-map';
|
||||
|
||||
interface IProps {
|
||||
node?: RAGFlowNodeType;
|
||||
@ -44,8 +44,6 @@ const FormSheet = ({
|
||||
const operatorName: Operator = node?.data.label as Operator;
|
||||
const clickedToolId = useGraphStore((state) => state.clickedToolId);
|
||||
|
||||
const FormConfigMap = useFormConfigMap();
|
||||
|
||||
const currentFormMap = FormConfigMap[operatorName];
|
||||
|
||||
const OperatorForm = currentFormMap?.component ?? EmptyContent;
|
||||
|
||||
@ -1,400 +0,0 @@
|
||||
import { LlmSettingSchema } from '@/components/llm-setting-items/next';
|
||||
import { CodeTemplateStrMap, ProgrammingLanguage } from '@/constants/agent';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { z } from 'zod';
|
||||
import { Operator } from '../constant';
|
||||
import AgentForm from '../form/agent-form';
|
||||
import AkShareForm from '../form/akshare-form';
|
||||
import AnswerForm from '../form/answer-form';
|
||||
import ArXivForm from '../form/arxiv-form';
|
||||
import BaiduFanyiForm from '../form/baidu-fanyi-form';
|
||||
import BaiduForm from '../form/baidu-form';
|
||||
import BeginForm from '../form/begin-form';
|
||||
import BingForm from '../form/bing-form';
|
||||
import CategorizeForm from '../form/categorize-form';
|
||||
import CodeForm from '../form/code-form';
|
||||
import CrawlerForm from '../form/crawler-form';
|
||||
import DeepLForm from '../form/deepl-form';
|
||||
import DuckDuckGoForm from '../form/duckduckgo-form';
|
||||
import EmailForm from '../form/email-form';
|
||||
import ExeSQLForm from '../form/exesql-form';
|
||||
import GenerateForm from '../form/generate-form';
|
||||
import GithubForm from '../form/github-form';
|
||||
import GoogleForm from '../form/google-form';
|
||||
import GoogleScholarForm from '../form/google-scholar-form';
|
||||
import InvokeForm from '../form/invoke-form';
|
||||
import IterationForm from '../form/iteration-form';
|
||||
import IterationStartForm from '../form/iteration-start-from';
|
||||
import Jin10Form from '../form/jin10-form';
|
||||
import KeywordExtractForm from '../form/keyword-extract-form';
|
||||
import MessageForm from '../form/message-form';
|
||||
import PubMedForm from '../form/pubmed-form';
|
||||
import QWeatherForm from '../form/qweather-form';
|
||||
import RelevantForm from '../form/relevant-form';
|
||||
import RetrievalForm from '../form/retrieval-form/next';
|
||||
import RewriteQuestionForm from '../form/rewrite-question-form';
|
||||
import { StringTransformForm } from '../form/string-transform-form';
|
||||
import SwitchForm from '../form/switch-form';
|
||||
import TavilyForm from '../form/tavily-form';
|
||||
import TemplateForm from '../form/template-form';
|
||||
import ToolForm from '../form/tool-form';
|
||||
import TuShareForm from '../form/tushare-form';
|
||||
import UserFillUpForm from '../form/user-fill-up-form';
|
||||
import WenCaiForm from '../form/wencai-form';
|
||||
import WikipediaForm from '../form/wikipedia-form';
|
||||
import YahooFinanceForm from '../form/yahoo-finance-form';
|
||||
|
||||
export function useFormConfigMap() {
|
||||
const { t } = useTranslation();
|
||||
|
||||
const FormConfigMap = {
|
||||
[Operator.Begin]: {
|
||||
component: BeginForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({
|
||||
enablePrologue: z.boolean().optional(),
|
||||
prologue: z
|
||||
.string()
|
||||
.min(1, {
|
||||
message: t('common.namePlaceholder'),
|
||||
})
|
||||
.trim()
|
||||
.optional(),
|
||||
mode: z.string(),
|
||||
query: z
|
||||
.array(
|
||||
z.object({
|
||||
key: z.string(),
|
||||
type: z.string(),
|
||||
value: z.string(),
|
||||
optional: z.boolean(),
|
||||
name: z.string(),
|
||||
options: z.array(z.union([z.number(), z.string(), z.boolean()])),
|
||||
}),
|
||||
)
|
||||
.optional(),
|
||||
}),
|
||||
},
|
||||
[Operator.Retrieval]: {
|
||||
component: RetrievalForm,
|
||||
defaultValues: { query: [] },
|
||||
schema: z.object({
|
||||
name: z
|
||||
.string()
|
||||
.min(1, {
|
||||
message: t('common.namePlaceholder'),
|
||||
})
|
||||
.trim(),
|
||||
age: z
|
||||
.string()
|
||||
.min(1, {
|
||||
message: t('common.namePlaceholder'),
|
||||
})
|
||||
.trim(),
|
||||
query: z.array(
|
||||
z.object({
|
||||
type: z.string(),
|
||||
}),
|
||||
),
|
||||
}),
|
||||
},
|
||||
[Operator.Generate]: {
|
||||
component: GenerateForm,
|
||||
defaultValues: {
|
||||
cite: true,
|
||||
prompt: t('flow.promptText'),
|
||||
},
|
||||
schema: z.object({
|
||||
prompt: z.string().min(1, {
|
||||
message: t('flow.promptMessage'),
|
||||
}),
|
||||
}),
|
||||
},
|
||||
[Operator.Answer]: {
|
||||
component: AnswerForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Categorize]: {
|
||||
component: CategorizeForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({
|
||||
parameter: z.string().optional(),
|
||||
...LlmSettingSchema,
|
||||
message_history_window_size: z.coerce.number(),
|
||||
items: z.array(
|
||||
z
|
||||
.object({
|
||||
name: z.string().min(1, t('flow.nameMessage')).trim(),
|
||||
description: z.string().optional(),
|
||||
// examples: z
|
||||
// .array(
|
||||
// z.object({
|
||||
// value: z.string(),
|
||||
// }),
|
||||
// )
|
||||
// .optional(),
|
||||
})
|
||||
.optional(),
|
||||
),
|
||||
}),
|
||||
},
|
||||
[Operator.Message]: {
|
||||
component: MessageForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({
|
||||
content: z
|
||||
.array(
|
||||
z.object({
|
||||
value: z.string(),
|
||||
}),
|
||||
)
|
||||
.optional(),
|
||||
}),
|
||||
},
|
||||
[Operator.Relevant]: {
|
||||
component: RelevantForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.RewriteQuestion]: {
|
||||
component: RewriteQuestionForm,
|
||||
defaultValues: {
|
||||
message_history_window_size: 6,
|
||||
},
|
||||
schema: z.object({
|
||||
llm_id: z.string(),
|
||||
message_history_window_size: z.number(),
|
||||
language: z.string(),
|
||||
}),
|
||||
},
|
||||
[Operator.Code]: {
|
||||
component: CodeForm,
|
||||
defaultValues: {
|
||||
lang: ProgrammingLanguage.Python,
|
||||
script: CodeTemplateStrMap[ProgrammingLanguage.Python],
|
||||
arguments: [],
|
||||
},
|
||||
schema: z.object({
|
||||
lang: z.string(),
|
||||
script: z.string(),
|
||||
arguments: z.array(
|
||||
z.object({ name: z.string(), component_id: z.string() }),
|
||||
),
|
||||
return: z.union([
|
||||
z
|
||||
.array(z.object({ name: z.string(), component_id: z.string() }))
|
||||
.optional(),
|
||||
z.object({ name: z.string(), component_id: z.string() }),
|
||||
]),
|
||||
}),
|
||||
},
|
||||
[Operator.WaitingDialogue]: {
|
||||
component: CodeForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({
|
||||
arguments: z.array(
|
||||
z.object({ name: z.string(), component_id: z.string() }),
|
||||
),
|
||||
}),
|
||||
},
|
||||
[Operator.Agent]: {
|
||||
component: AgentForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Baidu]: {
|
||||
component: BaiduForm,
|
||||
defaultValues: { top_n: 10 },
|
||||
schema: z.object({ top_n: z.number() }),
|
||||
},
|
||||
[Operator.DuckDuckGo]: {
|
||||
component: DuckDuckGoForm,
|
||||
defaultValues: {
|
||||
top_n: 10,
|
||||
channel: 'text',
|
||||
},
|
||||
schema: z.object({
|
||||
top_n: z.number(),
|
||||
}),
|
||||
},
|
||||
[Operator.KeywordExtract]: {
|
||||
component: KeywordExtractForm,
|
||||
defaultValues: { top_n: 3 },
|
||||
schema: z.object({
|
||||
llm_id: z.string(),
|
||||
top_n: z.number(),
|
||||
}),
|
||||
},
|
||||
[Operator.Wikipedia]: {
|
||||
component: WikipediaForm,
|
||||
defaultValues: {
|
||||
top_n: 10,
|
||||
},
|
||||
schema: z.object({
|
||||
language: z.string(),
|
||||
top_n: z.number(),
|
||||
}),
|
||||
},
|
||||
[Operator.PubMed]: {
|
||||
component: PubMedForm,
|
||||
defaultValues: { top_n: 10 },
|
||||
schema: z.object({
|
||||
top_n: z.number(),
|
||||
email: z.string(),
|
||||
}),
|
||||
},
|
||||
[Operator.ArXiv]: {
|
||||
component: ArXivForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Google]: {
|
||||
component: GoogleForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Bing]: {
|
||||
component: BingForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.GoogleScholar]: {
|
||||
component: GoogleScholarForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.DeepL]: {
|
||||
component: DeepLForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.GitHub]: {
|
||||
component: GithubForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.BaiduFanyi]: {
|
||||
component: BaiduFanyiForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.QWeather]: {
|
||||
component: QWeatherForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({
|
||||
web_apikey: z.string(),
|
||||
lang: z.string(),
|
||||
type: z.string(),
|
||||
user_type: z.string(),
|
||||
time_period: z.string().optional(),
|
||||
}),
|
||||
},
|
||||
[Operator.ExeSQL]: {
|
||||
component: ExeSQLForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Switch]: {
|
||||
component: SwitchForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.WenCai]: {
|
||||
component: WenCaiForm,
|
||||
defaultValues: {
|
||||
top_n: 20,
|
||||
},
|
||||
schema: z.object({
|
||||
top_n: z.number(),
|
||||
query_type: z.string(),
|
||||
}),
|
||||
},
|
||||
[Operator.AkShare]: {
|
||||
component: AkShareForm,
|
||||
defaultValues: {
|
||||
top_n: 10,
|
||||
},
|
||||
schema: z.object({
|
||||
top_n: z.number(),
|
||||
}),
|
||||
},
|
||||
[Operator.YahooFinance]: {
|
||||
component: YahooFinanceForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Jin10]: {
|
||||
component: Jin10Form,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.TuShare]: {
|
||||
component: TuShareForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Crawler]: {
|
||||
component: CrawlerForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Invoke]: {
|
||||
component: InvokeForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Concentrator]: {
|
||||
component: () => <></>,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Note]: {
|
||||
component: () => <></>,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Template]: {
|
||||
component: TemplateForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Email]: {
|
||||
component: EmailForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Iteration]: {
|
||||
component: IterationForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.IterationStart]: {
|
||||
component: IterationStartForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.Tool]: {
|
||||
component: ToolForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.TavilySearch]: {
|
||||
component: TavilyForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.UserFillUp]: {
|
||||
component: UserFillUpForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
[Operator.StringTransform]: {
|
||||
component: StringTransformForm,
|
||||
defaultValues: {},
|
||||
schema: z.object({}),
|
||||
},
|
||||
};
|
||||
|
||||
return FormConfigMap;
|
||||
}
|
||||
@ -1,42 +0,0 @@
|
||||
import { RAGFlowNodeType } from '@/interfaces/database/flow';
|
||||
import { get, isEmpty, isPlainObject, omit } from 'lodash';
|
||||
import { useMemo, useRef } from 'react';
|
||||
import { Operator } from '../constant';
|
||||
import { buildCategorizeListFromObject, convertToObjectArray } from '../utils';
|
||||
import { useFormConfigMap } from './use-form-config-map';
|
||||
|
||||
export function useValues(node?: RAGFlowNodeType, isDirty?: boolean) {
|
||||
const operatorName: Operator = node?.data.label as Operator;
|
||||
const previousId = useRef<string | undefined>(node?.id);
|
||||
|
||||
const FormConfigMap = useFormConfigMap();
|
||||
|
||||
const currentFormMap = FormConfigMap[operatorName];
|
||||
|
||||
const values = useMemo(() => {
|
||||
const formData = node?.data?.form;
|
||||
if (operatorName === Operator.Categorize) {
|
||||
const items = buildCategorizeListFromObject(
|
||||
get(node, 'data.form.category_description', {}),
|
||||
);
|
||||
if (isPlainObject(formData)) {
|
||||
console.info('xxx');
|
||||
const nextValues = {
|
||||
...omit(formData, 'category_description'),
|
||||
items,
|
||||
};
|
||||
|
||||
return nextValues;
|
||||
}
|
||||
} else if (operatorName === Operator.Message) {
|
||||
return {
|
||||
...formData,
|
||||
content: convertToObjectArray(formData.content),
|
||||
};
|
||||
} else {
|
||||
return isEmpty(formData) ? currentFormMap : formData;
|
||||
}
|
||||
}, [currentFormMap, node, operatorName]);
|
||||
|
||||
return values;
|
||||
}
|
||||
@ -18,6 +18,7 @@ const Menus = [
|
||||
label: 'Search',
|
||||
list: [
|
||||
Operator.TavilySearch,
|
||||
Operator.TavilyExtract,
|
||||
Operator.Google,
|
||||
Operator.Bing,
|
||||
Operator.DuckDuckGo,
|
||||
@ -41,7 +42,6 @@ const Menus = [
|
||||
Operator.GitHub,
|
||||
Operator.ExeSQL,
|
||||
Operator.Invoke,
|
||||
Operator.Crawler,
|
||||
Operator.Code,
|
||||
Operator.Retrieval,
|
||||
],
|
||||
|
||||
@ -1,6 +1,5 @@
|
||||
import { LargeModelFormField } from '@/components/large-model-form-field';
|
||||
import NumberInput from '@/components/originui/number-input';
|
||||
import { SelectWithSearch } from '@/components/originui/select-with-search';
|
||||
import { TopNFormField } from '@/components/top-n-item';
|
||||
import { ButtonLoading } from '@/components/ui/button';
|
||||
import {
|
||||
Form,
|
||||
@ -10,7 +9,7 @@ import {
|
||||
FormLabel,
|
||||
FormMessage,
|
||||
} from '@/components/ui/form';
|
||||
import { Input, NumberInput } from '@/components/ui/input';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { useTranslate } from '@/hooks/common-hooks';
|
||||
import { zodResolver } from '@hookform/resolvers/zod';
|
||||
import { memo } from 'react';
|
||||
@ -31,7 +30,6 @@ export function ExeSQLFormWidgets({ loading }: { loading: boolean }) {
|
||||
|
||||
return (
|
||||
<>
|
||||
<LargeModelFormField></LargeModelFormField>
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="db_type"
|
||||
@ -94,7 +92,7 @@ export function ExeSQLFormWidgets({ loading }: { loading: boolean }) {
|
||||
<FormItem>
|
||||
<FormLabel>{t('port')}</FormLabel>
|
||||
<FormControl>
|
||||
<NumberInput {...field}></NumberInput>
|
||||
<NumberInput {...field} className="w-full"></NumberInput>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
@ -113,20 +111,21 @@ export function ExeSQLFormWidgets({ loading }: { loading: boolean }) {
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="loop"
|
||||
name="max_records"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel tooltip={t('loopTip')}>{t('loop')}</FormLabel>
|
||||
<FormLabel>{t('maxRecords')}</FormLabel>
|
||||
<FormControl>
|
||||
<NumberInput {...field}></NumberInput>
|
||||
<NumberInput {...field} className="w-full"></NumberInput>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
<TopNFormField max={1000}></TopNFormField>
|
||||
|
||||
<div className="flex justify-end">
|
||||
<ButtonLoading loading={loading} type="submit">
|
||||
Test
|
||||
@ -151,7 +150,7 @@ function ExeSQLForm({ node }: INextOperatorForm) {
|
||||
return (
|
||||
<Form {...form}>
|
||||
<FormWrapper onSubmit={form.handleSubmit(onSubmit)}>
|
||||
<QueryVariable></QueryVariable>
|
||||
<QueryVariable name="sql"></QueryVariable>
|
||||
<ExeSQLFormWidgets loading={loading}></ExeSQLFormWidgets>
|
||||
</FormWrapper>
|
||||
</Form>
|
||||
|
||||
@ -3,15 +3,14 @@ import { useCallback } from 'react';
|
||||
import { z } from 'zod';
|
||||
|
||||
export const ExeSQLFormSchema = {
|
||||
llm_id: z.string().min(1),
|
||||
sql: z.string(),
|
||||
db_type: z.string().min(1),
|
||||
database: z.string().min(1),
|
||||
username: z.string().min(1),
|
||||
host: z.string().min(1),
|
||||
port: z.number(),
|
||||
password: z.string().min(1),
|
||||
loop: z.number(),
|
||||
top_n: z.number(),
|
||||
max_records: z.number(),
|
||||
};
|
||||
|
||||
export const FormSchema = z.object({
|
||||
|
||||
115
web/src/pages/agent/form/tavily-extract-form/index.tsx
Normal file
115
web/src/pages/agent/form/tavily-extract-form/index.tsx
Normal file
@ -0,0 +1,115 @@
|
||||
import { FormContainer } from '@/components/form-container';
|
||||
import {
|
||||
Form,
|
||||
FormControl,
|
||||
FormField,
|
||||
FormItem,
|
||||
FormLabel,
|
||||
FormMessage,
|
||||
} from '@/components/ui/form';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { RAGFlowSelect } from '@/components/ui/select';
|
||||
import { buildOptions } from '@/utils/form';
|
||||
import { zodResolver } from '@hookform/resolvers/zod';
|
||||
import { memo } from 'react';
|
||||
import { useForm } from 'react-hook-form';
|
||||
import { z } from 'zod';
|
||||
import {
|
||||
TavilyExtractDepth,
|
||||
TavilyExtractFormat,
|
||||
initialTavilyExtractValues,
|
||||
} from '../../constant';
|
||||
import { useFormValues } from '../../hooks/use-form-values';
|
||||
import { useWatchFormChange } from '../../hooks/use-watch-form-change';
|
||||
import { INextOperatorForm } from '../../interface';
|
||||
import { buildOutputList } from '../../utils/build-output-list';
|
||||
import { FormWrapper } from '../components/form-wrapper';
|
||||
import { Output } from '../components/output';
|
||||
import { TavilyApiKeyField, TavilyFormSchema } from '../tavily-form';
|
||||
|
||||
const outputList = buildOutputList(initialTavilyExtractValues.outputs);
|
||||
|
||||
function TavilyExtractForm({ node }: INextOperatorForm) {
|
||||
const values = useFormValues(initialTavilyExtractValues, node);
|
||||
|
||||
const FormSchema = z.object({
|
||||
...TavilyFormSchema,
|
||||
urls: z.string(),
|
||||
extract_depth: z.enum([
|
||||
TavilyExtractDepth.Advanced,
|
||||
TavilyExtractDepth.Basic,
|
||||
]),
|
||||
format: z.enum([TavilyExtractFormat.Text, TavilyExtractFormat.Markdown]),
|
||||
});
|
||||
|
||||
const form = useForm<z.infer<typeof FormSchema>>({
|
||||
defaultValues: values,
|
||||
resolver: zodResolver(FormSchema),
|
||||
});
|
||||
|
||||
useWatchFormChange(node?.id, form);
|
||||
|
||||
return (
|
||||
<Form {...form}>
|
||||
<FormWrapper>
|
||||
<FormContainer>
|
||||
<TavilyApiKeyField></TavilyApiKeyField>
|
||||
</FormContainer>
|
||||
<FormContainer>
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="urls"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel>URL</FormLabel>
|
||||
<FormControl>
|
||||
<Input {...field} />
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="extract_depth"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel>Extract Depth</FormLabel>
|
||||
<FormControl>
|
||||
<RAGFlowSelect
|
||||
placeholder="shadcn"
|
||||
{...field}
|
||||
options={buildOptions(TavilyExtractDepth)}
|
||||
/>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="format"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel>Format</FormLabel>
|
||||
<FormControl>
|
||||
<RAGFlowSelect
|
||||
placeholder="shadcn"
|
||||
{...field}
|
||||
options={buildOptions(TavilyExtractFormat)}
|
||||
/>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
</FormContainer>
|
||||
</FormWrapper>
|
||||
<div className="p-5">
|
||||
<Output list={outputList}></Output>
|
||||
</div>
|
||||
</Form>
|
||||
);
|
||||
}
|
||||
|
||||
export default memo(TavilyExtractForm);
|
||||
@ -13,7 +13,7 @@ import { Switch } from '@/components/ui/switch';
|
||||
import { buildOptions } from '@/utils/form';
|
||||
import { zodResolver } from '@hookform/resolvers/zod';
|
||||
import { memo, useMemo } from 'react';
|
||||
import { useForm } from 'react-hook-form';
|
||||
import { useForm, useFormContext } from 'react-hook-form';
|
||||
import { z } from 'zod';
|
||||
import {
|
||||
TavilySearchDepth,
|
||||
@ -21,17 +21,41 @@ import {
|
||||
initialTavilyValues,
|
||||
} from '../../constant';
|
||||
import { INextOperatorForm } from '../../interface';
|
||||
import { FormWrapper } from '../components/form-wrapper';
|
||||
import { Output, OutputType } from '../components/output';
|
||||
import { QueryVariable } from '../components/query-variable';
|
||||
import { DynamicDomain } from './dynamic-domain';
|
||||
import { useValues } from './use-values';
|
||||
import { useWatchFormChange } from './use-watch-change';
|
||||
|
||||
export function TavilyApiKeyField() {
|
||||
const form = useFormContext();
|
||||
return (
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="api_key"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel>Api Key</FormLabel>
|
||||
<FormControl>
|
||||
<Input type="password" {...field}></Input>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
export const TavilyFormSchema = {
|
||||
api_key: z.string(),
|
||||
};
|
||||
|
||||
function TavilyForm({ node }: INextOperatorForm) {
|
||||
const values = useValues(node);
|
||||
|
||||
const FormSchema = z.object({
|
||||
api_key: z.string(),
|
||||
...TavilyFormSchema,
|
||||
query: z.string(),
|
||||
search_depth: z.enum([TavilySearchDepth.Advanced, TavilySearchDepth.Basic]),
|
||||
topic: z.enum([TavilyTopic.News, TavilyTopic.General]),
|
||||
@ -64,27 +88,9 @@ function TavilyForm({ node }: INextOperatorForm) {
|
||||
|
||||
return (
|
||||
<Form {...form}>
|
||||
<form
|
||||
className="space-y-5 px-5 "
|
||||
autoComplete="off"
|
||||
onSubmit={(e) => {
|
||||
e.preventDefault();
|
||||
}}
|
||||
>
|
||||
<FormWrapper>
|
||||
<FormContainer>
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="api_key"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel>Api Key</FormLabel>
|
||||
<FormControl>
|
||||
<Input type="password" {...field}></Input>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
<TavilyApiKeyField></TavilyApiKeyField>
|
||||
</FormContainer>
|
||||
<FormContainer>
|
||||
<QueryVariable></QueryVariable>
|
||||
@ -221,7 +227,7 @@ function TavilyForm({ node }: INextOperatorForm) {
|
||||
label={'Exclude Domains'}
|
||||
></DynamicDomain>
|
||||
</FormContainer>
|
||||
</form>
|
||||
</FormWrapper>
|
||||
<div className="p-5">
|
||||
<Output list={outputList}></Output>
|
||||
</div>
|
||||
|
||||
@ -9,7 +9,7 @@ export function useWatchFormChange(id?: string, form?: UseFormReturn<any>) {
|
||||
|
||||
useEffect(() => {
|
||||
// Manually triggered form updates are synchronized to the canvas
|
||||
if (id && form?.formState.isDirty) {
|
||||
if (id) {
|
||||
values = form?.getValues();
|
||||
let nextValues: any = {
|
||||
...values,
|
||||
|
||||
@ -34,4 +34,5 @@ export const ToolFormConfigMap = {
|
||||
[Operator.Crawler]: CrawlerForm,
|
||||
[Operator.Email]: EmailForm,
|
||||
[Operator.TavilySearch]: TavilyForm,
|
||||
[Operator.TavilyExtract]: TavilyForm,
|
||||
};
|
||||
|
||||
@ -1,25 +1,17 @@
|
||||
import { FormContainer } from '@/components/form-container';
|
||||
import {
|
||||
Form,
|
||||
FormControl,
|
||||
FormField,
|
||||
FormItem,
|
||||
FormLabel,
|
||||
FormMessage,
|
||||
} from '@/components/ui/form';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { Form } from '@/components/ui/form';
|
||||
import { zodResolver } from '@hookform/resolvers/zod';
|
||||
import { useForm } from 'react-hook-form';
|
||||
import { z } from 'zod';
|
||||
import { FormWrapper } from '../../components/form-wrapper';
|
||||
import { TavilyApiKeyField, TavilyFormSchema } from '../../tavily-form';
|
||||
import { useValues } from '../use-values';
|
||||
import { useWatchFormChange } from '../use-watch-change';
|
||||
|
||||
const TavilyForm = () => {
|
||||
const values = useValues();
|
||||
|
||||
const FormSchema = z.object({
|
||||
api_key: z.string(),
|
||||
});
|
||||
const FormSchema = z.object(TavilyFormSchema);
|
||||
|
||||
const form = useForm<z.infer<typeof FormSchema>>({
|
||||
defaultValues: values,
|
||||
@ -30,29 +22,11 @@ const TavilyForm = () => {
|
||||
|
||||
return (
|
||||
<Form {...form}>
|
||||
<form
|
||||
className="space-y-5 px-5 "
|
||||
autoComplete="off"
|
||||
onSubmit={(e) => {
|
||||
e.preventDefault();
|
||||
}}
|
||||
>
|
||||
<FormWrapper>
|
||||
<FormContainer>
|
||||
<FormField
|
||||
control={form.control}
|
||||
name="api_key"
|
||||
render={({ field }) => (
|
||||
<FormItem>
|
||||
<FormLabel>Api Key</FormLabel>
|
||||
<FormControl>
|
||||
<Input type="password" {...field}></Input>
|
||||
</FormControl>
|
||||
<FormMessage />
|
||||
</FormItem>
|
||||
)}
|
||||
/>
|
||||
<TavilyApiKeyField></TavilyApiKeyField>
|
||||
</FormContainer>
|
||||
</form>
|
||||
</FormWrapper>
|
||||
</Form>
|
||||
);
|
||||
};
|
||||
|
||||
@ -41,6 +41,7 @@ import {
|
||||
initialRewriteQuestionValues,
|
||||
initialStringTransformValues,
|
||||
initialSwitchValues,
|
||||
initialTavilyExtractValues,
|
||||
initialTavilyValues,
|
||||
initialTemplateValues,
|
||||
initialTuShareValues,
|
||||
@ -94,7 +95,7 @@ export const useInitializeOperatorParams = () => {
|
||||
[Operator.GitHub]: initialGithubValues,
|
||||
[Operator.BaiduFanyi]: initialBaiduFanyiValues,
|
||||
[Operator.QWeather]: initialQWeatherValues,
|
||||
[Operator.ExeSQL]: { ...initialExeSqlValues, llm_id: llmId },
|
||||
[Operator.ExeSQL]: initialExeSqlValues,
|
||||
[Operator.Switch]: initialSwitchValues,
|
||||
[Operator.WenCai]: initialWenCaiValues,
|
||||
[Operator.AkShare]: initialAkShareValues,
|
||||
@ -116,6 +117,7 @@ export const useInitializeOperatorParams = () => {
|
||||
[Operator.TavilySearch]: initialTavilyValues,
|
||||
[Operator.UserFillUp]: initialUserFillUpValues,
|
||||
[Operator.StringTransform]: initialStringTransformValues,
|
||||
[Operator.TavilyExtract]: initialTavilyExtractValues,
|
||||
};
|
||||
}, [llmId]);
|
||||
|
||||
|
||||
@ -16,12 +16,12 @@ export function useAgentToolInitialValues() {
|
||||
...omit(initialValues, 'query'),
|
||||
description: '',
|
||||
};
|
||||
case Operator.TavilySearch:
|
||||
case (Operator.TavilySearch, Operator.TavilyExtract):
|
||||
return {
|
||||
api_key: '',
|
||||
};
|
||||
case Operator.ExeSQL:
|
||||
return omit(initialValues, 'query');
|
||||
return omit(initialValues, 'sql');
|
||||
case Operator.Bing:
|
||||
return omit(initialValues, 'query');
|
||||
|
||||
|
||||
Reference in New Issue
Block a user