今日已更新 32 条资讯 | 累计 27207 条内容
关于我们

Show HN: Pure Effect – Reproduce production bugs on your laptop without a DB

tie-in 2026年06月22日 01:36 2 次阅读 来源:HackerNews

Hi HN, I think it's safe to say that the majority of developers don't give a second thought to writing code with I/O tangled in business logic. It's all too common to see code like: const user = findUser(email); if (!user) await saveUser(user); Now, you may ask: what's the big deal? When we write code like this, two things happen: 1. It gets harder to debug production bugs. Unless you have the exact same database and remote API services to connect to, you may fail to reproduce the bug. 2. You ha

Hi HN, I think it's safe to say that the majority of developers don't give a second thought to writing code with I/O tangled in business logic. It's all too common to see code like: const user = findUser(email); if (!user) await saveUser(user); Now, you may ask: what's the big deal? When we write code like this, two things happen: 1. It gets harder to debug production bugs. Unless you have the exact same database and remote API services to connect to, you may fail to reproduce the bug. 2. You have to use mocks and fakes in your tests, or use test containers, which only help somewhat, and they are slow! To solve these issues, I built Pure Effect, a tiny TypeScript/JavaScript effect library. The core idea is simple: if a function performs I/O, it isn't pure. But if it returns a description of the I/O it wants to perform, it is. So instead of await findUser(email), you return a Command object that says, "I would like to call this function, and when it finishes, here's what to do next." Your business logic becomes a pure function. Same input, same output, every time. The database never gets touched until the interpreter (runEffect) runs. When I first started the library, I didn't expect just how far that one idea would stretch. Once your pipelines are just data, a lot of wonderful things become possible: - No need for mocking libraries. You walk the tree in tests and assert on its structure: assert.equal(flow.cmd.name, 'cmdFindUser'). Nothing is executed. - Wrap any effect with Retry(effect, { attempts: 3, delay: 200, backoff: 2 }). The configuration is plain data, so you can assert on it in tests. - Every command's input and output flows through the interpreter, so you get a full execution trace for free. You can write a simple timeTravel() function that replays it locally without touching any I/O. Perfect for debugging complex production bugs. - An onBeforeCommand hook sits between your business logic and the interpreter. Since it sees every intended side effect befor
本文内容来源于互联网,版权归原作者所有
查看原文