diff --git a/README.md b/README.md index c0f7247..4888c23 100644 --- a/README.md +++ b/README.md @@ -14,11 +14,15 @@ ## Description -TODO +Detect when and where mutations occur in your code. It may seem cool, but it's not a replacement for strict typings or tests. It is currently a proof-of-concept and a debugging tool. + +> Why did this property change?! I didn't do that!!! ## Features -- TODO +- Detect any proxy-compatible mutation as it happens +- Throws a stack trace of the code that caused the mutation +- Includes a property path to the mutation in the object ## Installation @@ -28,7 +32,48 @@ npm install will-mutate @babel/core@^7.0.0 --save-dev ## Usage -TODO +Add the `$shouldNotMutate` function call directly above any function declaration or expression with the name of any variable in-scope at the beginning of the function body. + +### Code + +```js +// In this example, we're asserting that the argument `foo` will not mutate +$shouldNotMutate(["foo"]); +function bar (foo, other) { + foo.prop = "Test"; + other.prop = "Don't change me"; +} +``` + +#### Errors + +The below error is taken from running the above code snippet with `node ./bar.js` after compilation with Babel. You can see that the `prop` property was changed using `set` (assignment operator) inside the `bar` function in the `bar.js` module. + + +```bash +Error: Mutation assertion failed. `set` trap triggered on `target.prop`. + at Object.handler. [as set] (bar.js:148:13) + at bar (bar.js:194:31) + at Object. (bar.js:211:1) +``` + +If you see a trap you do not understand, [MDN has a list of proxy traps](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Proxy/Proxy#Handler_functions) where you can understand the conditions it will trigger under. Every trap related to mutations is implemented. + +### Babel Config + +You must also add Will Mutate to your Babel config. If you intend to leave the functions in your codebase you can use `noop` to run whenever you do not want runtime errors (e.g. production). + +`babel.config.js` + +```js +module.exports = { + plugins: [ + process.env.NODE_ENV === "development" + ? "will-mutate" + : "will-mutate/noop", + ], +}; +``` ## License