关于hexo文章数量过多导致编译内存不足的解决

前言

文章数量过多, 执行hexo g渲染时报错, 如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
<--- Last few GCs --->

[3128:0x102d59000] 3164514 ms: Mark-sweep 9136.8 (9211.6) -> 9124.1 (9213.4) MB, 4252.7 / 0.0 ms (average mu = 0.099, current mu = 0.022) allocation failure scavenge might not succeed
[3128:0x102d59000] 3168989 ms: Mark-sweep 9138.4 (9213.5) -> 9127.1 (9215.3) MB, 4402.9 / 0.0 ms (average mu = 0.056, current mu = 0.016) allocation failure scavenge might not succeed


<--- JS stacktrace --->

==== JS stack trace =========================================

0: ExitFrame [pc: 0x1009d5fd9]
1: StubFrame [pc: 0x1009d6ead]
Security context: 0x1032be4808d1 <JSObject>
2: formatAttrs [0x10326c532831] [/node_modules/dom-serializer/index.js:~22] [pc=0x13101fad4423](this=0x1032ffa02da1 <JSGlobal Object>,0x10333f9ef9e1 <Object map = 0x1032643d71d9>,0x1032fa08d281 <Object map = 0x1032643ffae9>)
3: /* anonymous */ [0x103256ce9201] [/Use...

FATAL ERROR: Ineffective mark-compacts near heap limit Allocation failed - JavaScript heap out of memory
1: 0x1011c9b35 node::Abort() (.cold.1) [/usr/local/bin/node]
2: 0x10009ca99 node::Abort() [/usr/local/bin/node]
3: 0x10009cbff node::OnFatalError(char const*, char const*) [/usr/local/bin/node]
4: 0x1001ddb37 v8::Utils::ReportOOMFailure(v8::internal::Isolate*, char const*, bool) [/usr/local/bin/node]
5: 0x1001ddad7 v8::internal::V8::FatalProcessOutOfMemory(v8::internal::Isolate*, char const*, bool) [/usr/local/bin/node]
6: 0x1003659d5 v8::internal::Heap::FatalProcessOutOfMemory(char const*) [/usr/local/bin/node]
7: 0x10036724a v8::internal::Heap::RecomputeLimits(v8::internal::GarbageCollector) [/usr/local/bin/node]
8: 0x100363c7c v8::internal::Heap::PerformGarbageCollection(v8::internal::GarbageCollector, v8::GCCallbackFlags) [/usr/local/bin/node]
9: 0x100361a7e v8::internal::Heap::CollectGarbage(v8::internal::AllocationSpace, v8::internal::GarbageCollectionReason, v8::GCCallbackFlags) [/usr/local/bin/node]
10: 0x10036d94a v8::internal::Heap::AllocateRawWithLightRetry(int, v8::internal::AllocationType, v8::internal::AllocationOrigin, v8::internal::AllocationAlignment) [/usr/local/bin/node]
11: 0x10036d9d1 v8::internal::Heap::AllocateRawWithRetryOrFail(int, v8::internal::AllocationType, v8::internal::AllocationOrigin, v8::internal::AllocationAlignment) [/usr/local/bin/node]
12: 0x10033b60a v8::internal::Factory::NewFillerObject(int, bool, v8::internal::AllocationType, v8::internal::AllocationOrigin) [/usr/local/bin/node]
13: 0x10068cb88 v8::internal::Runtime_AllocateInYoungGeneration(int, unsigned long*, v8::internal::Isolate*) [/usr/local/bin/node]
14: 0x1009d5fd9 Builtins_CEntry_Return1_DontSaveFPRegs_ArgvOnStack_NoBuiltinExit [/usr/local/bin/node]
zsh: abort hexo g

这是由于node.js内存限制导致的, 默认堆内存上限为1024MB

解决方法也很简单, 那就是加大堆内存上限, 有四种方案

解决方案

第一种 临时性配置

比如用以下命令来替代hexo g:

1
node --max-old-space-size=16384 ./node_modules/hexo/bin/hexo generate

这里--max-old-space-size属性的数值可以自定义, 我这里选择的是16G, 你也可以设置为8G, 也就是--max-old-space-size=8192, 以此类推

第二种 系统级全局配置

修改电脑上的node配置文件

  1. 第一步 打开launchd.conf配置文件

    1
    2
    # 编辑 Node.js 全局启动配置
    sudo vim /etc/launchd.conf
  2. 添加以下内容

    1
    setenv NODE_OPTIONS "--max-old-space-size=16384"
  3. 运行配置

    1
    2
    sudo launchctl load /etc/launchd.conf
    reboot # 重启生效
  4. 验证是否生效

    1
    echo $NODE_OPTIONS  # 应显示 --max-old-space-size=8192

系统级配置, 针对所有用户生效

内存大小的设置需要根据自己电脑的实际情况来定, 避免设置过高 从而导致导致系统整体性能下降

关于Mac平台的更新

由于 /etc/launchd.conf在新版macOS 中已被弃用,推荐使用以下方式:

  1. 创建或修改 launchd plist 文件(系统级)

    1
    sudo nano /Library/LaunchDaemons/com.custom.node.env.plist
  2. 添加内容:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    <?xml version="1.0" encoding="UTF-8"?>
    <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
    <plist version="1.0">
    <dict>
    <key>Label</key>
    <string>com.custom.node.env</string>
    <key>ProgramArguments</key>
    <array>
    <string>/bin/launchctl</string>
    <string>setenv</string>
    <string>NODE_OPTIONS</string>
    <string>--max-old-space-size=4096</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    </dict>
    </plist>
  3. 加载配置:

    1
    sudo launchctl load /Library/LaunchDaemons/com.custom.node.env.plist

第三种 用户级配置

通过修改环境变量的方式

  1. 编辑 shell配置文件

    1
    2
    3
    nano ~/.zshrc  # macOS Catalina 及以后版本
    # 或
    nano ~/.bash_profile # macOS Catalina 之前版本
  2. 添加以下行

    1
    2
    # 设置 Node.js 内存限制
    export NODE_OPTIONS="--max-old-space-size=4096"
  3. 使配置生效

    1
    source ~/.zshrc  # 或 source ~/.bash_profile

该配置仅对当前用户生效, 适合用户配置隔离

第四种 项目级配置(更安全)

Hexo 项目的 package.json中修改scripts

1
2
3
4
"scripts": {
"build": "NODE_OPTIONS='--max-old-space-size=8192' hexo generate",
"serve": "NODE_OPTIONS='--max-old-space-size=8192' hexo server"
}

之后始终使用:

1
npm run build  # 代替 hexo generate

这算是一种一劳永逸的方案, 哪怕更换电脑也不怕, 而且进行了项目隔离, 不会影响到其他nodejs工程, 缺点是如果多个工程需要配置, 则得挨个添加

注意事项

如果运行后进程被终止, 比如报错:

1
zsh: killed     node --max-old-space-size=16384 ./node_modules/hexo/bin/hexo generate

主要原因是没有足够的物理内存 + 交换空间(swap)来满足需求,

首先运行top -o mem指令检查内存占用:

image-20250910100621554

随着node编译的进行, 我们会发现它的占用内存指标在不断上升,

iShot_2025-09-10_10.08.47

此时我们可以考虑通过关闭其他应用来给node足够的空间

本文为作者原创 转载时请注明出处 谢谢

乱码三千 – 点滴积累 ,欢迎来到乱码三千技术博客站

0%