diff --git a/skyvern-frontend/src/routes/workflows/Workflows.tsx b/skyvern-frontend/src/routes/workflows/Workflows.tsx index fa228fc7..d194590c 100644 --- a/skyvern-frontend/src/routes/workflows/Workflows.tsx +++ b/skyvern-frontend/src/routes/workflows/Workflows.tsx @@ -1,6 +1,6 @@ import { getClient } from "@/api/AxiosClient"; +import { WorkflowRunApiResponse } from "@/api/types"; import { StatusBadge } from "@/components/StatusBadge"; -import { Alert, AlertDescription, AlertTitle } from "@/components/ui/alert"; import { Button } from "@/components/ui/button"; import { Pagination, @@ -25,40 +25,20 @@ import { TooltipTrigger, } from "@/components/ui/tooltip"; import { useCredentialGetter } from "@/hooks/useCredentialGetter"; +import { downloadBlob } from "@/util/downloadBlob"; import { basicLocalTimeFormat, basicTimeFormat } from "@/util/timeFormat"; import { cn } from "@/util/utils"; -import { - DownloadIcon, - ExclamationTriangleIcon, - Pencil2Icon, - PlayIcon, - PlusIcon, - ReloadIcon, -} from "@radix-ui/react-icons"; -import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query"; +import { DownloadIcon, Pencil2Icon, PlayIcon } from "@radix-ui/react-icons"; +import { useQuery } from "@tanstack/react-query"; import { useNavigate, useSearchParams } from "react-router-dom"; -import { stringify as convertToYAML } from "yaml"; -import { ImportWorkflowButton } from "./ImportWorkflowButton"; -import { WorkflowCreateYAMLRequest } from "./types/workflowYamlTypes"; -import { WorkflowActions } from "./WorkflowActions"; -import { WorkflowTitle } from "./WorkflowTitle"; import { WorkflowApiResponse } from "./types/workflowTypes"; -import { WorkflowRunApiResponse } from "@/api/types"; -import { downloadBlob } from "@/util/downloadBlob"; - -const emptyWorkflowRequest: WorkflowCreateYAMLRequest = { - title: "New Workflow", - description: "", - workflow_definition: { - blocks: [], - parameters: [], - }, -}; +import { WorkflowActions } from "./WorkflowActions"; +import { WorkflowsPageBanner } from "./WorkflowsPageBanner"; +import { WorkflowTitle } from "./WorkflowTitle"; function Workflows() { const credentialGetter = useCredentialGetter(); const navigate = useNavigate(); - const queryClient = useQueryClient(); const [searchParams, setSearchParams] = useSearchParams(); const workflowsPage = searchParams.get("workflowsPage") ? Number(searchParams.get("workflowsPage")) @@ -99,27 +79,6 @@ function Workflows() { refetchOnMount: "always", }); - const createNewWorkflowMutation = useMutation({ - mutationFn: async () => { - const client = await getClient(credentialGetter); - const yaml = convertToYAML(emptyWorkflowRequest); - return client.post< - typeof emptyWorkflowRequest, - { data: WorkflowApiResponse } - >("/workflows", yaml, { - headers: { - "Content-Type": "text/plain", - }, - }); - }, - onSuccess: (response) => { - queryClient.invalidateQueries({ - queryKey: ["workflows"], - }); - navigate(`/workflows/${response.data.workflow_permanent_id}/edit`); - }, - }); - function handleExport() { if (!workflowRuns) { return; // should never happen @@ -176,55 +135,12 @@ function Workflows() { navigate(path); } - const showExperimentalMessage = - workflows?.length === 0 && workflowsPage === 1; - return (
- {showExperimentalMessage && ( - - -
- - Experimental Feature -
-
- - Workflows are still in experimental mode. Please{" "} - { - - book a demo - - }{" "} - if you'd like to learn more. If you're feeling adventurous, create - your first workflow! - -
- )} +
-
+

Workflows

-
- - -
diff --git a/skyvern-frontend/src/routes/workflows/WorkflowsPageBanner.tsx b/skyvern-frontend/src/routes/workflows/WorkflowsPageBanner.tsx new file mode 100644 index 00000000..30cf12ff --- /dev/null +++ b/skyvern-frontend/src/routes/workflows/WorkflowsPageBanner.tsx @@ -0,0 +1,102 @@ +import { Button } from "@/components/ui/button"; +import { ImportWorkflowButton } from "./ImportWorkflowButton"; +import { useNavigate } from "react-router-dom"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { getClient } from "@/api/AxiosClient"; +import { useCredentialGetter } from "@/hooks/useCredentialGetter"; +import { WorkflowCreateYAMLRequest } from "./types/workflowYamlTypes"; +import { stringify as convertToYAML } from "yaml"; +import { WorkflowApiResponse } from "./types/workflowTypes"; +import { PlusIcon, ReloadIcon } from "@radix-ui/react-icons"; + +const emptyWorkflowRequest: WorkflowCreateYAMLRequest = { + title: "New Workflow", + description: "", + workflow_definition: { + blocks: [], + parameters: [], + }, +}; + +function WorkflowsPageBanner() { + const navigate = useNavigate(); + const credentialGetter = useCredentialGetter(); + const queryClient = useQueryClient(); + + const createNewWorkflowMutation = useMutation({ + mutationFn: async () => { + const client = await getClient(credentialGetter); + const yaml = convertToYAML(emptyWorkflowRequest); + return client.post< + typeof emptyWorkflowRequest, + { data: WorkflowApiResponse } + >("/workflows", yaml, { + headers: { + "Content-Type": "text/plain", + }, + }); + }, + onSuccess: (response) => { + queryClient.invalidateQueries({ + queryKey: ["workflows"], + }); + navigate(`/workflows/${response.data.workflow_permanent_id}/edit`); + }, + }); + + return ( +
+
+

Workflows

+
+
+ + +
+
+
+
+ Workflows let you create complex web-agents that can: +
+
+
+ 1 +
+
Save browser sessions and re-use them in subsequent runs
+
+
+
+ 2 +
+
+ Connect multiple agents together to carry out complex objectives +
+
+
+
+ 3 +
+
+ Allow Skyvern agents to execute non-browser tasks such as sending + emails, or parsing PDFs +
+
+
+
+
+ ); +} + +export { WorkflowsPageBanner };