Express:在子路由

时间:2017-09-05 16:51:57

标签: javascript node.js reactjs express webpack

我已经构建了一个带有Express后端和React前端的Web应用程序。

每当向Express服务器发出请求时,它首先检查URL是否与任何后端路由匹配,如果不匹配,它会将使用Webpack生成的React包发送到客户端(其中URL路由由React Router处理) )。

这适用于所有基本路线。但是,只要向子路径发出请求(例如/foo/bar),Express就会正确提供index.html,但似乎要从foo查找目标bundle.js ,在这种情况下是不受欢迎的行为,并导致错误,因为在那里找不到文件。对于JS文件,这可以通过使用相对路径来修复,但问题仍然存在于由Webpack处理的图像。

有人知道解决方案吗?

server.js:

server.listen(port, () => {
    // set up API routes
    server.use('/api/auth', require(...));
    server.use('/api/users', require(...));

    // serve public files (JavaScript bundle, images, etc.)
    server.use(express.static(path.join(__dirname, '../client', 'public')));

    // serve index.html on all other routes
    server.get('*', (request, response) => {
        response.sendFile(path.join(__dirname, '../client', 'public', 'index.html'));
    });
});

的index.html:

<!DOCTYPE html>

<html>
    <head>
        ...
    </head>

    <body>
        <div id="root"></div>
        <script src="/client-bundle.js"></script>
    </body>
</html>

React组件中图像导入的示例:

import someIcon from '../public/img/someIcon.svg';
...
<img src={someIcon}>

Webpack配置:

module.exports = {
    entry: './client/index.jsx',
    output: {
        path: path.join(__dirname, 'client/public'),
        filename: 'bundle.js'
    },
    module: {
        rules: [
            { test: /\.jsx?$/, loader: 'babel-loader', exclude: /node_modules/ },
            { test: /\.scss$/, use: ['style-loader', 'css-loader', 'sass-loader'] },
            { test: /\.(jpe?g|png|gif|svg)$/, loader: 'file-loader?name=img/[name].[ext]' }
        ]
    },
    resolve: {
        extensions: ['.js', '.jsx']
    }
};

我的文件结构:

/app
    /client
        /components
            /SomeComponent.jsx
        /index.jsx
        /public
            /index.html
            /bundle.js
            /img
                /someIcon.svg
    /server
        /server.js

1 个答案:

答案 0 :(得分:1)

您可以在webpack配置中设置服务器的公共路径。如果你设置公共路径,那么webpack将用该公共路径替换图像和其他文件的路径。在你的wepack中设置公共路径为

output: {
        path: path.join(__dirname, 'client/public'),
        publicPath: "http://localhost:3000/",
        filename: 'bundle.js'
    },

同样在您的文件加载器中,您正在设置name=img/[name].[ext]

因此,通过上述配置,您的图像路径将替换为

http://localhost:3000/img/someIcon.svg