你的依赖可以读取磁盘上的任何文件。cap-std 让它们先请求权限。
Rust 的标准库向每个依赖授予隐式的文件系统权限。cap-std 将其替换为基于权能的 API,强制代码在打开路径之前证明它有权访问该路径。
你依赖树中的任何一个 crate 都可以打开 、向你的 目录写入内容,或者枚举你项目中的每一个文件。Rust 的标准库不会请求许可。它假设任何能够调用 的代码都有权接触操作系统允许的任何路径。 cap-std 改变了这一假设。它是 Rust I/O module…
探索 AI 优先开发、编码护栏和可处置架构。
Rust 的标准库向每个依赖授予隐式的文件系统权限。cap-std 将其替换为基于权能的 API,强制代码在打开路径之前证明它有权访问该路径。
你依赖树中的任何一个 crate 都可以打开 、向你的 目录写入内容,或者枚举你项目中的每一个文件。Rust 的标准库不会请求许可。它假设任何能够调用 的代码都有权接触操作系统允许的任何路径。 cap-std 改变了这一假设。它是 Rust I/O module…
Confused deputy 攻击会诱骗一个拥有特权的服务,让它利用自己的权限攻击自己。以下是攻击者如何利用隐式信任发起攻击,以及为什么 capability-based security 才是解决方案。
你的服务持有一个云存储的 API key。用户发来一个请求,你的服务乖乖地把文件写了进去。文件落到了攻击者的 bucket 里,而不是你的,于是攻击者拿到了你的数据。你在不知不觉中成了帮凶。 这就是 confused deputy 攻击。攻击者自己无法向目标 bucket…
基于能力的安全模型用不可伪造的权限令牌取代零散的角色检查。以下是如何在 TypeScript 中实现它,同时不让代码变得难以阅读。
事后看来,每个权限漏洞都长得一样。调用栈深处的某个函数假设调用者已经检查了 。但实际上并没有。又或者新增了一个角色,然后你在 47 个文件里 grep ,祈祷自己没有漏掉任何一个。…
大多数代码运行在 ambient authority 之下:每个函数都能触碰一切。Capability-based security 翻转了这一范式,强制函数只能接收显式、受限定范围的权限。
你的 函数可以访问数据库、支付网关和审计日志,仅仅因为它碰巧运行在同一个进程里。如果攻击者在某个 HTTP 处理程序中发现了注入漏洞,他就会继承这一切。这个函数从未主动请求这些权力,它只是凭借部署位置就默认拥有了它们。 这就是 ambient…
抛出的异常会把失败路径从你的类型系统中隐藏起来。下面解释为什么显式返回错误能让代码更诚实,以及如何在不折磨自己的情况下采用这一模式。
你的函数签名说它返回一个 。事实并非如此。它返回一个 ,或者它会爆炸。类型系统根本不知道还有第二条分支。 这正是基于异常的错误处理最根本的不诚实之处。每一个…
一个单字段包装结构体就能在编译期捕获单位混淆和类型错用,不增加哪怕一个字节的开销。
把一个 用户 ID 传给期望 order ID 的函数,Rust 不会报错。两者都是 。编译器看到的是完全相同的类型,所以帮不了你。直到运行时你才会发现,通常是在生产环境,通常是在一次你以为安全的重构之后。 这正是 newtype 模式存在所要消灭的那类 bug。 newtype…
TypeScript 的 switch 语句会悄无声息地让你遗漏分支。下面介绍如何用穷尽性检查模式来替代它,让构建阶段而非运行时暴露错误。
你重构了一个 shape 类型,加了一个新变体,TypeScript 却一切正常。CI 通过了。部署也上线了。然后某个用户触发了一个返回 的运行时分支,你的应用在生产环境抛出了异常。 罪魁祸首几乎肯定是 语句。TypeScript 的 不提供穷尽性保证。给 union 增加一个新成员,所有基于该 union 的…
给状态机添加新状态很容易。记住更新每一个 switch 语句却不然。下面介绍如何让 TypeScript 在你遗忘某个 case 时拒绝编译。
状态机起初很干净。三个值,三个 switch 分支。然后重试逻辑添加了第四个状态。部分失败添加了第五个。你更新了 reducer,却漏掉了状态徽标组件、分析映射器和导出格式化器。 一切都能编译通过。两个冲刺周期后,当用户在你从未手动测试过的边界场景中遇到空白屏幕时,bug 才浮出水面。 TypeScript…
TypeScript 把所有数字视为同一个东西。下面介绍如何让它区分 USD 和 EUR,使编译器在代码上线前就能拦截货币转换相关的 bug。
2022 年,一家大型金融科技平台处理了一笔 32,700,000.00 的批量转账。金额被存储为普通的 。下游服务以为它是以分为单位。事实并非如此。 这个 bug 逃过了代码审查、单元测试和集成测试。类型系统看到 和 ,就觉得没问题了。两个完全相同的类型,完美兼容,却带来了灾难性的错误。…
该传秒的地方传了毫秒,这种 bug 能躲过所有测试。下面介绍如何将单位直接编码进 TypeScript 的类型系统,让混用在编译阶段就报错,且运行时零开销。
某个函数的 timeout 参数要求毫秒,你传了 。另一个函数要求秒,你传了 。中间某个地方,你调用了 ,结果整整一小时二十三分钟什么也没发生。 TypeScript 在这里帮不了你。 和 都是 。编译器分辨不出米和英尺、摄氏和华氏、时间戳和时长的区别。你的测试套件大概率也抓不到,因为计算本身是对的,错的是单位。…