配置Express为每个url发送index.html,以.css和.js结尾的url除外

Configure Express to send index.html for every url EXCEPT those ending in .css and .js

本文关键字:url css js 除外 结尾 html Express index 发送 配置      更新时间:2023-09-26

我是Express的新手,我正在尝试建立一个SPA,其中每个url都由index.html(Backbone)处理。

我希望每个url都发送index.html,除了/bundle.js和/style.css——或者更好的是,任何指示文件(以.xyz结尾)的url

我试过了:

app.get('*', function(req, res) {
    res.sendfile(__dirname+'/public/index.html');
};

但是它发送了带有index.html内容的bundle.js。我该怎么做?

我相信有两种方法可以解决这个目标,第一种可能更可取。如果您可以移动bundle.jsstyle.css,请将它们以及任何其他静态文件放在public目录中,并使用以下方法静态服务于public之外的所有文件:

app.use(express.static(__dirname + '/public'));
app.get('*', function(req, res){
  res.sendfile(__dirname + '/public/index.html');
});

这种方法更可取,因为当您在public目录中放置新的静态文件时,它将"正常工作"。然后,您应该能够在http://server:port/bundle.js(或适当的子文件夹,取决于您选择的层次结构)

或者,您可以保持文件结构不变,并使用定义路由的顺序来完成类似的行为,尽管它没有那么灵活,而且基本上是静态定义的:

app.get('/bundle.js', function(req, res){
  res.sendfile(__dirname + '/bundle.js');
});
app.get('/style.css', function(req, res){
  res.sendfile(__dirname + '/style.css');
});
app.get('*', function(req, res){
  res.sendfile(__dirname + '/public/index.html');
});

我设法用这种方式解决了它:

const getExtension = fileName => (
  fileName.substr(fileName.lastIndexOf('.') + 1)
)
app.get('*', ({ url }, res) => {
  let filePath
  if (['js', 'css', 'png', 'jpg'].includes(getExtension(url))) {
    filePath = __dirname + '/public/' + url
  } else {
    filePath = __dirname + '/public/' + url + '/index.html'
  }
  res.sendFile(filePath)
});