Skip to content

Commit 096edeb

Browse files
authored
useRoutes should be able to return null when passing locationArg (#9485)
* useRoutes should be able to return `null` when passing `locationArg` * Add danielberndt to contributors.yml * add test cases to ensure that `useRoutes` returns `null` if no route matches
1 parent 2699759 commit 096edeb

File tree

3 files changed

+53
-1
lines changed

3 files changed

+53
-1
lines changed

contributors.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
- codeape2
2727
- coryhouse
2828
- cvbuelow
29+
- danielberndt
2930
- dauletbaev
3031
- david-crespo
3132
- dokeet

packages/react-router/__tests__/useRoutes-test.tsx

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,57 @@ describe("useRoutes", () => {
7575
`);
7676
});
7777

78+
it("returns null when no route matches", () => {
79+
let routes = [{ path: "one", element: <h1>one</h1> }];
80+
81+
const NullRenderer = (props: { routes: RouteObject[] }) => {
82+
const element = useRoutes(props.routes);
83+
return element === null ? <div>is null</div> : <div>is not null</div>;
84+
};
85+
86+
let renderer: TestRenderer.ReactTestRenderer;
87+
TestRenderer.act(() => {
88+
renderer = TestRenderer.create(
89+
<MemoryRouter initialEntries={["/two"]}>
90+
<NullRenderer routes={routes} />
91+
</MemoryRouter>
92+
);
93+
});
94+
95+
expect(renderer.toJSON()).toMatchInlineSnapshot(`
96+
<div>
97+
is null
98+
</div>
99+
`);
100+
});
101+
102+
it("returns null when no route matches and a `location` prop is passed", () => {
103+
let routes = [{ path: "one", element: <h1>one</h1> }];
104+
105+
const NullRenderer = (props: {
106+
routes: RouteObject[];
107+
location?: Partial<Location> & { pathname: string };
108+
}) => {
109+
const element = useRoutes(props.routes, props.location);
110+
return element === null ? <div>is null</div> : <div>is not null</div>;
111+
};
112+
113+
let renderer: TestRenderer.ReactTestRenderer;
114+
TestRenderer.act(() => {
115+
renderer = TestRenderer.create(
116+
<MemoryRouter initialEntries={["/two"]}>
117+
<NullRenderer routes={routes} location={{ pathname: "/three" }} />
118+
</MemoryRouter>
119+
);
120+
});
121+
122+
expect(renderer.toJSON()).toMatchInlineSnapshot(`
123+
<div>
124+
is null
125+
</div>
126+
`);
127+
});
128+
78129
describe("warns", () => {
79130
let consoleWarn: jest.SpyInstance;
80131
beforeEach(() => {

packages/react-router/lib/hooks.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -415,7 +415,7 @@ export function useRoutes(
415415
// When a user passes in a `locationArg`, the associated routes need to
416416
// be wrapped in a new `LocationContext.Provider` in order for `useLocation`
417417
// to use the scoped location instead of the global location.
418-
if (locationArg) {
418+
if (locationArg && renderedMatches) {
419419
return (
420420
<LocationContext.Provider
421421
value={{

0 commit comments

Comments
 (0)