2019 年,19 种方法让自己成为更好的 Node.js 工程师

avatar
花呗借呗前端团队 @蚂蚁集团

原文作者:Yoni Goldberg

译者:UC 国际研发 Jothy

写在最前:欢迎你来到“UC国际技术”公众号,我们将为大家提供与客户端、服务端、算法、测试、数据、前端等相关的高质量技术文章,不限于原创与翻译。

编者按:文中作者为大家提供了19种方法,大多数方法后面都提供了例子,如果你对这些例子感兴趣,请直接查看英文原文,并访问例子中的链接。

简介

我已经汇集了 19 项 2019 年可能有价值的技能和主题。请别为难我 - 我和大多数开发人员一样,不可能熟悉每一个主题。 这些只是我所关注的令人兴奋的事情,JavaScript 的视野永无止境。

我叫 Yoni Goldberg,是一名独立的 Node.js 顾问,也是《Node.js 最佳实践》的合著者。 我与美国,欧洲和以色列的客户一起研究他们的 Node.js 应用。 我的服务包括代码、应用程和架构审查、测试和 CI、高级培训课程以及其他服务。 你可以关注我的推特(https://twitter.com/goldbergyoni)。

1. 使用类型(type)和模式(schema)。 TypeScript 是 2019 年的极佳选择

事实证明,以无类型方式编码会适得其反,并且容易出错(参见研究)。 这并不意味着你必须一直使用严格类型的语法,而是通过使用 JSON Schema(或 Joi)验证你的实体/模型来选择你想要的原理图代码程度,用静态类型来注释原生 JS( 请参阅 Facebook Flow)或持续使用强类型语法如 TypeScript。 后者在 2018 年取得了显著的发展势头,似乎已成为 Node 领域的共识。 如果你计划使用 TypeScript,先问问自己,你的用法是否不仅仅是类型(Typing)功能,否则使用接口和抽象类会把你带入一个你从未尝试过的范例。

参考链接:

  • 研究地址:http://ttendency.cs.ucl.ac.uk/projects/type_study/documents/type_study.pdf

  • JSON 模式:https://www.npmjs.com/package/jsonschema

  • Joi:https://www.npmjs.com/package/joi

  • Facebook Flow:https://github.com/facebook/flow

例子:

  • 使用 JSON Schema 的显式模型架构:https://www.npmjs.com/package/jsonschema

  • 使用 Facebook Flow 静态输入原生 JS:https://github.com/facebook/flow

  • 使用 Typed 语法 TypeScript:https://www.typescriptlang.org/

2. 丰富你的 Linters

Linters 是免费的午餐,通过 5 分钟的设置你可以免费获得一个自动驾驶员来保护你的代码并在输入时监测重大问题的发现。 linting(化妆棉)与 cosmetics(化妆品)相关的日子已经一去不复返了(没有分号!)。 如今,Linters 可以捕获严重的问题,例如错误未正确抛出,丢失信息,Promise 永不 resolve,以及其它你从未想在代码中看见的痛点。

例子:

  • eslint-plugin-chai-expect 可以发现没有断言的测试

  • eslint-plugin-promise 可以发现未 resolve 的 Promise(你的代码永远不会继续)

  • eslint-plugin-security 可以发现可能用于 DOS 攻击的正则表达式

3. 多一点 Java,少一点 Ruby - 加深你的架构知识

Node.js 生态系统的架构和设计知识很少,大家都在讲微服务,但只谈了一些内部结构。而大多数应用和示例都是 MVC 概念和 Ruby 的其他可疑模式。这有什么问题?例如,MVC 是为服务内容构建的,并且是构建健壮后端的一种令人印象深刻的技术(Uncle Bob:“MVC 是一种传递机制,而不是应用架构”)。你真的可以描述整个业务逻辑、规则、数据访问、与 控制器和模型中的其他微服务的通信吗?有关其他设计问题和可能的补救措施,请参阅下面的示例。

我绝对不建议使用沉重的 Java/Spring 模式(我们来到 Node 领域是有原因的,不是吗?:)),只是挑选一些提供超值而不牺牲应用简单性的想法。

例子:

  • 你是否阅读过我的《Node.js 最佳实践》第 1 部分 - 架构?

  • 避免使用 Express 对象扰乱你的业务逻辑,阅读有关域驱动设计的内容(请参阅此新颖书籍的缩短版本)和 Hexagonal 架构

  • 将逻辑和数据访问代码混合在一个类中(Active Record 模式 - 在使用 Mongoose 和 Sequelize 的开发人员中非常流行)很容易导致更难测试的膨胀对象。 请考虑使用数据映射器模式。

  • 浏览一下这个实现领域驱动设计和干净架构的优秀 Node.js 样板代码

4. 规划如何利用异步 Hook 来获得更好的跟踪和上下文

单线程模型有一个主要缺点 - 请求丢失上下文:当它们流经多个文件并执行异步操作时,变量在其整个生命周期中不会被保留。为什么这很痛苦呢?例如,开发人员通常希望在每个日志中包含唯一标识符,以便稍后可以关联同一请求的所有日志 - 这在 2018 年不是很容易。2019 带来了新的亮点,异步 hooks 正是其中之一(不是全新的但很快就会退出实验模式)。简单地说,这是一种在异步操作开始和结束时随时注入自定义代码的机制。鉴于此,可以关联同一请求的所有代码并保留上下文。这为许多自定义程序包奠定了基础,这些程序包将 Node 的跟踪和上下文功能提升到了一个新的水平。

例子:

  • cls-hooked 允许在整个请求生命周期中共享变量和上下文

  • Jaeger 客户端将可视化整个系统的请求流,甚至是微服务和服务器(开放跟踪标准的一部分,需要专用服务器来记录所有活动)

  • 了解异步 hook 机会以及如何对其进行编码。由 @guysegev 提出

5. 了解最新的 Serverless 功能:它已经准备好在强大的基础设施领域展开激战(Kubernetes 杀手?)

注意:FaaS 和 Serverless 这两个词在这里可以互换使用,尽管它们并不完全相同。实际上,我指的是云供应商 FaaS 服务,如 Lambda 和 Google Functions。

最初,FaaS 用于开发微任务,而不是用于强大的“微服务”应用。随着他们的受欢迎程度越来越高,云供应商的胃口越来越大,很快就出现了新的功能。FaaS 在 2019 年突然出现,它似乎是一个强大应用的基础设施。它现在可以与 Kubernetes 竞争并提供大型应用程序吗?有些人认为 Serverless 和 Faas 是正交技术,但实际上 2019 年的每一个新的云应用都必须三选一(实际上每个云供应商 UI 上都会显示这个选择):(1)裸机实例,如 EC2 或 GCP 计算( 2)Kubernetes 或(3)FaaS。因此,能够比较 K8S 与 FaaS/Serverless 并告知后果成为强制性设计技能。

附:以下示例仅为方便起见与 AWS 相关。

例子:

  • AWS Lambda SAM 工具允许在本地定义和运行 FaaS

  • AWS Lambda 现在支持灰度部署!

  • AWS Lambda 层允许在多个 FaaS 之间重用逻辑(模拟典型微服务的域/业务逻辑层)

6. 了解即将支持的最新 JavaScript 功能

我不是追逐每一种语言新功能的狂热粉丝,有时这些闪亮的玩具会违背代码的简单性。 一些非常有价值的 Javascript 功能不时会出现(比如两年前 async/await 的介绍),所以可以了解 TC39 的提议和 node.green 以找到适合你编码风格的有吸引力的新功能。

例子:

  • Class 层面字段位于第 3 阶段(最后阶段),并可能在 2019 年支持

  • BigInt 处于第 3 阶段(最后阶段),在与其他产生巨大数字的微服务,机器或数据仓库进行交互时可能会有所帮助

  • 异步迭代器(Matt Krick)和 †promise - 终于已经支持,如果你没用过,那么值得一试

7. 熟悉至少一种 API 技术。 GraphQL 是 2019 年的不错选择

REST 风格的 API 非常契合它的构建初衷:可以很好地控制实体的修改和查询。你有财务记录系统吗?你可能希望设计非常严格的端点,即单个显式数据模型。然而,在其他非常常见的用例中,REST 风格确实不足,比如执行可能返回不同数据集的类似查询,低带宽网络决定最小化 API 负载,强调速度的机器到机器通信,仅举几例。你应该换一个吗?绝对不是,只是混用一下别的。 API 不是你的架构,它们只是应用程序的一个端口(即入口点),并且多个 API 样式可以轻松共存,甚至在像 Express 这样的单一 Web 框架之上。

那么要学哪一个?你最好的选择可能是 GraphQL,它直接就是主流。它的生态系统已经非常成熟,它可以提供非常流行的用例,如动态搜索和分层数据源。另一方面,Grpc 仍然是一种适合服务器到服务器通信用例的小众技术,你可以获得最小的开销(例如,Pub-sub/消息队列系统)。

例子:

  • 对比学习很棒 - REST vs Graph vs grpc

  • 浏览 GraphQL,Node&Express 教程

  • 观看简短的 YouTube(11分钟) - 什么是 GraphQL?

8. 超越单元和集成测试 - 使用全新测试技术丰富你的测试产品组合

你熟悉测试金字塔,单元,集成和端到端测试了?很棒,这些是成功测试策略的基础。然而,在过去 10 年中,开发世界经历了巨大的变化,但测试模型保持不变,我们好奇如何测试像微服务、丰富的前端和 Serverless 这样的东西。一些现代技术与传统堆栈相辅相成,有时甚至可以替换它,以实现 ROI 更好的更精简的测试策略。

例子:

  • 消费者驱动合约可以防止微服务之间或你与 API 消费者之间的问题

  • 快照测试不仅可以用于 UI,还可以用于防止 API 回归

  • 组件测试是微服务测试的均衡方法

  • 请参考我的 YouTube 视频 “Beyond Unit Tests:5 Shiny Node.JS Test Types(2018)”

视频:Yoni Goldberg 的 5 项闪亮测试技术

https://www.youtube.com/watch?v=-2zP494wdUY&feature=youtu.be

9. 使你的监控与 SRE/DevOps 最佳实践保持一致

2019 年,即使是一个中型应用也可能由数十个物理移动部件构成,并且应该非常谨慎地立于这个“大型管弦乐队”之上。然而,大多数开发者没有花功夫学习监控和告警课程,各路大牛十分乐意教授这门课。例如,开发人员通常会优先考虑并专注于 CPU 和内存等内部硬件指标,而不是从直接影响最终用户的指标开始,例如错误率或延迟(“我称之为基于症状的监控”,来自'我的警示哲学')。那些面向客户的指标也被称为“黄金信号”,而在 2019 年,也许你希望由此开始并采用类似的最佳实践。

例子:

  • 了解 4 个监测'黄金信号'

  • 阅读《Google Site 可靠性工程》,或者至少阅读有关监控的章节

  • request-stats 包也许有助于你提取这些面向客户的指标,以便与监控系统共享

10. 像攻击者一样思考:通过学习攻击工具和技术来提高安全级别

如果你不能像攻击者那样思考,你就不能像防守者一样思考。2019 年,你不该将防御工作外包给第三方公司或仅依靠静态安全扫描程序:各种攻击的数量是压倒性的(开发管道和 NPM 是最新趋势),应用更改的速度是难以控制的 - 在开展安全研讨会两天后,团队可以添加几个新的 AWS 服务,数据库类型和新的 IAM 角色......因此,隐藏的开发者成为最大的威胁,教育他们似乎是最终的补救措施。你必须将安全 DNA 植入到你和你的团队中,并且谨慎进行所有操作。

一旦你开始这么做了,事实会证明并没有那么可怕。只需熟悉常见的攻击类型和工具,绘制应用架构和流程,并思考如何攻击它。慢慢地在不知不觉中,你将在每个设计决策和每一行代码中开始考虑安全性。

例子:

  • 尝试 OWASP ZAP - 一款丰富的评估和渗透工具,甚至允许新手探索应用的安全级别

  • 阅读我的 Node.js 安全最佳实践列表,其中包含 23 个以上的攻击想法,包括 JavaScript 代码示例

  • 进行每月威胁分析会议,让你的团队试着查看应用设计并提出攻击。听起来很无聊?不一定,如果你把它游戏化,奖励找到漏洞的成员,或者成立两个相互竞争的组,一组设计模块,一组找漏洞

11. 制定包更新策略。 2018 年吸取的教训:过早更新很危险

团队通常有两个 npm/Yarn 包更新策略:(1)尽快更新,甚至使用自动化流程(2)根本没有更新策略,有时候会根据口碑进行更新。 虽然第一种方法似乎更优越,但令人惊讶的是它是 2018 年最危险的方法:社区在 40 天内发现的所有诸如平流等恶意包,处于等待状态以及更新不快的包都被保存了。 考虑使用自动化工具格式化更新策略,并找到”完全不更新“到”正在更新“过程之间的位置。

例子:

  • Liran Tal 的 npq 是一个很棒的咨询包安装器,它也关注发布日期

  • 一旦包更新,greenkeeper 等商业工具将立刻 PR。 不过在发布版本被证实安全之前,没有人能够暂停更新

12. 执行逐步安装,区分部署和发布阶段

2019 年,你可能会发现执行更安全的部署非常有用,这些部署不是一锤子买卖。在更安全的方面,粒度部署(a.k.a canary)建议分为 3 个阶段:(1)部署 - 将新代码发送到隔离的新生产区域(例如,新的 Kubernetes 服务或机器实例)。在这个阶段,它为任何人服务,所以不必害怕(2)测试 - 现在很少有人可以在最现实的生产环境中开发和测试新代码(3)发布 - 逐渐允许更多用户发布新版本(例如,整个东海岸),等你有了足够的信心,你可以淡出旧版本。

需要注意的是:2019 年进行全面的灰度部署仍然非常昂贵,因为它需要协调许多基础设施部件,如路由和监控。因此,请考虑从简单和半手动灰度部署开始(例如,根据监控指标手动启动更多新版本机器)

例子:

  • 了解有关灰度版本的更多信息

  • 如果你愿意一直跟进到灰度部署,Spinnaker 是一个强大的部署平台

13. Kubernetes 吃了这个世界

Kubernetes(K8S),它是无缝提供网络,横向扩展,部署和其他骨干服务的应用组件的基础架构,现在几乎是托管应用的事实标准。它的受欢迎程度十分惊人:在所有云供应商的支持下,拥有无与伦比的扩展回声系统,即使 54% 的企业已经拥有至少一个 K8S 集群。如果你是初学者,此链接提供了一个很好的动手概述。你的 K8S 第一步已经完成了吗?确保熟悉 Istio,K-Native,Kuberenes 工作,内部概述,网络政策,Helm,Scaffold。总的就一句话:你花在加深 K8S 技能上的任何时间都会得到回报。

14. 区块链技术带来了一些很好的机会

除了比特币和加密功能,区块链也可以用于任何分布式系统处理事务。

15. 获得可靠的机器学习技能,或者至少能够聪明地阐述

这个我说不了太多,它也许是我们时代的主导趋势。可惜,我对机器库一无所知,我对 2019 的目标是至少能够聪明地谈论它,并找出快速获胜的机会(例如,像 tensorflow.js 和 brain.js 这样的 JS 库可以在没有强大的基础设施的情况下提供一些帮助)

16. 浏览所选开源库的代码

注意,使用相同的技术长时间开发同一个项目上,可能会限制你的视野或错过很多替代方案。努力经常调研其他项目,主要是成功的开源项目。

17. 深化对 Linux 操作系统的理解,重点关注 Linux 进程的解剖

了解 Linux 进程将给予你真正的竞争优势,因为它会影响许多开发任务,如监视,保护进程(例如重新启动),使用 Docker 优雅地关闭以及许多其他任务。努力了解流程,信号,权限模型,常用命令,流程类型等的生命周期。本教程涵盖了大多基础知识。

18. 深入了解 Node.js 内部原理

我真的很喜欢 Ryan Dahl(Node.js v0,1的创造者)的一句话:“你永远无法理解一切。但是,你应该让自己去了解系统“。当需要处理生产问题或设计一些基础结构组件(例如监视事件循环性能)时,对底层机器的深入理解会显得很有价值。你可能已经熟悉了 v8 和 libuv 等核心构建块。难道 2019 不是深入 Node.js 兔子洞(译者注:《爱丽丝梦游仙境》的兔子洞)之旅的好时机吗!例如,了解每个 libuv 事件循环周期内究竟发生了什么?或者了解如何与操作系统 IO 交互(例如活动句柄)?

例子:

  • 了解每个事件循环周期中发生的事情,由 Deepal Jayasekara 提出

  • 了解如何将 C/C++ 代码打包为 NPM 模块,由 Konstantin Tarkus 提出

  • 访问这篇由 Eugene Obrezkov 撰写的涵盖整个 Node.js 内部的深度文章

19. 压轴:学习使用科学方法

你学到的东西和内化将塑造你未来的职业生涯。然而,许多开发人员既没有学习策略,也不知道如何使用科学方法有效地学习。假设有个关于“避免 JavaScript 类型错误”的会议,VP 要求继续使用原生 JavaScript 而不重构整个代码库(不使用 TypeScript ......),突然间你的同事建议使用 Facebook 流程,房间里的每个人都喜欢它!你突然想起你曾经读过它,但它从来没有被内化为你的只是,只是在你的脑海中溜过。为什么会这样?显然,有一种名为“竞争幻觉”的现象解释了为什么我们会忘记这些事情:你可能花了 1 个小时阅读一篇博文,但是你自欺欺人,几天之内就不记得了!研究表明,如果你稍后尝试与人谈论它,或者在第二天再次阅读摘要,你就可以大大提高记忆这个概念的机会。还有其他各种技巧可以帮助你在正确的时间记住并获取正确的知识(参见下面的示例),花几个小时学习如何学习,对你的职业生涯大有裨益!

例子:

  • 参加《学习如何学习》这个超棒的课程

  • 在学习时进行分块和分类

  • 学习新技术的时候呢?将它与你熟悉的现有事物相比较,与你的队友谈论它,问问自己“这有什么用”的问题 - 为什么需要它,绘制图表,重新阅读摘要,帮助你的大脑内化并对其进行分类,如此你将能够在重要的情况下获得它!

英文原文:

https://medium.com/@me_37286/19-ways-to-become-a-better-node-js-developer-in-2019-ffd3a8fbfe38

好文推荐:

Node.js 基金会和JS 基金会准备合并,你怎么看?

“UC国际技术”致力于与你共享高质量的技术文章

欢迎关注我们的公众号、将文章分享给你的好友