Javascript 使用客户端路由进行服务器端渲染
我的主页路径(/)的初始服务器呈现工作正常 此外,后续客户端导航到(/#/page2)也可以正常工作 但是,如果我直接从地址栏加载/#/page2,服务器呈现的主页将首先在浏览器中加载,然后明显地过渡到/#/page2,这不是我想要的。我只想显示/#/page2,而不首先刷新主页 发生的情况是,节点正在为请求/提供主页,然后当响应到达客户端时,客户端正在运行/#/page2的路由处理程序。两人的行为都是正确的。但这不是我想要的 我如何避免这种行为 我想我需要的是一种方法,让服务器和客户端都知道不同的路由,并且都能够处理它们(同构),但是,服务器不知道url的片段部分 还有其他人有这个问题吗 这个问题并不具体。它是特定于SSR的一个深层链接 我的节点路由器处理“/”如下Javascript 使用客户端路由进行服务器端渲染,javascript,reactjs,single-page-application,isomorphic-javascript,Javascript,Reactjs,Single Page Application,Isomorphic Javascript,我的主页路径(/)的初始服务器呈现工作正常 此外,后续客户端导航到(/#/page2)也可以正常工作 但是,如果我直接从地址栏加载/#/page2,服务器呈现的主页将首先在浏览器中加载,然后明显地过渡到/#/page2,这不是我想要的。我只想显示/#/page2,而不首先刷新主页 发生的情况是,节点正在为请求/提供主页,然后当响应到达客户端时,客户端正在运行/#/page2的路由处理程序。两人的行为都是正确的。但这不是我想要的 我如何避免这种行为 我想我需要的是一种方法,让服务器和客户端都知道不
router.get('/', function(req, res) {
var React = require('react');
var Router = require('react-router');
var Routes = require("../app/clapi-routes.jsx");
var router = Router.create({location: req.url, routes: Routes});
router.run(function(Handler, state) {
var html = React.renderToString(<Handler/>);
return res.render('index.ejs', {html:html});
})
});
router.get('/',函数(req,res){
var React=要求('React');
var-Router=require('react-Router');
var Routes=require(“../app/clapi Routes.jsx”);
var router=router.create({location:req.url,routes:routes});
run(函数(处理程序,状态){
var html=React.renderToString();
返回res.render('index.ejs',{html:html});
})
});
index.ejs只是:
<html lang="en">
<head>
<meta charset="UTF-8">
<link rel="stylesheet" href="/css/json-inspector.css"/>
</head>
<body style="margin:0">
<%- html %>
<script src="/build/bundle.js"></script>
</body>
</html>
停止使用哈希驱动的导航。
#
之后的所有内容都是客户端的,对于这样的事情来说是无用的。所以/#/page2
需要变成/page2
我不确定react是否正确,但其他路由系统也存在同样的问题,因此很容易关闭URL中的
在angular的ui中,路由器是这样做的$locationProvider.html5Mode(true)代码>
服务器端需要知道如何对客户端知道的所有URL做出反应,但这就是实现健壮性的方法-无论导航是如何发生的(客户端事件或链接单击),客户端和服务器都可以端到端地处理场景。我发现有两个步骤:
首先:将react路由器更改为使用router.HistoryLocation而不是默认的(HashLocation)。这使您的路由使用html5推送状态,并将路由路径从/#/page2更改为/page2
// in app.jsx (client side routing)
Router.run(AppRoutes, Router.HistoryLocation, function(Handler) {
React.render(<Handler/>, document.body);
});
//在app.jsx(客户端路由)中
Router.run(批准、Router.HistoryLocation、函数(处理程序){
React.render(,document.body);
});
Second:确保节点页面路由都返回相同的“index.ejs”。否则,您的路由(如/page2将在整页刷新(或deeplink)时显示404
//在server.js(服务器端路由)中
router.get('*',函数(req,res){
Router.run(路由、请求路径、函数(处理程序){
var html=React.renderToString();
返回res.render('index.ejs',{html:html});
});
});
此外:如果您正在为“公共”静态资产提供服务,请在您的路线之前声明:,并删除您可能拥有的任何public/index.html,以便您的节点路由器使用服务器呈现的内容处理/请求。您是否能够编写一个小的JSFIDLE/plnkr来说明您的问题?@harshtuna如何处理节点服务器代码?@joehanik@joehanik忽略了SSR的要点。也许用这个做演示?@jantimon,太酷了。如果需要,我可以复制我的项目。现在,这里有一个屏幕记录的行为:你是正确的。我在下面贴了一个对我有用的完整答案。
// in server.js (server side routing)
router.get('*', function(req, res) {
Router.run(Routes, req.path, function(Handler) {
var html = React.renderToString(<Handler/>);
return res.render('index.ejs', {html: html});
});
});