Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Vue SSR 内存泄漏问题 #32

Open
yinxin630 opened this issue Dec 26, 2019 · 0 comments
Open

Vue SSR 内存泄漏问题 #32

yinxin630 opened this issue Dec 26, 2019 · 0 comments
Labels

Comments

@yinxin630
Copy link
Owner

首先要明确的是, SSR 时只会执行同步的代码, 对于异步调用, 代码会执行但是不会等待完成. 对于 vue 组件, 仅执行到第一次 render 结束, 在 render 之前的阶段会执行到, 而之后的就不会. 之前的阶段包括 data 初始化、beforeCreate()、created()

在这些代码中, 务必小心不要造成内存泄漏

产生内容泄漏的常见情况

1. 使用全局变量

例如

function doSomething() {
    a = 1;
}
doSomething();

a 被错误的定义为全局变量, 在 node 应用周期内将一直存在, 始终不会释放

可以用 eslint 避免这种错误定义全局变量的情况

2. setInterval / setTimeout

var a = 1;

setInterval(() => {
    connsole.log(a);
}, 1000);

setTimeout(() => {
    connsole.log(a);
}, 1000000) // 长时间不结束

如果 setInterval / setTimeout 内包含对上层作用域变量的引用, 那么该变量将无法释放

setInterval 定时器如果没有关闭逻辑的话, 将会一直触发. 并且每一次 SSR 过程都会新注册一个定时器

setTimeout 定时器虽然会在触发后退出, 接触对变量的引用, 但是通常不会立刻触发 GC, 该块内存仍会保留不定时间

因为 SSR 不等待异步结果, 所以最好在 SSR 时就别调用定时器

3. 闭包

闭包的情况会复杂一些, 并且通常难以定位

比如这个例子

var theThing = null;
var replaceThing = function () {
    var originalThing = theThing;
    var unused = function () {
        if(originalThing) {}
    };
    theThing = {
        longStr: Date.now() +  Array(1000000).join('*'),
        someMethod: function () {}
    };
};

replaceThing();
replaceThing();
replaceThing();
... // call many times

思考下为什么会产生内存泄漏

在编写闭包时, 务必要注意变量的作用范围

4. 缓存

简单的使用 js 变量做缓存也可能造成内存泄漏

var cache = {}
function setCache(key, value) {
    cache[key] = value;
}

要注意及时将不再需要的内容释放掉

如何排查内存泄漏

内存快照

  1. heapdump 记录内存快照
  2. Chrome Devtool Memory 分析内存快照

用法参考 https://www.bookstack.cn/read/node-in-debugging/2.2heapdump.md

实时内核性能监控分析工具

国人开发的 easy-monitor

用法参考 https://github.com/hyj1991/easy-monitor#ii-%E5%BF%AB%E9%80%9F%E5%BC%80%E5%A7%8B

@yinxin630 yinxin630 added the vue label Dec 26, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

1 participant