Million 的使命是让 React 应用更快,而新的 VS Code 扩展 Million Lint 采用了一种新的方法:想象一下 ESLint,但用于提出性能改进建议。
正式上线啦!经过三个月和数百次的提交,我们邀请您尝试 Million Lint。这个体验还没有完全完成 - 还有一些已知的错误和一些缺失的功能 - 但我们对它的发展非常满意,迫不及待地想与您分享。
通过在任何 React 应用中运行以下命令,即可一键启动:
npx @million/lint@latest
如果您有任何 问题或反馈,请告诉我们!
什么是 Million Lint?
Million Lint 是一个用于保持 React 网站快速的 VSCode 扩展。我们会识别慢代码并提供建议修复。它就像 ESLint,但专注于性能!
许多开发人员尝试使用 React Devtools 等工具来查找不必要的渲染。不幸的是,大多数人缺乏正确管理复杂性的知识。
查看 React Devtools 与 Million Lint 之间的区别:
- React Devtools:感到迷茫?是的,我们也是如此(+99%的所有开发者)
- Million Lint:在 VSCode 中获取概要信息!
复杂的工具意味着开发人员放弃。每个开发人员都有这样的经历:我们随处插入 console.log
,捕获一些有希望的线索,但在“时间耗尽”之前什么都没有发生。最终,慢/有错误的代码永远不会得到修复,问题堆积在待办事项中,最终用户受到影响。
难道没有更好的方法来展现性能问题吗?
你与分析工具的对决
现有的工具(Sentry、Datadog 等)向您展示了 web 数据的“整个宇宙”。这可能包括每个函数调用、网络请求、用户交互、核心 web 要素、屏幕截图、内存等… 处理的信息量令人眼花缭乱。因此,这些工具的界面让人不知所措。
至于 React 和 Chrome Devtools,如果您不知道自己在做什么,它们根本无法使用。即使您知道,也很难判断组件重新渲染的哪一部分,或者哪个钩子或属性导致了这个变化。除非您是专家,否则性能调试的当前体验对大多数开发人员都是敌对的。
编译器还是运行时?
JavaScript 编译器使我们能够对源代码进行静态分析。对于性能优化,静态分析在广度上非常有用 - 通过编写规则,开发人员可以在整个代码库中发现问题。这就是为什么 ESLint 如此出色的原因。不过,缺点是,我们无法在实际运行之前预测操作有多慢,这使得仅将 Million Lint 实现为编译器变得不可能。
因此,另一种方法是在运行时进行仪器化。这里的优势是,我们可以直接运行应用程序并获取渲染信息(通过 React Fiber),因此许多与静态分析相关的复杂性问题会立即解决。然而,运行时的缺点是您没有原始源代码(除非使用痛苦而慢的源映射)。“哪个钩子或属性导致了这个变化?”“组件的哪一部分重新渲染了?”没有源代码,我们无法回答这些问题。
寻找更好的方法
因此,我们回到了绘图板。对于 Million Lint,我们问自己:我们如何可以在静态分析和运行时分析之间兼具两全的优势?我们需要创建一种不会占用构建时间或运行时的分析体验;然后,支持一个帮助开发人员快速找到性能问题的调试流程。
我们的答案是动态分析 - 在合适的地方同时使用静态分析和运行时分析。我们不是自上而下地进行过滤,而是遵循必要的数据流来了解每个组件的渲染,并从那里构建。这导致了我们专为 React 应用程序设计的自定义仪器库。
import MillionCompiler from '@million/lint';
Million Lint 的体验始于运行动态分析的编译器对单个 React 组件进行分析。
首先,编译器注入处理程序:
function App({ start }) {
Million.capture({ start }); // ✨ 注入
const [count, setCount] = Million.capture(useState)(start); // ✨ 注入
useEffect(
() => {
console.log("double: ", count * 2);
},
Million.capture([count]), // ✨ 注入
);
return Million.capture( // ✨ 注入
<Button onClick={() => setCount(count + 1)}>{count}</Button>,
);
}
(源代码):
function App({ start }) {
const [count, setCount] = useState(start);
useEffect(() => {
console.log('double: ', count * 2);
}, [count]);
return <Button onClick={() => setCount(count + 1)}>{count}</Button>;
}
在运行时,这些注入处理程序会捕获与开发模式中的 web 应用程序交互时的渲染、定时和元数据信息。通过这种方法,我们可以从运行应用程序中获取运行时分析数据,同时由于 JavaScript 编译器,仍然可以访问源代码!
// 收集数据的伪代码:
[
{
类型: '状态',
计数: 7,
时间: 0.1,
更改: [{ 之前: 0, 之后: 8 }, ...],
},
// 等等...
];
在捕获渲染后,我们扩展了编译器,以异步收集捆绑、网络和状态管理器信息,而无需构建时间开销。然后将这些实时见解馈送到 VSCode 扩展中,您可以在那里查看收集的信息和修复建议。
- 渲染信息
- Bundle 大小
最后,我们推出了 Lint++,它将收集的信息馈送到语言模型中,以发现优化机会。因此,即使您不知道自己在做什么 - Million Lint 也会向您展示!
Lint++ 有多好?
衡量 Lint++ 的客观质量需要一个非平凡的数据集,因此我们正在制作一个开源的 React web 应用程序优化基准测试,用于代码生成模型(即将推出!)。目前,我们已在我们的朋友之间的十几个正在生产中的产品上测试了 Lint++。作为一个公开示例,Lint++ 能够识别并提出正确的修复建议,解决了我们的朋友 Ivan Akulov 构建的 缓慢的教育性 React 应用程序中的每个问题。
在运行 Lint++ 后,它标记了 6 个组件中的以下问题:
- 不稳定的引用作为属性优化
- 记忆昂贵的组件
- 缓存内联函数
- 建议虚拟化
- 建议
use-context-selector
>useContext
- 将上下文提供程序移至树的顶部
我们邀请一个以前从未见过代码库的工程师尝试加速 notes
应用程序。使用 Million Lint,他在约 15 分钟的工作后将主页的性能提高了 3 倍。
当然,notes
只是一个小应用程序,Million Lint 不会总是找到每个问题的最佳修复方法。我们正在努力提高其质量 - 请尝试并告诉我们您的体验!
我们将如何从中赚钱?
在接下来的几周内,我们将开源 Million Lint 编译器和 VSCode 扩展。编译器和编辑器中的注释都是永久免费使用的。我们的重点是构建一个出色的开发人员工具,我们相信建立出色的开发人员工具的最佳方式是在开放中构建它。
为了谋生,我们将以每月 20 美元的价格收费 Lint++ 服务,可提供 100 次检测。对于更频繁的用户,我们仍在制定详细计划,但想法是根据您转化为代码的检测数量收费。我们相信这会使我们的激励与您的激励保持一致:只有在我们使您的应用程序更快时,我们才赚钱。
Million Lint 1.0 的道路
我们仍处于实验的早期阶段!Million Lints 目前主要解决不必要的重新渲染问题(但我们明白这对于长期来说可能 不是问题)并将着手处理来自 React 生态系统的减速问题:状态管理器、动画、捆绑大小、瀑布等等。我们的最终目标是创建一个工具链,可以自动保持整个 web 基础设施快速 - 从前端到后端。
我们希望 邀请您一同 走这条路,以打造可能的最佳 web 性能开发人员工具。Million Lint 是我们的第一步。尝试一下,告诉我们哪些部分还有待改进!
我如何帮助?
我们正在寻找在湾区加入我们的优秀前端和 pl/ml 工程师。
在 Million,我们对软件性能有一个简单的理论 - 我们可以构建使 任何人 成为性能专家的工具。开发人员应该只考虑发布功能和修复错误 - 不要让他们的代码变慢。我们计划从 React 开始,然后扩展到更广泛的前端、后端和其他平台。
如果你觉得你错过了 Million.js 的开头,请参与其中。开始时的乐趣在于你有多少机会塑造 🔜 我的电子邮件
Million 团队 + Ivan Akulov 一步一步解决 React 性能问题。加入我们!