Skip to content

Commit

Permalink
homepage that redirects on tenant lock
Browse files Browse the repository at this point in the history
  • Loading branch information
macfarlandian committed Apr 14, 2021
1 parent 9196c3b commit 980159b
Show file tree
Hide file tree
Showing 11 changed files with 172 additions and 15 deletions.
3 changes: 1 addition & 2 deletions spotlight-client/src/App-auth.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -54,8 +54,7 @@ async function getApp() {
// mocking the node env is esoteric, see https://stackoverflow.com/a/48042799
const ORIGINAL_ENV = process.env;

// home page redirects to the ND home page
const authenticatedTextMatch = /North Dakota/;
const authenticatedTextMatch = /Spotlight/;

beforeEach(async () => {
// make a copy that we can modify
Expand Down
9 changes: 4 additions & 5 deletions spotlight-client/src/App.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -54,10 +54,10 @@ describe("navigation", () => {
expect(screen.getByRole(...lookupArgs)).toBeInTheDocument();
}

test("site home redirects to ND", async () => {
test("site home", async () => {
renderNavigableApp();
expect(
await screen.findByRole("heading", { name: /North Dakota/, level: 1 })
await screen.findByRole("heading", { name: /Spotlight/, level: 1 })
).toBeVisible();
});

Expand Down Expand Up @@ -108,7 +108,7 @@ describe("navigation", () => {
});

test("links", async () => {
renderNavigableApp();
renderNavigableApp({ route: "/us-nd" });

const inNav = within(screen.getByRole("navigation"));

Expand Down Expand Up @@ -145,10 +145,9 @@ describe("navigation", () => {
);

fireEvent.click(homeLink);
// home redirect to ND
await waitFor(async () =>
expect(await screen.findByTestId("PageTitle")).toHaveTextContent(
"North Dakota"
"Spotlight"
)
);
});
Expand Down
4 changes: 2 additions & 2 deletions spotlight-client/src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import AuthWall from "./AuthWall";
import { FOOTER_HEIGHT, NAV_BAR_HEIGHT } from "./constants";
import GlobalStyles from "./GlobalStyles";
import NotFound from "./NotFound";
import PageHome from "./PageHome";
import PageNarrative from "./PageNarrative";
import PageTenant from "./PageTenant";
import PageviewTracker from "./PageviewTracker";
Expand Down Expand Up @@ -69,13 +70,12 @@ const App: React.FC = () => {
NOTE: every leaf route component in this router should be wrapped
by the withRouteSync higher-order component to keep data and UI in sync!
*/}
{/* while there is only one state, home simply redirects to ND home */}
<Redirect from="/" to="/us-nd" noThrow />
{/*
this was the ND homepage for v1;
let's make sure people who bookmarked it are not lost
*/}
<Redirect from="/us_nd/overview" to="/us-nd" noThrow />
<PageHome path="/" />
<PassThroughPage path="/:tenantId">
<PageTenant path="/" />
<PageNarrative path={`/${NarrativesSlug}/:narrativeTypeId`} />
Expand Down
11 changes: 10 additions & 1 deletion spotlight-client/src/DataStore/TenantStore.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,16 @@ test("lock tenant if set from current domain", () => {
reactImmediately(() => {
expect(tenantStore.currentTenant?.id).toBe("US_ND");
expect(tenantStore.currentTenantId).toBe("US_ND");
expect(tenantStore.locked).toBe(true);
});

// TODO (#391): we shouldn't be able to change to another tenant either
// we shouldn't be able to switch to another tenant either
runInAction(() => {
tenantStore.currentTenantId = "US_PA";
});
reactImmediately(() => {
expect(tenantStore.currentTenant?.id).toBe("US_ND");
expect(tenantStore.currentTenantId).toBe("US_ND");
expect(tenantStore.locked).toBe(true);
});
});
3 changes: 3 additions & 0 deletions spotlight-client/src/DataStore/TenantStore.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ export default class TenantStore {

currentTenantId?: TenantId;

readonly locked: boolean = false;

rootStore: RootStore;

tenants: Map<TenantId, Tenant>;
Expand All @@ -46,6 +48,7 @@ export default class TenantStore {
// tenant mapped from domain should be locked
const tenantFromDomain = getTenantFromDomain();
if (tenantFromDomain) {
this.locked = true;
this.currentTenantId = tenantFromDomain;
// returning null renders an observable property immutable
intercept(this, "currentTenantId", () => null);
Expand Down
71 changes: 71 additions & 0 deletions spotlight-client/src/PageHome/PageHome.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
// Recidiviz - a data platform for criminal justice reform
// Copyright (C) 2021 Recidiviz, Inc.
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
// =============================================================================

import { Link, Redirect } from "@reach/router";
import { observer } from "mobx-react-lite";
import { rem } from "polished";
import React from "react";
import styled from "styled-components/macro";
import getTenantList from "../contentApi/getTenantList";
import getUrlForResource from "../routerUtils/getUrlForResource";
import { useDataStore } from "../StoreProvider";
import { CopyBlock, PageSection, PageTitle } from "../UiLibrary";
import withRouteSync from "../withRouteSync";

const PageContainer = styled(PageSection)`
padding-bottom: ${rem(48)};
padding-top: ${rem(48)};
`;

const PageHome = (): React.ReactElement => {
const {
tenantStore: { locked, currentTenantId },
} = useDataStore();

if (locked && currentTenantId) {
return (
<Redirect
to={getUrlForResource({
page: "tenant",
params: { tenantId: currentTenantId },
})}
/>
);
}

return (
<PageContainer>
<PageTitle>Spotlight</PageTitle>
<CopyBlock>
{getTenantList().map(({ id, name }) => (
<p>
<Link
to={getUrlForResource({
page: "tenant",
params: { tenantId: id },
})}
>
{name}
</Link>
</p>
))}
</CopyBlock>
</PageContainer>
);
};

export default withRouteSync(observer(PageHome));
18 changes: 18 additions & 0 deletions spotlight-client/src/PageHome/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
// Recidiviz - a data platform for criminal justice reform
// Copyright (C) 2021 Recidiviz, Inc.
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
// =============================================================================

export { default } from "./PageHome";
6 changes: 1 addition & 5 deletions spotlight-client/src/ScrollManager/ScrollManager.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,11 +30,7 @@ test("scrolls on page change", async () => {
history: { navigate },
} = renderNavigableApp();

await waitFor(() => {
// once for site root load, once for redirect to ND home
expect(scrollSpy).toHaveBeenNthCalledWith(1, 0, 0);
expect(scrollSpy).toHaveBeenNthCalledWith(2, 0, 0);
});
expect(scrollSpy).toHaveBeenCalledWith(0, 0);
scrollSpy.mockClear();

await act(() => navigate(`/us-nd/${NarrativesSlug}/prison`));
Expand Down
33 changes: 33 additions & 0 deletions spotlight-client/src/contentApi/getTenantList.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
// Recidiviz - a data platform for criminal justice reform
// Copyright (C) 2021 Recidiviz, Inc.
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
// =============================================================================

import getTenantList from "./getTenantList";

test("getTenantList", () => {
expect(getTenantList()).toMatchInlineSnapshot(`
Array [
Object {
"id": "US_ND",
"name": "North Dakota",
},
Object {
"id": "US_PA",
"name": "Pennsylvania",
},
]
`);
});
26 changes: 26 additions & 0 deletions spotlight-client/src/contentApi/getTenantList.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
// Recidiviz - a data platform for criminal justice reform
// Copyright (C) 2021 Recidiviz, Inc.
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
// =============================================================================

import retrieveContent from "./retrieveContent";
import { TenantId, TenantIdList } from "./types";

export default function getTenantList(): { id: TenantId; name: string }[] {
return TenantIdList.map((id) => ({
id,
name: retrieveContent({ tenantId: id }).name,
}));
}
3 changes: 3 additions & 0 deletions spotlight-client/src/testUtils/testUtils.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,9 @@ export function renderNavigableApp({ route = "/" } = {}): {
history: ReturnType<typeof createHistory>;
rendered: ReturnType<typeof render>;
} {
// make sure the current window.history state matches the route we are rendering
// (Reach Router will keep it in sync for subsequent navigation)
window.history.replaceState(null, "", route);
const history = createHistory(createMemorySource(route));

return {
Expand Down

0 comments on commit 980159b

Please sign in to comment.