大多数的导航都是通过链接来进行的,我们可以通过编程的方式来修改通过链接来导航,比如我们可以提交表单或者点击按钮等等。
//Repos.js
import React from 'react'
import NavLink from './NavLink'
export default React.createClass({
// add this method
handleSubmit(event) {
event.preventDefault()
const userName = event.target.elements[0].value
const repo = event.target.elements[1].value
const path = `/repos/${userName}/${repo}`
console.log(path)
},
render() {
return (
Repos
React Router
React
{/* add this form */}
-
{this.props.children}
)
}
})
效果如图所示:
我们有两种方式实现上述的功能,但是第一种相比第二种简单。
第二种方法就是通过browserHistory
进入Router
当中的index.js
来把URL存入历史记录当中。
// modules/Repos.js
import { browserHistory } from 'react-router'
// ...
handleSubmit(event) {
// ...
const path = `/repos/${userName}/${repo}`
browserHistory.push(path)
},
// ...
但是这样会有一个潜在的问题就是如果你传入了不同的历史给路由了,那么就会出错。
你可以使用Router
所提供的上下路由,但是在使用之前你必须要声明才能使用。
export default React.createClass({
// ask for `router` from context
contextTypes: {
router: React.PropTypes.object
},
// ...
handleSubmit(event) {
// ...
this.context.router.push(path)
},
// ..
})
在React中,我们首先要做的第一件事就是要渲染服务器。
但是呢,节点不认识JSX语法,所以我们需要让节点识别并且解析JSX语法,所以我们要配置一个文件:
//webpack.server.config.js
var fs = require('fs')
var path = require('path')
module.exports = {
entry: path.resolve(__dirname, 'server.js'),
output: {
filename: 'server.bundle.js'
},
target: 'node',
// keep node_module paths out of the bundle
externals: fs.readdirSync(path.resolve(__dirname, 'node_modules')).concat([
'react-dom/server', 'react/addons',
]).reduce(function (ext, mod) {
ext[mod] = 'commonjs ' + mod
return ext
}, {}),
node: {
__filename: true,
__dirname: true
},
module: {
loaders: [
{ test: /\.js$/, exclude: /node_modules/, loader: 'babel-loader?presets[]=es2015&presets[]=react' }
]
}
}
在运行我们的程序之前我们需要更新一下脚本来配置服务器:
//package.josn
"scripts": {
"start": "if-env NODE_ENV=production && npm run start:prod || npm run start:dev",
"start:dev": "webpack-dev-server --inline --content-base public/ --history-api-fallback",
"start:prod": "npm run build && node server.bundle.js",
"build:client": "webpack",
"build:server": "webpack --config webpack.server.config.js",
"build": "npm run build:client && npm run build:server"
},
很不幸,当我运行NODE_ENV=production npm start
命令时,客户端与服务器之间都出错了,qwq。我去找错误了,qwq。
等我找到错误之后我再回来完善。。。
找到错误了,是我自己太蠢,没有按照官方示例库的步骤一步一步地来。
不说废话了,回来继续:
这个命令要分开运行才可以,直接运行这句命令cmd会说内部没这个命令的,分两步走:
1、set NODE_ENV=production
2、npm start
弄好之后我们就通过webpack把服务端与客户端都搭建好了。
我们现在回归路由,我们把路由拆分成一个模块,以便客户端和服务器条目都可以需要它。在模块/路由上创建一个文件,并将路由和组件移动到其中。
// modules/routes.js
import React from 'react'
import { Route, IndexRoute } from 'react-router'
import App from './App'
import About from './About'
import Repos from './Repos'
import Repo from './Repo'
import Home from './Home'
module.exports = (
)
// index.js
import React from 'react'
import { render } from 'react-dom'
import { Router, browserHistory } from 'react-router'
// import routes and pass them into
import routes from './modules/routes'
render(
,
document.getElementById('app')
)