mirror of https://github.com/kortix-ai/suna.git
Merge pull request #920 from escapade-mckv/cleanup-main
fix: frontend mcp type fix
This commit is contained in:
commit
6f9c8147ad
|
@ -289,7 +289,10 @@ export const CreateAgentDialog = ({ isOpen, onOpenChange, onAgentCreated }: Crea
|
|||
|
||||
<TabsContent value="mcp" className="flex-1 m-0 p-6 overflow-y-auto">
|
||||
<MCPConfigurationNew
|
||||
configuredMCPs={formData.configured_mcps}
|
||||
configuredMCPs={formData.configured_mcps.map(mcp => ({
|
||||
...mcp,
|
||||
enabledTools: mcp.enabledTools || []
|
||||
}))}
|
||||
onConfigurationChange={handleMCPConfigurationChange}
|
||||
/>
|
||||
</TabsContent>
|
||||
|
|
|
@ -393,14 +393,20 @@ export const UpdateAgentDialog = ({ agentId, isOpen, onOpenChange, onAgentUpdate
|
|||
|
||||
<TabsContent value="mcp" className="flex-1 m-0 p-6 overflow-y-auto">
|
||||
<MCPConfigurationNew
|
||||
configuredMCPs={[...(formData.configured_mcps || []), ...(formData.custom_mcps || []).map(customMcp => ({
|
||||
name: customMcp.name,
|
||||
qualifiedName: `custom_${customMcp.type}_${customMcp.name.replace(' ', '_').toLowerCase()}`,
|
||||
config: customMcp.config,
|
||||
enabledTools: customMcp.enabledTools,
|
||||
isCustom: true,
|
||||
customType: customMcp.type
|
||||
}))]}
|
||||
configuredMCPs={[
|
||||
...(formData.configured_mcps || []).map(mcp => ({
|
||||
...mcp,
|
||||
enabledTools: mcp.enabledTools || []
|
||||
})),
|
||||
...(formData.custom_mcps || []).map(customMcp => ({
|
||||
name: customMcp.name,
|
||||
qualifiedName: `custom_${customMcp.type}_${customMcp.name.replace(' ', '_').toLowerCase()}`,
|
||||
config: customMcp.config,
|
||||
enabledTools: customMcp.enabledTools,
|
||||
isCustom: true,
|
||||
customType: customMcp.type
|
||||
}))
|
||||
]}
|
||||
onConfigurationChange={handleMCPConfigurationChange}
|
||||
/>
|
||||
</TabsContent>
|
||||
|
|
|
@ -86,15 +86,25 @@ export const PipedreamAppBrowser: React.FC<PipedreamAppBrowserProps> = ({
|
|||
|
||||
<div className="space-y-4">
|
||||
<div className="flex gap-2">
|
||||
<div className="relative flex-1">
|
||||
<form onSubmit={(e) => {e.preventDefault()}} className="relative flex-1">
|
||||
<Search className="absolute left-3 top-1/2 transform -translate-y-1/2 h-4 w-4 text-muted-foreground" />
|
||||
<Input
|
||||
placeholder="Search apps..."
|
||||
placeholder="Search apps... (e.g., Gmail, Slack, Notion)"
|
||||
value={searchQuery}
|
||||
onChange={(e) => setSearchQuery(e.target.value)}
|
||||
className="pl-10"
|
||||
/>
|
||||
</div>
|
||||
{searchQuery && (
|
||||
<Button
|
||||
type="submit"
|
||||
size="sm"
|
||||
variant="ghost"
|
||||
className="absolute right-1 top-1/2 transform -translate-y-1/2 h-8 px-2"
|
||||
>
|
||||
Search
|
||||
</Button>
|
||||
)}
|
||||
</form>
|
||||
{selectedCategory && (
|
||||
<Button
|
||||
variant="outline"
|
||||
|
|
|
@ -66,6 +66,11 @@ export const PipedreamRegistry: React.FC<PipedreamRegistryProps> = ({
|
|||
setPage(1);
|
||||
};
|
||||
|
||||
const handleSearchSubmit = (e: React.FormEvent) => {
|
||||
e.preventDefault();
|
||||
refetch();
|
||||
};
|
||||
|
||||
const handleCategorySelect = (category: string) => {
|
||||
setSelectedCategory(category === selectedCategory ? '' : category);
|
||||
setPage(1);
|
||||
|
@ -281,15 +286,25 @@ export const PipedreamRegistry: React.FC<PipedreamRegistryProps> = ({
|
|||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="relative">
|
||||
<form onSubmit={handleSearchSubmit} className="relative">
|
||||
<Search className="absolute left-2.5 top-1/2 transform -translate-y-1/2 h-3 w-3 text-muted-foreground" />
|
||||
<Input
|
||||
placeholder="Search apps..."
|
||||
placeholder="Search apps... (e.g., Gmail, Slack, Notion)"
|
||||
value={search}
|
||||
onChange={(e) => handleSearch(e.target.value)}
|
||||
className="pl-8 h-8 text-sm"
|
||||
/>
|
||||
</div>
|
||||
{search && (
|
||||
<Button
|
||||
type="submit"
|
||||
size="sm"
|
||||
variant="ghost"
|
||||
className="absolute right-1 top-1/2 transform -translate-y-1/2 h-6 px-2"
|
||||
>
|
||||
Search
|
||||
</Button>
|
||||
)}
|
||||
</form>
|
||||
</div>
|
||||
<div className="flex-1 overflow-auto p-4">
|
||||
{isLoading && (
|
||||
|
|
|
@ -7,6 +7,7 @@ export const pipedreamKeys = {
|
|||
workflows: () => [...pipedreamKeys.all, 'workflows'] as const,
|
||||
workflowRuns: (workflowId: string) => [...pipedreamKeys.all, 'workflow-runs', workflowId] as const,
|
||||
apps: (page: number, search?: string, category?: string) => [...pipedreamKeys.all, 'apps', page, search || '', category || ''] as const,
|
||||
appsSearch: (query: string, page: number, category?: string) => [...pipedreamKeys.all, 'apps', 'search', query, page, category || ''] as const,
|
||||
availableTools: () => [...pipedreamKeys.all, 'available-tools'] as const,
|
||||
mcpDiscovery: (options?: { app_slug?: string; oauth_app_id?: string; custom?: boolean }) =>
|
||||
[...pipedreamKeys.all, 'mcp-discovery', options?.app_slug, options?.oauth_app_id, options?.custom] as const,
|
||||
|
|
|
@ -62,6 +62,18 @@ export const usePipedreamApps = (page: number = 1, search?: string, category?: s
|
|||
});
|
||||
};
|
||||
|
||||
export const usePipedreamAppsSearch = (query: string, page: number = 1, category?: string) => {
|
||||
return useQuery({
|
||||
queryKey: ['pipedream', 'apps', 'search', query, page, category],
|
||||
queryFn: async (): Promise<PipedreamAppResponse> => {
|
||||
return await pipedreamApi.searchApps(query, page, category);
|
||||
},
|
||||
staleTime: 5 * 60 * 1000,
|
||||
retry: 2,
|
||||
enabled: !!query && query.length > 0,
|
||||
});
|
||||
};
|
||||
|
||||
export const usePipedreamAvailableTools = createQueryHook(
|
||||
pipedreamKeys.availableTools(),
|
||||
async (forceRefresh: boolean = false): Promise<PipedreamToolsResponse> => {
|
||||
|
|
|
@ -100,8 +100,13 @@ export interface PipedreamAppResponse {
|
|||
current_page: number;
|
||||
page_size: number;
|
||||
has_more: boolean;
|
||||
count?: number;
|
||||
start_cursor?: string;
|
||||
end_cursor?: string;
|
||||
};
|
||||
total_count: number;
|
||||
error?: string;
|
||||
search_query?: string;
|
||||
}
|
||||
|
||||
export interface PipedreamTool {
|
||||
|
@ -174,13 +179,14 @@ export const pipedreamApi = {
|
|||
},
|
||||
|
||||
async getApps(page: number = 1, search?: string, category?: string): Promise<PipedreamAppResponse> {
|
||||
if (search) {
|
||||
return await this.searchApps(search, page, category);
|
||||
}
|
||||
|
||||
const params = new URLSearchParams({
|
||||
page: page.toString(),
|
||||
});
|
||||
|
||||
if (search) {
|
||||
params.append('search', search);
|
||||
}
|
||||
if (category) {
|
||||
params.append('category', category);
|
||||
}
|
||||
|
@ -195,8 +201,41 @@ export const pipedreamApi = {
|
|||
if (!result.success) {
|
||||
throw new Error(result.error?.message || 'Failed to get apps');
|
||||
}
|
||||
const data = result.data!;
|
||||
if (!data.success && data.error) {
|
||||
throw new Error(data.error);
|
||||
}
|
||||
return data;
|
||||
},
|
||||
|
||||
return result.data!;
|
||||
async searchApps(query: string, page: number = 1, category?: string): Promise<PipedreamAppResponse> {
|
||||
const params = new URLSearchParams({
|
||||
q: query,
|
||||
page: page.toString(),
|
||||
});
|
||||
|
||||
if (category) {
|
||||
params.append('category', category);
|
||||
}
|
||||
|
||||
const result = await backendApi.get<PipedreamAppResponse>(
|
||||
`/pipedream/apps/search?${params.toString()}`,
|
||||
{
|
||||
errorContext: { operation: 'search apps', resource: 'Pipedream apps' },
|
||||
}
|
||||
);
|
||||
|
||||
if (!result.success) {
|
||||
throw new Error(result.error?.message || 'Failed to search apps');
|
||||
}
|
||||
|
||||
// Handle both success response and potential error in the data
|
||||
const data = result.data!;
|
||||
if (!data.success && data.error) {
|
||||
throw new Error(data.error);
|
||||
}
|
||||
|
||||
return data;
|
||||
},
|
||||
|
||||
async getAvailableTools(): Promise<PipedreamToolsResponse> {
|
||||
|
|
Loading…
Reference in New Issue