为了账号安全,请及时绑定邮箱和手机立即绑定

我如何通过一个配置更改让Node.js提速54倍

我是如何通过策略调试让Node.js身份验证速度提高54倍的

照片由Nubelson Fernandes拍摄于Unsplash

作为一名资深后端工程师,我最近解决了一个棘手的性能问题,这个问题出现在一个Feathers.js应用程序中。最初只是一个例行调查,结果却变成了一次令人着迷的调试之旅,最终取得了惊人的98%性能提升。

13秒登录的谜团

在性能监控期间,我发现了令人担忧的问题——我们的登录API耗时达到13秒。通常来说,大多数认证请求只需几毫秒。显然出问题了。

掉进调试兔子洞:深入探索

应用程序使用了Feathers.js。Feathers.js包含了几层抽象概念,这可能让调试变得困难。

我是从在整个认证过程中添加了详细的时间记录开始,

    async 比较密码(entity: any, password: string) {  
        console.time('比较密码');  
        const 结果 = await bcrypt.compare(密码, hash);  
        console.timeEnd('比较密码');  
        return 结果;  
    }

日志显示了一个有趣的发现——仅比较密码就花费了12.15秒。这是怎么回事?

检查我们数据库中的密码哈希为我们提供了关键线索:

    $2a$17$KVFGQnjIzkxy/Le0EQdW1u2Ht0hNqx4dWyvAvaf85AFBWlK9Dmh1e

那正是确凿的证据。Bcrypt 的实现过程远远超出大多数应用程序推荐的一般 8 到 12 轮。

解决方案:性能配置

修复需要理解Feathers.js如何对密码哈希进行配置。我没有采用默认实现,而是增加了明确的配置:

    // config/default.json
    {
      "身份验证": {
        "本地": {
          "哈希": 8,
          "密码字段": "password"
        }
      }
    }
    // authentication.ts  
    const authConfig = app.get('authentication');  
    const hashRounds = authConfig.local.hash;  
    authConfig.local.hash = async (password: string) => {  
        return bcrypt.hash(password, hashRounds);  
    };  
    app.set('authentication', authConfig);
深入了解核心领域

真正的突破来自于深入研究Feathers.js的核心认证代码。我没有把它当作黑盒子,而是深入研究了它的内部实现。

    // Inside feathers-authentication-local/lib/hooks/hash-password.js  
    var hashPw = options.hash || _hash2.default;

这让我决定自定义一套身份验证策略,以此来扩展核心功能的范围。

    class 自定义本地策略 extends 认证基础策略 {  
        get 配置() {  
            const authConfig = this.认证.配置;  
            const config = Object.assign(super.配置 || {}, {});
{  
    hashSize: 8,  // 自定义哈希大小  
    service: authConfig.service,  
    entity: authConfig.entity,  
    // ... 其他配置项  
}  

通过理解并自定义核心认证机制,而不是只是使用它,我能够做到以下几点:

  1. 实现对哈希过程的精确控制
  2. 保持框架的兼容性
  3. 确保我们的优化不会影响其他认证功能的正常运行

深入调试的方法通常能带来最有效的解决办法,往往超越表面配置,直达核心实现。

结果如下

影响是立即且显著的:

  • 原来登录时间:13,000毫秒(13秒)
  • 现在登录时间:240毫秒
  • 性能改进:98.15%
  • 速度现在提升54倍

下一步:处理现有用户

虽然新密码现在采用了8轮哈希,现有用户仍然使用更长轮数的哈希密码。这意味着他们登录时仍需等待13秒,直到他们修改密码。

我们不能自动更新现有的哈希值,这是出于安全考虑——我们从不存储原始密码,只存储密码的哈希值。这意味着用户需要再次提供他们的密码,以便我们生成一个新的带有8轮加密的哈希。

技术要点回顾

这次经历让我更深刻地记住了几个重要的教训:

  1. 默认配置不一定总是最适合您的需求
  2. 理解框架如何处理安全等功能至关重要
  3. 正确的仪器化是识别瓶颈的关键
  4. 有时候最简单的解决方案能带来最显著的改进

有兴趣深入了解技术细节或讨论类似性能优化挑战的朋友,欢迎随时联系我。

高级后端开发工程师,构建可扩展系统,同时保持代码库的整洁。

LinkedIn: Ali Fadda GitHub: alifadda-me 邮箱: contact@alifadda.me 联系邮箱: silvertechguy@gmail.com

点击查看更多内容
TA 点赞

若觉得本文不错,就分享一下吧!

评论

作者其他优质文章

正在加载中
  • 推荐
  • 评论
  • 收藏
  • 共同学习,写下你的评论
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦
今天注册有机会得

100积分直接送

付费专栏免费学

大额优惠券免费领

立即参与 放弃机会
意见反馈 帮助中心 APP下载
官方微信

举报

0/150
提交
取消