gpt4 book ai didi

reactjs - 使用webpack和react-router进行延迟加载和代码分割不加载

转载 作者:行者123 更新时间:2023-12-03 13:25:47 24 4
gpt4 key购买 nike

我正在努力从客户端移动我的 react v0.14+ redux v3.0 + react-router v1.0 代码库使用 webpack v1.12 将端渲染到服务器端渲染进行捆绑和代码分割成 block ,以按需加载路由和组件。

我正在关注 https://github.com/rackt/example-react-router-server-rendering-lazy-routes 并基于我的设置因为我认为它提供了简单性和强大的实用性。昨天一整天,我一直在努力转向服务器端渲染,但遇到了一些我无法解决的问题,我不确定它们是否是因为 webpack 不设置正确,如果服务器/客户端或路由配置上的 react-router 出现问题,或者我在设置 redux 时出现问题这就是导致这些问题的原因。

我遇到了以下问题:

  1. 我能够加载初始页面,一切正常,但没有其他路由加载并给我 GET http://localhost:3000/profile 404 (Not Found)
  2. 索引/主页 javascript 可以工作,但所有资源 (css) 均呈现为 text/javascript,因此除非内联,否则样式不会显示。

webpack.config.js

var fs = require('fs')
var path = require('path')
var webpack = require('webpack')

module.exports = {

devtool: 'source-map',

entry: './client/client.jsx',

output: {
path: __dirname + '/__build__',
filename: '[name].js',
chunkFilename: '[id].chunk.js',
publicPath: '/__build__/'
},

module: {
loaders: [
{
test: /\.jsx?$/,
exclude: /(node_modules|bower_components)/,
loader: 'babel-loader'
}
]
},

plugins: [
new webpack.optimize.OccurenceOrderPlugin(),
new webpack.optimize.DedupePlugin(),
new webpack.optimize.UglifyJsPlugin({
compressor: { warnings: false },
}),
new webpack.DefinePlugin({
'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV || 'development')
})
]

}

服务器.js

import http from 'http';
import React from 'react';
import {renderToString} from 'react-dom/server';
import { match, RoutingContext } from 'react-router';
import {Provider} from 'react-redux';
import configureStore from './../common/store/store.js';

import fs from 'fs';
import { createPage, write, writeError, writeNotFound, redirect } from './server-utils.js';
import routes from './../common/routes/rootRoutes.js';

const PORT = process.env.PORT || 3000;

var store = configureStore();
const initialState = store.getState();

function renderApp(props, res) {
var markup = renderToString(
<Provider store={store}>
<RoutingContext {...props}/>
</Provider>
);
var html = createPage(markup, initialState);
write(html, 'text/html', res);
}

http.createServer((req, res) => {

if (req.url === '/favicon.ico') {
write('haha', 'text/plain', res);
}

// serve JavaScript assets
else if (/__build__/.test(req.url)) {
fs.readFile(`.${req.url}`, (err, data) => {
write(data, 'text/javascript', res);
})
}

// handle all other urls with React Router
else {
match({ routes, location: req.url }, (error, redirectLocation, renderProps) => {
if (error)
writeError('ERROR!', res);
else if (redirectLocation)
redirect(redirectLocation, res);
else if (renderProps)
renderApp(renderProps, res);
else
writeNotFound(res);
});
}

}).listen(PORT)
console.log(`listening on port ${PORT}`)

服务器实用程序

与我上面发布的存储库相同example-react-router-server-rendering-lazy-routes只需导航到/modules/utils/server-utils.js存储库中的 。唯一的区别是 createPage 函数:

export function createPage(html, initialState) {
return( `
<!doctype html>
<html>
<head>
<meta charset="utf-8"/>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="./../bower_components/Ionicons/css/ionicons.min.css">
<link rel="stylesheet" href="./../dist/main.css">
<title>Sell Your Soles</title>
</head>
<body>
<div id="app">${html}</div>
<script>window.__INITIAL_STATE__ = ${JSON.stringify(initialState)};</script>
<script src="/__build__/main.js"></script>
</body>
</html>
`);
}

rootRoute.js

// polyfill webpack require.ensure
if (typeof require.ensure !== 'function') require.ensure = (d, c) => c(require)

import App from '../components/App.jsx'
import Landing from '../components/Landing/Landing.jsx'

export default {
path: '/',
component: App,
getChildRoutes(location, cb) {
require.ensure([], (require) => {
cb(null, [
require('./UserProfile/UserProfileRoute.js'),
require('./UserHome/UserHomeRoute.js'),
require('./SneakerPage/SneakerPageRoute.js'),
require('./Reviews/ReviewsRoute.js'),
require('./Listings/ListingsRoute.js'),
require('./Events/EventsRoute.js')
])
})
},
indexRoute: {
component: Landing
}
}

userProfileRoute.js

import UserProfile from '../../components/UserProfile/UserProfile.jsx';

export default {
path: 'profile',
component: UserProfile
}

client.js

import React from 'react';
import { match, Router } from 'react-router';
import { render } from 'react-dom';
import { createHistory } from 'history';
import routes from './../common/routes/rootRoutes.js';
import {Provider} from 'react-redux';
import configureStore from './../common/store/store.js';


const { pathname, search, hash } = window.location;
const location = `${pathname}${search}${hash}`;

const initialState = window.__INITIAL_STATE__;
const store = configureStore(initialState);



// calling `match` is simply for side effects of
// loading route/component code for the initial location
match({ routes, location }, () => {
render(
<Provider store={store}>
<Router routes={routes} history={createHistory()} />
</Provider>,
document.getElementById('app')
);
});

最佳答案

我帮助你解决了不和谐问题,但我想我也应该在这里发布答案。

如果您使用 babel6(而不是 babel5)并在组件中使用导出默认值,那么您需要将路由更新为以下内容:

getChildRoutes(location, cb) {
require.ensure([], (require) => {
cb(null, [
require('./UserProfile/UserProfileRoute.js').default,
require('./UserHome/UserHomeRoute.js').default,
require('./SneakerPage/SneakerPageRoute.js').default,
require('./Reviews/ReviewsRoute.js').default,
require('./Listings/ListingsRoute.js').default,
require('./Events/EventsRoute.js').default
])
})
}

有关更多详细信息,请参阅此 SO 讨论:Babel 6 changes how it exports default

关于reactjs - 使用webpack和react-router进行延迟加载和代码分割不加载,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34925717/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com