diff --git a/components/agents/AgentWorkflowPanel.tsx b/components/agents/AgentWorkflowPanel.tsx
index 78f7bdc8b..c7cd26bd1 100644
--- a/components/agents/AgentWorkflowPanel.tsx
+++ b/components/agents/AgentWorkflowPanel.tsx
@@ -6,6 +6,7 @@ import { toast } from "sonner";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { ScrollArea } from "@/components/ui/scroll-area";
+import { SearchableSelect } from "@/components/ui/searchable-select";
import { Textarea } from "@/components/ui/textarea";
import { cn } from "@/lib/utils";
import { defaultAgentWorkflowUiConfig } from "@/lib/agents/workflow-ui-config";
@@ -185,32 +186,22 @@ export function AgentWorkflowPanel({
}
placeholder="搭配 SKU"
/>
-
- onInputsChange({ ...inputs, brand: event.target.value })
- }
+ options={brandOptions}
placeholder="品牌"
- list="agent-workflow-brand-options"
+ searchPlaceholder="输入品牌名筛选"
+ emptyText="暂无品牌可选,请先到系统设置配置"
+ onValueChange={(value) => onInputsChange({ ...inputs, brand: value })}
/>
-
-
- onInputsChange({ ...inputs, store: event.target.value })
- }
+ options={storeOptions}
placeholder="店铺"
- list="agent-workflow-store-options"
+ searchPlaceholder="输入店铺名筛选"
+ emptyText="暂无店铺可选,请先到系统设置配置"
+ onValueChange={(value) => onInputsChange({ ...inputs, store: value })}
/>
-
{(brandOptions.length > 0 || storeOptions.length > 0) && (
diff --git a/components/ui/searchable-select.tsx b/components/ui/searchable-select.tsx
new file mode 100644
index 000000000..d1557759f
--- /dev/null
+++ b/components/ui/searchable-select.tsx
@@ -0,0 +1,101 @@
+"use client";
+
+import { useEffect, useMemo, useState } from "react";
+import { Check, ChevronsUpDown } from "lucide-react";
+import { Button } from "@/components/ui/button";
+import { Input } from "@/components/ui/input";
+import { Popover, PopoverContent, PopoverTrigger } from "@/components/ui/popover";
+import { ScrollArea } from "@/components/ui/scroll-area";
+import { cn } from "@/lib/utils";
+
+interface SearchableSelectProps {
+ value: string;
+ options: string[];
+ placeholder: string;
+ searchPlaceholder?: string;
+ emptyText?: string;
+ onValueChange: (value: string) => void;
+}
+
+export function SearchableSelect({
+ value,
+ options,
+ placeholder,
+ searchPlaceholder = "输入关键字搜索",
+ emptyText = "暂无可选项",
+ onValueChange,
+}: SearchableSelectProps) {
+ const [open, setOpen] = useState(false);
+ const [query, setQuery] = useState("");
+
+ useEffect(() => {
+ if (!open) {
+ setQuery("");
+ }
+ }, [open]);
+
+ const filteredOptions = useMemo(() => {
+ const normalizedQuery = query.trim().toLowerCase();
+ if (!normalizedQuery) return options;
+ return options.filter((item) => item.toLowerCase().includes(normalizedQuery));
+ }, [options, query]);
+
+ return (
+
+
+
+
+
+
+
setQuery(event.target.value)}
+ placeholder={searchPlaceholder}
+ />
+
+
+ {filteredOptions.length > 0 ? (
+ filteredOptions.map((item) => {
+ const selected = item === value;
+ return (
+
+ );
+ })
+ ) : (
+
+ {emptyText}
+
+ )}
+
+
+
+
+
+ );
+}