- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我按照教程将 Universal 集成到我们的 Angular 9 应用程序中。现在我们已经配置了 server.ts。
在每个教程中我都会看到这个:
// Example Express Rest API endpoints
// app.get('/api/**', (req, res) => { });
然后:
server.get(
'*.*',
express.static(distFolder, {
maxAge: '1y',
})
);
如果我们就这样保留它,我想每个请求都会被缓存,还有/api 的内容。这是正确的吗?我们的应用程序有很多“产品页面”,其中库存和价格可能会经常变化。因此,我们需要始终拥有新鲜的库存和价格。出于这个原因,我不会缓存从我们的 API 调用返回的服务器数据,这些 API 调用位于“/api/”路径(如果需要绝对路径,则为 https://api.my-app.com“)。保留上面写的所有内容应该缓存所有内容,如果我没看错,我直接在数据库里改了个价格做了个测试,我希望看到旧的,但不是这样的,我看到的总是新的。所以我怀疑缓存机制不起作用。而且当我浏览组件时,我继续看到每个 api 调用(未缓存)
谁能更好地解释一下这个机制?
关于此的另一个问题是:如果缓存有效,如何在 Node 中清除它? Node 在内存中缓存所有内容。我认为当我们停止 Node 时缓存会被清除。这样对吗?
这是我的包 json:
"scripts": {
"ng": "node --max_old_space_size=8192 node_modules/@angular/cli/bin/ng",
"start": "npm run ng -- serve",
"serve:server": "node ./dist-server/main.js",
"serve:server:debug": "node --inspect ./dist-server/main.js",
"start:server": "npm run build:server && node ./dist-server/main.js",
"start:server:debug": "npm run build:server && node ./dist-server/main.js --inspect",
"build": "npm run ng -- build",
"build:server": "ng run my-app:server:production",
"ssr:watch": "ng run my-app:serve-ssr:production",
"demo:ssr:watch": "ng run universal-demo:serve-ssr:dev",
"build-all": "npm-run-all build-production build:server-app:prod",
"start:express-server": "ts-node -P ./src/tsconfig.server.json ./server.ts",
"prerender": "ts-node -P ./server.tsconfig.json ./prerender.ts",
"prerender:debug": "ts-node -P ./server.tsconfig.json --inspect ./prerender.ts",
"test": "npm run ng -- test",
"lint": "npm run ng -- lint",
"e2e": "npm run ng -- e2e",
"analyze": "webpack-bundle-analyzer dist/stats.json",
"compodoc": "npx compodoc -p src/tsconfig.app.json",
"build:stats": "ng build --stats-json --prod",
"build-preprod": "ng build --configuration preprod --index=/src/index/preprod/index.html",
"build-production": "ng build --configuration production --index=/src/index/production/index.html",
"build-staging": "ng build --configuration staging --index=/src/index/staging/index.html"
}
这是我的 angular.json:
{
"$schema": "./node_modules/@angular/cli/lib/config/schema.json",
"version": 1,
"newProjectRoot": "projects",
"projects": {
"my-app": {
"root": "",
"sourceRoot": "src",
"projectType": "application",
"prefix": "app",
"schematics": {
"@schematics/angular:component": {
"style": "scss"
}
},
"architect": {
"build": {
"builder": "@angular-devkit/build-angular:browser",
"options": {
"aot": true,
"outputPath": "dist",
"index": "src/index.html",
"main": "src/main.ts",
"polyfills": "src/polyfills.ts",
"tsConfig": "src/tsconfig.app.json",
"stylePreprocessorOptions": {
"includePaths": ["src/assets/sass"]
},
"assets": [
"src/assets",
"src/favicon.ico",
"src/manifest.json",
"src/firebase-messaging-sw.js",
"src/main-sw.js",
"src/assets/js/intersection-observer.js"
],
"styles": [
"src/styles/styles.scss",
"src/styles/my-app.scss",
"node_modules/font-awesome/css/font-awesome.css"
],
"scripts": [],
"es5BrowserSupport": true
},
"configurations": {
"staging": {
"budgets": [
{
"type": "anyComponentStyle",
"maximumWarning": "6kb"
}
],
"optimization": true,
"outputHashing": "all",
"sourceMap": false,
"extractCss": true,
"namedChunks": false,
"aot": true,
"extractLicenses": true,
"vendorChunk": false,
"buildOptimizer": true,
"ngswConfigPath": "src/app/config/ngsw-config.json",
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.staging.ts"
}
],
"serviceWorker": true
},
"preprod": {
"budgets": [
{
"type": "anyComponentStyle",
"maximumWarning": "6kb"
}
],
"optimization": true,
"outputHashing": "all",
"sourceMap": false,
"extractCss": true,
"namedChunks": false,
"aot": true,
"extractLicenses": true,
"vendorChunk": false,
"buildOptimizer": true,
"ngswConfigPath": "src/app/config/ngsw-config.json",
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.preprod.ts"
}
],
"serviceWorker": true
},
"production": {
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.prod.ts"
}
],
"optimization": true,
"outputHashing": "all",
"sourceMap": true,
"extractCss": true,
"namedChunks": true,
"aot": true,
"extractLicenses": true,
"vendorChunk": false,
"buildOptimizer": true,
"ngswConfigPath": "src/app/config/ngsw-config.json",
"budgets": [
{
"type": "initial",
"maximumWarning": "2mb",
"maximumError": "5mb"
},
{
"type": "anyComponentStyle",
"maximumWarning": "6kb"
}
],
"serviceWorker": true
}
}
},
"serve": {
"builder": "@angular-devkit/build-angular:dev-server",
"options": {
"browserTarget": "my-app:build"
},
"configurations": {
"production": {
"browserTarget": "my-app:build:production"
}
}
},
"extract-i18n": {
"builder": "@angular-devkit/build-angular:extract-i18n",
"options": {
"browserTarget": "my-app:build"
}
},
"test": {
"builder": "@angular-devkit/build-angular:karma",
"options": {
"main": "src/test.ts",
"polyfills": "src/polyfills.ts",
"tsConfig": "src/tsconfig.spec.json",
"karmaConfig": "src/karma.conf.js",
"styles": ["src/styles.scss"],
"scripts": [],
"assets": ["src/favicon.ico", "src/assets"]
}
},
"lint": {
"builder": "@angular-devkit/build-angular:tslint",
"options": {
"tsConfig": ["src/tsconfig.app.json", "src/tsconfig.spec.json"],
"exclude": ["**/node_modules/**"]
}
},
"server": {
"builder": "@angular-devkit/build-angular:server",
"options": {
"outputPath": "dist-server",
"main": "server.ts",
"tsConfig": "src/tsconfig.server.json",
"stylePreprocessorOptions": {
"includePaths": ["src/assets/sass"]
}
},
"configurations": {
"dev": {
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.prod.ts"
}
],
"optimization": true
},
"production": {
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.prod.ts"
}
],
"optimization": true
}
}
},
"serve-ssr": {
"builder": "@nguniversal/builders:ssr-dev-server",
"options": {
"browserTarget": "my-app:build",
"serverTarget": "my-app:server"
},
"configurations": {
"production": {
"browserTarget": "my-app:build:production",
"serverTarget": "my-app:server:production"
}
}
},
"prerender": {
"builder": "@nguniversal/builders:prerender",
"options": {
"browserTarget": "my-app:build:production",
"serverTarget": "my-app:server:production",
"routes": ["/"]
},
"configurations": {
"production": {}
}
}
}
},
"my-app-e2e": {
"root": "e2e/",
"projectType": "application",
"prefix": "",
"architect": {
"e2e": {
"builder": "@angular-devkit/build-angular:protractor",
"options": {
"protractorConfig": "e2e/protractor.conf.js",
"devServerTarget": "my-app:serve"
},
"configurations": {
"production": {
"devServerTarget": "my-app:serve:production"
}
}
},
"lint": {
"builder": "@angular-devkit/build-angular:tslint",
"options": {
"tsConfig": "e2e/tsconfig.e2e.json",
"exclude": ["**/node_modules/**"]
}
}
}
}
},
"defaultProject": "my-app"
}
谢谢
最佳答案
以下代码适用于构建项目后位于 dist/browser
目录中的静态文件。这些主要是 JavaScript、CSS 和图像文件。 maxAge
将设置 Cache-Control header ,指示文件将被视为新鲜的最长时间。同样,这仅适用于在 dist/browser
中提供文件,这将永远改变。
server.get(
'*.*',
express.static(distFolder, {
maxAge: '1y',
})
);
包含以下代码只是作为如何将其他端点添加到 Express 服务器的示例:https://expressjs.com/en/guide/routing.html .它与缓存没有任何关系。
// Example Express Rest API endpoints
// app.get('/api/**', (req, res) => { });
以下代码是使用 Angular 应用程序呈现 HTML 响应的代码。默认实现中没有为此提供缓存,因为它会根据您应用中内容更改的频率而有所不同。
server.get('*', (req, res) => {
res.render(
indexHtml,
{
req,
providers: [{ provide: APP_BASE_HREF, useValue: req.baseUrl }]
});
});
这里有一些关于如何实现缓存的伪代码。 cache
变量可以是内存缓存,如 Redis或其他一些实现。
server.get('*',
// Middleware to check if cached response exists
(req, res, next) => {
const cachedHtml = cache.get(req.url);
if (cachedHtml) {
// Cache exists. Send it.
res.send(cachedHtml);
} else {
// Cache does not exist. Render a response using the Angular app
next();
}
},
// Angular SSR rendering
(req, res) => {
res.render(
indexHtml,
{
req,
providers: [{ provide: APP_BASE_HREF, useValue: req.baseUrl }]
},
(err: Error, html: string) => {
// Cache the rendered `html` for this request url to use for subsequent requests
cache.set(req.url, html);
res.send(html);
}
);
}
);
关于node.js - 如何在 Angular Universal 中配置缓存,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61939272/
我阅读了有关 JSR 107 缓存 (JCache) 的内容。 我很困惑:据我所知,每个 CPU 都管理其缓存内存(无需操作系统的任何帮助)。 那么,为什么我们需要 Java 缓存处理程序? (如果C
好吧,我是 jQuery 的新手。我一直在这里和那里搞乱一点点并习惯它。我终于明白了(它并不像某些人想象的那么难)。因此,鉴于此链接:http://jqueryui.com/sortable/#dis
我正在使用 Struts 2 和 Hibernate。我有一个简单的表,其中包含一个日期字段,用于存储有关何时发生特定操作的信息。这个日期值显示在我的 jsp 中。 我遇到的问题是hibernate更
我有点不确定这里发生了什么,但是我试图解释正在发生的事情,也许一旦我弄清楚我到底在问什么,就可能写一个更好的问题。 我刚刚安装了Varnish,对于我的请求时间来说似乎很棒。这是一个Magneto 2
解决 Project Euler 的问题后,我在论坛中发现了以下 Haskell 代码: fillRow115 minLength = cache where cache = ((map fill
我正试图找到一种方法来为我网络上的每台计算机缓存或存储某些 python 包。我看过以下解决方案: pypicache但它不再被积极开发,作者推荐 devpi,请参见此处:https://bitbuc
我想到的一个问题是可以从一开始就缓存网络套接字吗?在我的拓扑中,我在通过双 ISP 连接连接到互联网的 HAProxy 服务器后面有 2 个 Apache 服务器(带有 Google PageSpee
我很难说出不同缓存区域 (OS) 之间的区别。我想简要解释一下磁盘\缓冲区\交换\页面缓存。他们住在哪里?它们之间的主要区别是什么? 据我了解,页面缓存是主内存的一部分,用于存储从 I/O 设备获取的
1.题目 请你为最不经常使用(LFU)缓存算法设计并实现数据结构。 实现 LFUCache 类: LFUCache(int capacity) - 用数据结构的容量 capacity 初始化对象 in
1.题目 请你设计并实现一个满足 LRU (最近最少使用) 缓存 约束的数据结构。 实现 LRUCache 类: ① LRUCache(int capacity) 以正整数作为容量 capacity
我想在访问该 View 时关闭某些页面的缓存。它适用于简单查询模型对象的页面。 好像什么时候 'django.middleware.cache.FetchFromCacheMiddleware', 启
documents为 ExePackage element state Cache属性的目的是 Whether to cache the package. The default is "yes".
我知道 docker 用图层存储每个图像。如果我在一台开发服务器上有多个用户,并且每个人都在运行相同的 Dockerfile,但将镜像存储为 user1_myapp . user2 将其存储为 use
在 Codeigniter 中没有出现缓存问题几年后,我发现了一个问题。我在其他地方看到过该问题,但没有适合我的解决方案。 例如,如果我在 View 中更改一些纯 html 文本并上传新文件并按 F5
我在 Janusgraph 文档中阅读了有关 Janusgraph Cache 的内容。关于事务缓存,我几乎没有怀疑。我在我的应用程序中使用嵌入式 janusgrah 服务器。 如果我只对例如进行读取
我想知道是否有来自终端的任何命令可以用来匹配 Android Studio 中执行文件>使缓存无效/重新启动的使用。 谢谢! 最佳答案 According to a JetBrains employe
我想制作一个 python 装饰器来内存函数。例如,如果 @memoization_decorator def add(a, b, negative=False): print "Com
我经常在 jQuery 事件处理程序中使用 $(this) 并且从不缓存它。如果我愿意的话 var $this = $(this); 并且将使用变量而不是构造函数,我的代码会获得任何显着的额外性能吗?
是的,我要说实话,我不知道varnish vcl,我可以解决一些基本问题,但是我不太清楚,这就是为什么我遇到问题了。 我正在尝试通过http请求设置缓存禁止,但是该请求不能通过DNS而是通过 Varn
在 WP 站点上加载约 4000 个并发用户时遇到此问题。 这是我的配置: F5 负载均衡器 ---> Varnish 4,8 核,32 Gb RAM ---> 9 个后端,4 个核,每个 16 RA
我是一名优秀的程序员,十分优秀!