Skip to content

Commit fdec57f

Browse files
committed
Use RouterContext in Link
1 parent 45d5f7d commit fdec57f

File tree

3 files changed

+22
-18
lines changed

3 files changed

+22
-18
lines changed

packages/react-router-dom/modules/Link.js

Lines changed: 18 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2,27 +2,21 @@ import React from "react";
22
import PropTypes from "prop-types";
33
import invariant from "invariant";
44
import { createLocation } from "history";
5+
import RouterContext from "./RouterContext";
56

67
const isModifiedEvent = event =>
78
!!(event.metaKey || event.altKey || event.ctrlKey || event.shiftKey);
89

910
/**
1011
* The public API for rendering a history-aware <a>.
1112
*/
12-
class Link extends React.Component {
13+
class InnerLink extends React.Component {
1314
static propTypes = {
1415
onClick: PropTypes.func,
1516
target: PropTypes.string,
1617
replace: PropTypes.bool,
1718
to: PropTypes.oneOfType([PropTypes.string, PropTypes.object]).isRequired,
18-
innerRef: PropTypes.oneOfType([PropTypes.string, PropTypes.func])
19-
};
20-
21-
static defaultProps = {
22-
replace: false
23-
};
24-
25-
static contextTypes = {
19+
innerRef: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),
2620
router: PropTypes.shape({
2721
history: PropTypes.shape({
2822
push: PropTypes.func.isRequired,
@@ -32,6 +26,10 @@ class Link extends React.Component {
3226
}).isRequired
3327
};
3428

29+
static defaultProps = {
30+
replace: false
31+
};
32+
3533
handleClick = event => {
3634
if (this.props.onClick) this.props.onClick(event);
3735

@@ -43,8 +41,7 @@ class Link extends React.Component {
4341
) {
4442
event.preventDefault();
4543

46-
const { history } = this.context.router;
47-
const { replace, to } = this.props;
44+
const { replace, to, router: { history } } = this.props;
4845

4946
if (replace) {
5047
history.replace(to);
@@ -55,16 +52,16 @@ class Link extends React.Component {
5552
};
5653

5754
render() {
58-
const { replace, to, innerRef, ...props } = this.props; // eslint-disable-line no-unused-vars
55+
const { replace, to, innerRef, router, ...props } = this.props; // eslint-disable-line no-unused-vars
5956

6057
invariant(
61-
this.context.router,
58+
this.props.router,
6259
"You should not use <Link> outside a <Router>"
6360
);
6461

6562
invariant(to !== undefined, 'You must specify the "to" property');
6663

67-
const { history } = this.context.router;
64+
const { history } = router;
6865
const location =
6966
typeof to === "string"
7067
? createLocation(to, null, null, history.location)
@@ -77,4 +74,11 @@ class Link extends React.Component {
7774
}
7875
}
7976

77+
export { InnerLink };
78+
79+
const Link = props =>
80+
RouterContext.consume(({ router }) => (
81+
<InnerLink {...props} router={router} />
82+
));
83+
8084
export default Link;

packages/react-router-dom/modules/NavLink.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import React from "react";
22
import PropTypes from "prop-types";
33
import Route from "./Route";
4-
import Link from "./Link";
4+
import Link, { InnerLink } from "./Link";
55

66
/**
77
* A <Link> wrapper that knows if it's "active" or not.
@@ -52,7 +52,7 @@ const NavLink = ({
5252
};
5353

5454
NavLink.propTypes = {
55-
to: Link.propTypes.to,
55+
to: InnerLink.propTypes.to,
5656
exact: PropTypes.bool,
5757
strict: PropTypes.bool,
5858
location: PropTypes.object,

packages/react-router-dom/modules/__tests__/Link-test.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ describe("A <Link>", () => {
5353

5454
expect(console.error.calls.count()).toBe(3);
5555
expect(console.error.calls.argsFor(0)[0]).toContain(
56-
"The context `router` is marked as required in `Link`"
56+
"The prop `router` is marked as required in `InnerLink`"
5757
);
5858
});
5959

@@ -73,7 +73,7 @@ describe("A <Link>", () => {
7373

7474
expect(console.error.calls.count()).toBe(3);
7575
expect(console.error.calls.argsFor(0)[0]).toContain(
76-
"The prop `to` is marked as required in `Link`"
76+
"The prop `to` is marked as required in `InnerLink`"
7777
);
7878
});
7979

0 commit comments

Comments
 (0)