dify/web/app/components/plugins/marketplace/context.tsx

200 lines
6.7 KiB
TypeScript
Raw Normal View History

2024-10-12 18:02:24 +08:00
'use client'
2024-10-30 15:27:38 +08:00
import type {
ReactNode,
} from 'react'
2024-10-12 18:02:24 +08:00
import {
2024-10-29 10:51:41 +08:00
useCallback,
2024-10-30 15:27:38 +08:00
useRef,
2024-10-12 18:02:24 +08:00
useState,
} from 'react'
import {
createContext,
useContextSelector,
} from 'use-context-selector'
2024-10-29 10:51:41 +08:00
import { useDebounceFn } from 'ahooks'
import { PLUGIN_TYPE_SEARCH_MAP } from './plugin-type-switch'
import type { Plugin } from '../types'
2024-10-29 18:13:47 +08:00
import type {
2024-10-30 15:15:53 +08:00
CollectionsAndPluginsSearchParams,
MarketplaceCollection,
2024-10-29 18:13:47 +08:00
PluginsSearchParams,
PluginsSort,
} from './types'
2024-10-30 15:15:53 +08:00
import {
getMarketplaceCollectionsAndPlugins,
getMarketplacePlugins,
} from './utils'
2024-10-29 18:13:47 +08:00
import { DEFAULT_SORT } from './constants'
2024-10-12 18:02:24 +08:00
export type MarketplaceContextValue = {
intersected: boolean
setIntersected: (intersected: boolean) => void
2024-10-29 10:51:41 +08:00
searchPluginText: string
handleSearchPluginTextChange: (text: string) => void
filterPluginTags: string[]
handleFilterPluginTagsChange: (tags: string[]) => void
activePluginType: string
handleActivePluginTypeChange: (type: string) => void
plugins?: Plugin[]
2024-10-30 15:15:53 +08:00
setPlugins: (plugins: Plugin[]) => void
2024-10-29 18:13:47 +08:00
sort: PluginsSort
handleSortChange: (sort: PluginsSort) => void
2024-10-30 15:15:53 +08:00
marketplaceCollectionsFromClient?: MarketplaceCollection[]
setMarketplaceCollectionsFromClient: (collections: MarketplaceCollection[]) => void
marketplaceCollectionPluginsMapFromClient?: Record<string, Plugin[]>
setMarketplaceCollectionPluginsMapFromClient: (map: Record<string, Plugin[]>) => void
2024-10-12 18:02:24 +08:00
}
export const MarketplaceContext = createContext<MarketplaceContextValue>({
intersected: true,
setIntersected: () => {},
2024-10-29 10:51:41 +08:00
searchPluginText: '',
handleSearchPluginTextChange: () => {},
filterPluginTags: [],
handleFilterPluginTagsChange: () => {},
activePluginType: PLUGIN_TYPE_SEARCH_MAP.all,
handleActivePluginTypeChange: () => {},
plugins: undefined,
setPlugins: () => {},
2024-10-29 18:13:47 +08:00
sort: DEFAULT_SORT,
handleSortChange: () => {},
2024-10-30 15:15:53 +08:00
marketplaceCollectionsFromClient: [],
setMarketplaceCollectionsFromClient: () => {},
marketplaceCollectionPluginsMapFromClient: {},
setMarketplaceCollectionPluginsMapFromClient: () => {},
2024-10-12 18:02:24 +08:00
})
type MarketplaceContextProviderProps = {
children: ReactNode
}
export function useMarketplaceContext(selector: (value: MarketplaceContextValue) => any) {
return useContextSelector(MarketplaceContext, selector)
}
export const MarketplaceContextProvider = ({
children,
}: MarketplaceContextProviderProps) => {
const [intersected, setIntersected] = useState(true)
2024-10-29 10:51:41 +08:00
const [searchPluginText, setSearchPluginText] = useState('')
2024-10-30 15:27:38 +08:00
const searchPluginTextRef = useRef(searchPluginText)
2024-10-29 10:51:41 +08:00
const [filterPluginTags, setFilterPluginTags] = useState<string[]>([])
2024-10-30 15:27:38 +08:00
const filterPluginTagsRef = useRef(filterPluginTags)
2024-10-29 10:51:41 +08:00
const [activePluginType, setActivePluginType] = useState(PLUGIN_TYPE_SEARCH_MAP.all)
2024-10-30 15:27:38 +08:00
const activePluginTypeRef = useRef(activePluginType)
2024-10-29 10:51:41 +08:00
const [plugins, setPlugins] = useState<Plugin[]>()
2024-10-29 18:13:47 +08:00
const [sort, setSort] = useState(DEFAULT_SORT)
2024-10-30 15:27:38 +08:00
const sortRef = useRef(sort)
2024-10-30 15:15:53 +08:00
const [marketplaceCollectionsFromClient, setMarketplaceCollectionsFromClient] = useState<MarketplaceCollection[] | undefined>(undefined)
const [marketplaceCollectionPluginsMapFromClient, setMarketplaceCollectionPluginsMapFromClient] = useState<Record<string, Plugin[]> | undefined>(undefined)
2024-10-29 10:51:41 +08:00
2024-10-29 14:44:30 +08:00
const handleUpdatePlugins = useCallback(async (query: PluginsSearchParams) => {
const { marketplacePlugins } = await getMarketplacePlugins(query)
2024-10-29 10:51:41 +08:00
2024-10-29 14:44:30 +08:00
setPlugins(marketplacePlugins)
2024-10-30 15:15:53 +08:00
setMarketplaceCollectionsFromClient(undefined)
setMarketplaceCollectionPluginsMapFromClient(undefined)
}, [])
const handleUpdateMarketplaceCollectionsAndPlugins = useCallback(async (query?: CollectionsAndPluginsSearchParams) => {
const {
marketplaceCollections,
marketplaceCollectionPluginsMap,
} = await getMarketplaceCollectionsAndPlugins(query)
setMarketplaceCollectionsFromClient(marketplaceCollections)
setMarketplaceCollectionPluginsMapFromClient(marketplaceCollectionPluginsMap)
setPlugins(undefined)
2024-10-29 10:51:41 +08:00
}, [])
const { run: handleUpdatePluginsWithDebounced } = useDebounceFn(handleUpdatePlugins, {
wait: 500,
})
const handleSearchPluginTextChange = useCallback((text: string) => {
setSearchPluginText(text)
2024-10-30 15:27:38 +08:00
searchPluginTextRef.current = text
2024-10-29 10:51:41 +08:00
2024-10-30 15:15:53 +08:00
handleUpdatePluginsWithDebounced({
query: text,
2024-10-30 15:27:38 +08:00
category: activePluginTypeRef.current === PLUGIN_TYPE_SEARCH_MAP.all ? undefined : activePluginTypeRef.current,
tags: filterPluginTagsRef.current,
sortBy: sortRef.current.sortBy,
sortOrder: sortRef.current.sortOrder,
2024-10-30 15:15:53 +08:00
})
2024-10-30 15:27:38 +08:00
}, [handleUpdatePluginsWithDebounced])
2024-10-29 10:51:41 +08:00
const handleFilterPluginTagsChange = useCallback((tags: string[]) => {
setFilterPluginTags(tags)
2024-10-30 15:27:38 +08:00
filterPluginTagsRef.current = tags
2024-10-30 15:15:53 +08:00
handleUpdatePlugins({
2024-10-30 15:27:38 +08:00
query: searchPluginTextRef.current,
category: activePluginTypeRef.current === PLUGIN_TYPE_SEARCH_MAP.all ? undefined : activePluginTypeRef.current,
2024-10-30 15:15:53 +08:00
tags,
2024-10-30 15:27:38 +08:00
sortBy: sortRef.current.sortBy,
sortOrder: sortRef.current.sortOrder,
2024-10-30 15:15:53 +08:00
})
2024-10-30 15:27:38 +08:00
}, [handleUpdatePlugins])
2024-10-29 10:51:41 +08:00
const handleActivePluginTypeChange = useCallback((type: string) => {
setActivePluginType(type)
2024-10-30 15:27:38 +08:00
activePluginTypeRef.current = type
2024-10-30 15:15:53 +08:00
2024-10-30 15:27:38 +08:00
if (!searchPluginTextRef.current && !filterPluginTagsRef.current.length) {
2024-10-30 15:15:53 +08:00
handleUpdateMarketplaceCollectionsAndPlugins({
category: type === PLUGIN_TYPE_SEARCH_MAP.all ? undefined : type,
})
return
}
handleUpdatePlugins({
2024-10-30 15:27:38 +08:00
query: searchPluginTextRef.current,
2024-10-30 15:15:53 +08:00
category: type === PLUGIN_TYPE_SEARCH_MAP.all ? undefined : type,
2024-10-30 15:27:38 +08:00
tags: filterPluginTagsRef.current,
sortBy: sortRef.current.sortBy,
sortOrder: sortRef.current.sortOrder,
2024-10-30 15:15:53 +08:00
})
2024-10-30 15:27:38 +08:00
}, [handleUpdatePlugins, handleUpdateMarketplaceCollectionsAndPlugins])
2024-10-12 18:02:24 +08:00
2024-10-29 18:13:47 +08:00
const handleSortChange = useCallback((sort: PluginsSort) => {
setSort(sort)
2024-10-30 15:27:38 +08:00
sortRef.current = sort
2024-10-30 15:15:53 +08:00
handleUpdatePlugins({
2024-10-30 15:27:38 +08:00
query: searchPluginTextRef.current,
category: activePluginTypeRef.current === PLUGIN_TYPE_SEARCH_MAP.all ? undefined : activePluginTypeRef.current,
tags: filterPluginTagsRef.current,
sortBy: sortRef.current.sortBy,
sortOrder: sortRef.current.sortOrder,
2024-10-30 15:15:53 +08:00
})
2024-10-30 15:27:38 +08:00
}, [handleUpdatePlugins])
2024-10-29 18:13:47 +08:00
2024-10-12 18:02:24 +08:00
return (
<MarketplaceContext.Provider
value={{
intersected,
setIntersected,
2024-10-29 10:51:41 +08:00
searchPluginText,
handleSearchPluginTextChange,
filterPluginTags,
handleFilterPluginTagsChange,
activePluginType,
handleActivePluginTypeChange,
plugins,
setPlugins,
2024-10-29 18:13:47 +08:00
sort,
handleSortChange,
2024-10-30 15:15:53 +08:00
marketplaceCollectionsFromClient,
setMarketplaceCollectionsFromClient,
marketplaceCollectionPluginsMapFromClient,
setMarketplaceCollectionPluginsMapFromClient,
2024-10-12 18:02:24 +08:00
}}
>
{children}
</MarketplaceContext.Provider>
)
}