all-tools.tsx 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081
  1. import {
  2. useMemo,
  3. useState,
  4. } from 'react'
  5. import type {
  6. OnSelectBlock,
  7. ToolWithProvider,
  8. } from '../types'
  9. import { useStore } from '../store'
  10. import { ToolTypeEnum } from './types'
  11. import Tools from './tools'
  12. import { useToolTabs } from './hooks'
  13. import cn from '@/utils/classnames'
  14. type AllToolsProps = {
  15. searchText: string
  16. onSelect: OnSelectBlock
  17. }
  18. const AllTools = ({
  19. searchText,
  20. onSelect,
  21. }: AllToolsProps) => {
  22. const tabs = useToolTabs()
  23. const [activeTab, setActiveTab] = useState(ToolTypeEnum.All)
  24. const buildInTools = useStore(s => s.buildInTools)
  25. const customTools = useStore(s => s.customTools)
  26. const workflowTools = useStore(s => s.workflowTools)
  27. const isMatchingKeywords = (text: string, keywords: string) => {
  28. return text.toLowerCase().includes(keywords.toLowerCase())
  29. }
  30. const tools = useMemo(() => {
  31. let mergedTools: ToolWithProvider[] = []
  32. if (activeTab === ToolTypeEnum.All)
  33. mergedTools = [...buildInTools, ...customTools, ...workflowTools]
  34. if (activeTab === ToolTypeEnum.BuiltIn)
  35. mergedTools = buildInTools
  36. if (activeTab === ToolTypeEnum.Custom)
  37. mergedTools = customTools
  38. if (activeTab === ToolTypeEnum.Workflow)
  39. mergedTools = workflowTools
  40. return mergedTools.filter((toolWithProvider) => {
  41. return isMatchingKeywords(toolWithProvider.name, searchText)
  42. || toolWithProvider.tools.some((tool) => {
  43. return Object.values(tool.label).some((label) => {
  44. return isMatchingKeywords(label, searchText)
  45. })
  46. })
  47. })
  48. }, [activeTab, buildInTools, customTools, workflowTools, searchText])
  49. return (
  50. <div>
  51. <div className='flex items-center px-3 h-8 space-x-1 bg-gray-25 border-b-[0.5px] border-black/[0.08] shadow-xs'>
  52. {
  53. tabs.map(tab => (
  54. <div
  55. className={cn(
  56. 'flex items-center px-2 h-6 rounded-md hover:bg-gray-100 cursor-pointer',
  57. 'text-xs font-medium text-gray-700',
  58. activeTab === tab.key && 'bg-gray-200',
  59. )}
  60. key={tab.key}
  61. onClick={() => setActiveTab(tab.key)}
  62. >
  63. {tab.name}
  64. </div>
  65. ))
  66. }
  67. </div>
  68. <Tools
  69. showWorkflowEmpty={activeTab === ToolTypeEnum.Workflow}
  70. tools={tools}
  71. onSelect={onSelect}
  72. />
  73. </div>
  74. )
  75. }
  76. export default AllTools