組件如下
import {Link, Route, Switch, Redirect, withRouter, RouteComponentProps} from "react-router-dom";
/** path of router */
export interface IRoutePath {
a: string;
b: string;
c: string;
d: string;
e: string;
f: string;
}
//在組件的Prop接口中加 extends RouteComponentProps
export interface ITestDProps extends RouteComponentProps {
// all router
routePath: IRoutePath;
}
export class TestD extends React.Component<ITestDProps> {
public render() {
const {routePath} = {...this.props};
return (
<>
<Link className={this.linkClassName(routePath.e)} to={routePath.e}>e</Link>
<Link className={this.linkClassName(routePath.f)} to={routePath.f}>f</Link>
<Switch>
<Route exact={true} path={routePath.e}>組件e</Route>
<Route exact={true} path={routePath.f}>組件f</Route>
//點擊link d, 跳轉到e, 這裏的this.props.location.pathname就是當前路由
{this.props.location.pathname === routePath.d? (
<Route>
<Redirect to={routePath.e} />
</Route>
) : null}
</Switch>
</>
);
}
/**
* return link className
* @param currentRouter `string` current router name
*/
private linkClassName(currentRouter) {
return this.props.location.pathname === currentRouter
? "links links-selected"
: "links";
}
}
export const TestDWithRoute= withRouter<any, React.ComponentClass<ITestDProps>>(TestD);
測試如下 //注意,想要在項目中使用mocha請參考我其他文章
import {expect} from "chai";
import * as enzyme from "enzyme";
import * as Adapter from "enzyme-adapter-react-16";
import * as React from "react";
import * as TypeMoq from "typemoq";
import {IRoutePath } from "xxx"; //TestD組件的位置
import {TestD} from "xxx"; //TestD組件的位置
import {Link} from "react-router-dom";
enzyme.configure({adapter: new Adapter()});
const routePath: IRoutePath = {
a: "/a",
b: "/b",
c: "/c",
d: "/d",
e: "/d/e",
f: "/d/f",
};
describe("test TestD component", () => {
let frame: any;
beforeEach(async () => {
const frames = () =>
Promise.resolve(
enzyme.shallow(
<TestD
routePath={routePath}
history={TypeMoq.It.isAny()}
location={TypeMoq.It.isAny()}
match={TypeMoq.It.isAny()}
/>
)
);
frame = await frames();
});
afterEach(() => {
frame.unmount();
});
it("navigation button which called 'e' connect to 'routePath.e'", () => {
expect(frame.find(Link).at(0).prop("to")).equal(routePath.e);
});
it("navigation button which called 'f' connect to 'routePath.f'", () => {
expect(frame.find(Link).at(1).prop("to")).equal(routePath.f);
});
it("when current router is 'routePath.e', the link of e is selected", () => {
//修改prop pathname,就相當於修改路由
frame.setProps({location: {hash: "", pathname: routePath.e, search: "", state: undefined}});
expect(frame.find(".links-selected")).have.lengthOf(1);
});
});
因爲是項目的簡化版,可能直接跑跑不通,請根據自己的項目自行修改