Skip to content

revert: remove localStorage sync for workspaces search params #9827

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Sep 22, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 0 additions & 21 deletions site/src/components/Filter/filter.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ import Divider from "@mui/material/Divider";
import OpenInNewOutlined from "@mui/icons-material/OpenInNewOutlined";

import { useDebouncedFunction } from "hooks/debounce";
import { useEffectEvent } from "hooks/hookPolyfills";
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we are not using this hook anymore we should remove it


export type PresetFilter = {
name: string;
Expand Down Expand Up @@ -56,26 +55,6 @@ export const useFilter = ({
const [searchParams, setSearchParams] = searchParamsResult;
const query = searchParams.get(useFilterParamsKey) ?? fallbackFilter;

// Stabilizing reference to setSearchParams from one central spot, just to be
// on the extra careful side; don't want effects over-running. You would think
// this would be overkill, but setSearchParams isn't stable out of the box
const stableSetSearchParams = useEffectEvent(setSearchParams);

// Keep params synced with query, even as query changes from outside sources
useEffect(() => {
stableSetSearchParams((currentParams) => {
const currentQuery = currentParams.get(useFilterParamsKey);

if (query === "") {
currentParams.delete(useFilterParamsKey);
} else if (currentQuery !== query) {
currentParams.set(useFilterParamsKey, query);
}

return currentParams;
});
}, [stableSetSearchParams, query]);

const update = (newValues: string | FilterValues) => {
const serialized =
typeof newValues === "string" ? newValues : stringifyFilter(newValues);
Expand Down
46 changes: 3 additions & 43 deletions site/src/pages/WorkspacesPage/WorkspacesPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import {
useDashboard,
useIsWorkspaceActionsEnabled,
} from "components/Dashboard/DashboardProvider";
import { type FC, useEffect, useState, useSyncExternalStore } from "react";
import { type FC, useEffect, useState } from "react";
import { Helmet } from "react-helmet-async";
import { pageTitle } from "utils/page";
import { useWorkspacesData, useWorkspaceUpdate } from "./data";
Expand Down Expand Up @@ -140,29 +140,6 @@ const WorkspacesPage: FC = () => {

export default WorkspacesPage;

const workspaceFilterKey = "WorkspacesPage/filter";
const defaultWorkspaceFilter = "owner:me";

// Function should stay outside components as much as possible; if declared
// inside the component, React would add/remove event listeners every render
function subscribeToFilterChanges(notifyReact: () => void) {
const onStorageChange = (event: StorageEvent) => {
const { key, storageArea, oldValue, newValue } = event;

const shouldNotify =
key === workspaceFilterKey &&
storageArea === window.localStorage &&
newValue !== oldValue;

if (shouldNotify) {
notifyReact();
}
};

window.addEventListener("storage", onStorageChange);
return () => window.removeEventListener("storage", onStorageChange);
}

type UseWorkspacesFilterOptions = {
searchParamsResult: ReturnType<typeof useSearchParams>;
onFilterChange: () => void;
Expand All @@ -172,27 +149,10 @@ const useWorkspacesFilter = ({
searchParamsResult,
onFilterChange,
}: UseWorkspacesFilterOptions) => {
// Using useSyncExternalStore store to safely access localStorage from the
// first render; both snapshot callbacks return primitives, so no special
// trickery needed to prevent hook from immediately blowing up in dev mode
const localStorageFilter = useSyncExternalStore(
subscribeToFilterChanges,
() => {
return (
window.localStorage.getItem(workspaceFilterKey) ??
defaultWorkspaceFilter
);
},
() => defaultWorkspaceFilter,
);

const filter = useFilter({
fallbackFilter: localStorageFilter,
fallbackFilter: "owner:me",
searchParamsResult,
onUpdate: (newValues) => {
window.localStorage.setItem(workspaceFilterKey, newValues);
onFilterChange();
},
onUpdate: onFilterChange,
});

const permissions = usePermissions();
Expand Down