diff --git a/site/src/pages/WorkspacesPage/WorkspacesPage.test.tsx b/site/src/pages/WorkspacesPage/WorkspacesPage.test.tsx index 462ce080add5d..2486d500c6527 100644 --- a/site/src/pages/WorkspacesPage/WorkspacesPage.test.tsx +++ b/site/src/pages/WorkspacesPage/WorkspacesPage.test.tsx @@ -23,7 +23,7 @@ describe("WorkspacesPage", () => { render() // Then - await screen.findByText(Language.emptyMessage) + await screen.findByText(Language.emptyCreateWorkspaceMessage) }) it("renders a filled workspaces page", async () => { diff --git a/site/src/pages/WorkspacesPage/WorkspacesPage.tsx b/site/src/pages/WorkspacesPage/WorkspacesPage.tsx index b3c47f173e46a..d8fd2f329d84f 100644 --- a/site/src/pages/WorkspacesPage/WorkspacesPage.tsx +++ b/site/src/pages/WorkspacesPage/WorkspacesPage.tsx @@ -1,12 +1,25 @@ import { useMachine } from "@xstate/react" -import { FC } from "react" +import { FC, useEffect } from "react" import { Helmet } from "react-helmet" +import { useSearchParams } from "react-router-dom" import { pageTitle } from "../../util/page" +import { workspaceFilterQuery } from "../../util/workspace" import { workspacesMachine } from "../../xServices/workspaces/workspacesXService" import { WorkspacesPageView } from "./WorkspacesPageView" const WorkspacesPage: FC = () => { const [workspacesState, send] = useMachine(workspacesMachine) + const [searchParams, setSearchParams] = useSearchParams() + + useEffect(() => { + const filter = searchParams.get("filter") + const query = filter ? filter : workspaceFilterQuery.me + + send({ + type: "SET_FILTER", + query, + }) + }, [searchParams, send]) return ( <> @@ -19,10 +32,8 @@ const WorkspacesPage: FC = () => { loading={workspacesState.hasTag("loading")} workspaces={workspacesState.context.workspaces} onFilter={(query) => { - send({ - type: "SET_FILTER", - query, - }) + searchParams.set("filter", query) + setSearchParams(searchParams) }} /> diff --git a/site/src/pages/WorkspacesPage/WorkspacesPageView.stories.tsx b/site/src/pages/WorkspacesPage/WorkspacesPageView.stories.tsx index 880698a8a0c8a..1b62b533ae30b 100644 --- a/site/src/pages/WorkspacesPage/WorkspacesPageView.stories.tsx +++ b/site/src/pages/WorkspacesPage/WorkspacesPageView.stories.tsx @@ -1,6 +1,7 @@ import { ComponentMeta, Story } from "@storybook/react" import { ProvisionerJobStatus, Workspace, WorkspaceTransition } from "../../api/typesGenerated" import { MockWorkspace } from "../../testHelpers/entities" +import { workspaceFilterQuery } from "../../util/workspace" import { WorkspacesPageView, WorkspacesPageViewProps } from "./WorkspacesPageView" export default { @@ -48,7 +49,14 @@ AllStates.args = { ], } -export const Empty = Template.bind({}) -Empty.args = { +export const OwnerHasNoWorkspaces = Template.bind({}) +OwnerHasNoWorkspaces.args = { workspaces: [], + filter: workspaceFilterQuery.me, +} + +export const NoResults = Template.bind({}) +NoResults.args = { + workspaces: [], + filter: "searchtearmwithnoresults", } diff --git a/site/src/pages/WorkspacesPage/WorkspacesPageView.tsx b/site/src/pages/WorkspacesPage/WorkspacesPageView.tsx index 53fb77512c251..02d38604736a8 100644 --- a/site/src/pages/WorkspacesPage/WorkspacesPageView.tsx +++ b/site/src/pages/WorkspacesPage/WorkspacesPageView.tsx @@ -35,16 +35,16 @@ import { PageHeader, PageHeaderTitle } from "../../components/PageHeader/PageHea import { Stack } from "../../components/Stack/Stack" import { TableLoader } from "../../components/TableLoader/TableLoader" import { getFormHelpers, onChangeTrimmed } from "../../util/formUtils" -import { getDisplayStatus } from "../../util/workspace" +import { getDisplayStatus, workspaceFilterQuery } from "../../util/workspace" dayjs.extend(relativeTime) export const Language = { - createButton: "Create workspace", - emptyMessage: "Create your first workspace", - emptyDescription: "Start editing your source code and building your software", - filterName: "Filters", createWorkspaceButton: "Create workspace", + emptyCreateWorkspaceMessage: "Create your first workspace", + emptyCreateWorkspaceDescription: "Start editing your source code and building your software", + emptyResultsMessage: "No results matched your search", + filterName: "Filters", yourWorkspacesButton: "Your workspaces", allWorkspacesButton: "All workspaces", workspaceTooltipTitle: "What is workspace?", @@ -93,6 +93,7 @@ export const WorkspacesPageView: FC = ({ loading, works const theme: Theme = useTheme() const form = useFormik({ + enableReinitialize: true, initialValues: { query: filter ?? "", }, @@ -200,19 +201,29 @@ export const WorkspacesPageView: FC = ({ loading, works {!workspaces && loading && } {workspaces && workspaces.length === 0 && ( - - - - - - } - /> - - + <> + {filter === workspaceFilterQuery.me || filter === workspaceFilterQuery.all ? ( + + + + + + } + /> + + + ) : ( + + + + + + )} + )} {workspaces && workspaces.map((workspace) => { diff --git a/site/src/util/workspace.ts b/site/src/util/workspace.ts index 95f85295a0a81..1c60e40ae9074 100644 --- a/site/src/util/workspace.ts +++ b/site/src/util/workspace.ts @@ -297,3 +297,8 @@ export const workspaceQueryToFilter = (query?: string): TypesGen.WorkspaceFilter return defaultFilter } } + +export const workspaceFilterQuery = { + me: "owner:me", + all: "", +} diff --git a/site/src/xServices/workspaces/workspacesXService.ts b/site/src/xServices/workspaces/workspacesXService.ts index d4367b7ad95a3..842d1108d2b67 100644 --- a/site/src/xServices/workspaces/workspacesXService.ts +++ b/site/src/xServices/workspaces/workspacesXService.ts @@ -24,10 +24,7 @@ export const workspacesMachine = createMachine( }, }, id: "workspaceState", - context: { - filter: "owner:me", - }, - initial: "gettingWorkspaces", + initial: "ready", states: { ready: { on: {