You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在现有Express服务器中集成Angular Universal实现服务端渲染

现有JavaScript Express服务集成Angular Universal步骤

第一步:生成Angular Universal编译产物

在你的Angular项目根目录执行ng add @nguniversal/express-engine,自动生成服务端渲染所需的AppServerModule、构建配置等文件。随后执行npm run build:ssr完成编译,编译后dist目录会得到两个核心产物:

  • 浏览器端静态资源包:默认路径为dist/{你的项目名称}/browser
  • 服务端渲染CommonJS格式bundle:默认路径为dist/{你的项目名称}/server/main.js
    官方生成的server.ts文件不需要用到,直接忽略即可。

第二步:现有Express服务安装依赖

在你的Express服务项目中执行以下命令安装必要依赖:

npm install @angular/ssr @angular/common @angular/core @angular/platform-server

如果你使用的是Angular 16及更早版本,将@angular/ssr替换为@nguniversal/express-engine即可。

第三步:修改Express服务代码

路由匹配顺序非常关键,必须按照「现有业务接口 -> 非Angular静态资源 -> Angular静态资源 -> SSR通配路由」的顺序编写,避免业务逻辑被SSR路由拦截。
完整示例代码如下:

const express = require('express');
// Angular 17+引入方式,Angular 16及以下改为 require('@nguniversal/express-engine')
const { ngExpressEngine } = require('@angular/ssr');
const { join } = require('path');
// 引入编译好的Angular服务端bundle,路径替换为你实际的产物路径
const { AppServerModule } = require('./dist/你的项目名称/server/main');

const app = express();
// Angular浏览器端静态资源目录路径,替换为你实际的产物路径
const browserDistPath = join(__dirname, 'dist/你的项目名称/browser');

// 配置Angular模板渲染引擎
app.engine('html', ngExpressEngine({
  bootstrap: AppServerModule
}));
app.set('view engine', 'html');
app.set('views', browserDistPath);

// ---------------------- 原有业务逻辑放在最前面 ----------------------
// 你的原有业务接口
app.get('/api/*', (req, res) => {
  // 原有逻辑不变
  res.json({ code: 0 });
});
// 其他非Angular静态资源托管,比如上传文件、后台系统静态页等
app.use('/upload', express.static(join(__dirname, 'upload')));
app.use('/admin', express.static(join(__dirname, 'admin-static')));

// ---------------------- Angular相关逻辑放在后面 ----------------------
// 托管Angular浏览器端静态资源(js、css、图片等)
app.get('*.*', express.static(browserDistPath, {
  maxAge: '1y'
}));
// SSR通配路由,处理所有未匹配到前面规则的请求
app.get('*', (req, res, next) => {
  // 如有特殊路由不需要走SSR,可在此处过滤直接返回静态index.html
  if (req.path.startsWith('/test-no-ssr')) {
    return res.sendFile(join(browserDistPath, 'index.html'));
  }
  res.render('index', { req, res });
});

// 原有启动逻辑不变
app.listen(3000, () => {
  console.log('服务启动在3000端口');
});

注意事项

  • 如果Angular项目中用到了window、document等浏览器专属API,需要提前做兼容处理:可通过isPlatformServer判断运行环境,避免服务端渲染时报错
  • 每次更新Angular项目代码后,都需要重新执行npm run build:ssr更新产物,再重启Express服务生效
  • 如需配置SSR缓存、请求透传等能力,可直接在res.render的第二个参数中传入自定义参数,在Angular服务端代码中通过REQUEST注入token读取

内容的提问来源于stack exchange,提问作者NeNaD

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.07 14:09:02