我正在努力使服务器端渲染和Service Worker在服务器端进行协作。
有关本地主机的信息->运行中
这按预期工作。服务人员会在每次更新时工作并更新我的应用程序。此外; curl localhost:8082
向我发送了我的信息。
我使用以下命令启动我的应用程序:npm run ssr
"ssr": "npm run build:ssr && npm run serve:ssr",
"build:ssr": "npm run build:client-and-server-bundles",
"serve:ssr": "node dist/server.js",
"build:client-and-server-bundles": "ng build --prod && npm run webpack:server",
"webpack:server": "webpack --config webpack.server.config.js --progress --colors"
有关生产的信息->不起作用
网站通过HTTPS:https://airdropers.io 网站进程正在关闭的端口上运行,并且HAPROXY将流量从443重定向到Web服务器的端口
在Web服务器日志上可见的问题:无法订阅通知 错误:此浏览器禁用或不支持服务人员
其他信息:
本地主机上的节点js和生产版本相同:v9.0.0 我通过以下过程构建生产:
更新23/02/2019
我现在有了更深刻的理解。 我的问题是,我使用诸如“ node dist / server.js”之类的节点命令来启动SSR / PWA服务器。
据我了解,“ node dist / server.js”不适用于Service Worker(PWA) 我引用(https://angular.io/guide/service-worker-getting-started)
由于服务不能与服务人员一起使用,因此必须使用 单独的HTTP服务器以在本地测试您的项目。您可以使用任何 HTTP服务器。下面的示例使用npm中的http-server软件包。 为了减少冲突的可能性并避免陈旧 内容,在专用端口上测试并禁用缓存。
我无法使用http-server dist/browser
进行启动,因为我将失去SSR功能。
如何启动PWA / SSR服务器?
我应该使用什么命令?
我该怎么做?
更新24/02/2019
如@GökhanKurt所述,服务工作者无法与我的SSR服务器正常工作。 我需要SEO的SSR,也需要服务人员的浏览器推送通知。 我必须使用什么解决方案来处理浏览器用户推送通知?第三方库,例如One Signals?
任何想法建议都将受到欢迎,以帮助我完成这项工作。 谢谢你的支持, 亚历克斯
答案 0 :(得分:3)
它实际上根本与您的服务器无关。问题是,尝试在服务器端注册Service Worker,这不受支持。您可以做的是使服务人员在客户端注册。
我没有尝试过,但这可能对您有用。您需要在body
中index.html
的末尾放置一个单独的脚本,以便在浏览器上运行:
<script>
if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('/ngsw-worker.js');
}
</script>
请注意,这只会为您提供Service Worker的基本缓存功能,并且可能不适用于SwPush
或SwUpdate
。您可以检查服务工作者模块在here内部的工作方式。
您应该知道的另一件事是,服务工作者实际上不适合SSR应用程序。生成的ngsw.json
文件不会包含您拥有的所有页面。您将不得不手动修改此文件,或者将其作为静态文件使用,而不是将其动态创建。
缓存所有页面不是您想做的事情(除非页面内容是静态的)。因为由于您不在客户端执行XHR请求,所以缓存的页面将始终显示相同的内容。例如,如果为客户端缓存了主页,则该客户端将始终看到同一页面,而不管预期的动态内容如何。
这时,您应该考虑为什么同时需要SSR和Web APP。如果您需要SSR进行SEO,则不需要软件。当用户代理属于爬虫时,只需执行SSR,而当客户端是普通用户时,则提供动态角度服务。
如何根据用户代理切换请求
这是我的想法,我不知道是否有人这样做。但从理论上讲,它应该起作用。
首先,您必须使用服务器端和客户端渲染配置将应用程序构建到两个不同的目录(在我的示例中为DIST_FOLDER/ssr
和DIST_FOLDER/csr
)。您可以从SSR中排除软件。您可以照常在CSR中使用SW。
我发现this package可以检测爬网程序/漫游器用户代理。对于express和Angular,您可以像这样使用它:
app.get('*', (req, res) => {
var CrawlerDetector = new Crawler(req)
// check the current visitor's useragent
if (CrawlerDetector.isCrawler())
{
// render the index html at server side
res.render(path.join(DIST_FOLDER, 'ssr', 'index.html'), { req });
}
else {
// serve static index.html file built without SSR and let the client render it
res.sendFile(path.join(DIST_FOLDER, 'csr', 'index.html'));
}
});
实施此操作后,您可以通过将用户代理更改为写为here(即使用Postman)的用户代理来调试应用程序,以查看其是否正常运行。
答案 1 :(得分:1)
通过对 #13351 的一些“不错的”解决方法,在 main.browser.ts
中几乎没有变化就可以在Angular 10
上工作
// Workaround for service worker, issue #13351.
document.addEventListener('DOMContentLoaded', () => {
platformBrowserDynamic()
.bootstrapModule(AppModule)
.then(() => {
if ('serviceWorker' in navigator && environment.production) {
navigator.serviceWorker.register('./ngsw-worker.js');
}
})
.catch((err) => console.error(err));
});
在 ngsw-config.json
中,我编辑了 index
以引用 index2.html
而不是 index.html
。在我的情况下,需要在 Firebase
/NestJS
根 (/
) 路径上正确呈现 SSR。
ngsw-config.json
{
"$schema": "../../node_modules/@angular/service-worker/config/schema.json",
"index": "/index2.html",
...
}
当在 prod
中使用 Chrome DevTools
标志运行时 -> Application
-> Service Workers
可以看到它。 View Page Source
显示 SSR。我还可以通过 Chrome 在我的桌面上添加安装应用程序。除此之外,该应用程序可以离线工作。均通过移动浏览器和桌面应用进行。
不知道为什么没有弹出默认的移动通知,即 Add to home screen
。
答案 2 :(得分:0)