乐趣区

关于ssr:运行在-SSR-模式下的-Angular-应用的内存泄漏问题分析

运行在 SSR 模式下的 Angular 利用,为了防止服务器端和客户端两次调用同样的 API 引起屏幕的 Flickering 问题,通过都会应用 Angular TransferState 服务将信息从服务器发送到客户端,其工作原理如下图所示:

首先在应用程序 app.module.ts 中导入 BrowserTransferStateModule

import {BrowserModule, BrowserTransferStateModule} from '@angular/platform-browser';
imports: [BrowserModule.withServerTransition({appId: 'my-app'}),
  BrowserTransferStateModule,
  ...
]

而后在服务器端模块 app.server.module.ts 中导入 ServerTransferStateModule

import {ServerModule, ServerTransferStateModule} from '@angular/platform-server';
imports: [
  AppModule,
  ServerModule,
  ServerTransferStateModule,
  ...
]

咱们能够应用 makeStateKey 函数来创立一个键,以存储状态中的数据(将传递给浏览器)。应用 this.state.get 从状态中获取数据,并应用 this.state.set 设置状态中的数据。进行 API 调用时,应用之前调用 makeStateKey 创立的密钥将返回的数据存储在 Angular state 中。

采纳了 TransferState 服务的 Spartacus SSR 利用,在呈现内存透露时通常有下列体现:

  • 用户申请响应工夫减少
  • jsapps pods 频繁重启
  • 运行时呈现如下日志:

(1) SSR rendering exceeded timeout 3000, fallbacking to CSR for /xyz
(2) PM2 Process 0 restarted because it exceeds –max-memory-restart value (current_memory=4009730048 max_memory_limit=3865051136 [octets])
(3) Rendering of /xyz was not able to complete. This might cause memory leaks!

如果呈现了以上之一的症状,咱们能够应用 Dynatrace 进行内存透露起因剖析。

在 Dynatrace 中,能够从左侧导航菜单中的技术和过程选项和 Node.js 技术中找到每个 SSR pod。过程组将具备蕴含您的应用程序 SSR 的主文件的名称,通常是 main.js 或 server.js。单击后者将列出在指定工夫范畴内处于活动状态的 pod,容许咱们拜访任何单个 pod 的过程详细信息页面。

在 high level 层面,仅通过查看 Dynatrace 中的 V8 堆内存图表就能够对内存透露的可能性做出理智的判断。Node.js 中潜在内存透露的最显著迹象是:

  1. V8 堆内存呈现峰值(sharp spike)
  2. 每次 pod 重新启动后,内存占用图都会 再次 呈现峰值

通常状况下,如下图所示的锯齿模式 (saw tooth) 仿佛表明应用程序衰弱,因为假如内存中的每个开释都是因为垃圾收集而产生的。然而,如果您发现内存中的每个峰值之后都会有一个内存开释的行为,而该内存开释仅仅是因为 pod 的重启造成的,那么该利用很可能存在内存透露的问题。

如果咱们减少零碎的可用内存,然而 Dynatrace 里观测到的锯齿模式依然存在,这种性能更能成为该利用存在内存透露的无力证据之一。

退出移动版