{"record":{"id":"c59170d386a12cb8","repo":"mobxjs/mobx","slug":"mobx-spy-is-a-no-op-in-production-builds","errorCode":null,"errorMessage":"[mobx.spy] Is a no-op in production builds","messagePattern":"\\[mobx\\.spy\\] Is a no-op in production builds","errorType":"console","errorClass":null,"httpStatus":null,"severity":"info","filePath":"packages/mobx/src/core/spy.ts","lineNumber":63,"sourceCode":"    spyReport(change)\n}\n\nconst END_EVENT: SpyEvent = { type: \"report-end\", spyReportEnd: true }\n\nexport function spyReportEnd(change?: { time?: number }) {\n    if (!__DEV__) {\n        return\n    }\n    if (change) {\n        spyReport(assign({}, change, { type: \"report-end\" as const, spyReportEnd: true as const }))\n    } else {\n        spyReport(END_EVENT)\n    }\n}\n\nexport function spy(listener: (change: SpyEvent) => void): Lambda {\n    if (!__DEV__) {\n        console.warn(`[mobx.spy] Is a no-op in production builds`)\n        return function () {}\n    } else {\n        globalState.spyListeners.push(listener)\n        return once(() => {\n            globalState.spyListeners = globalState.spyListeners.filter(l => l !== listener)\n        })\n    }\n}\n","sourceCodeStart":45,"sourceCodeEnd":72,"githubUrl":"https://github.com/mobxjs/mobx/blob/01211a698b64ea94de8e5f276ff8235fcf8ddf96/packages/mobx/src/core/spy.ts#L45-L72","documentation":"spy() registers a global listener for MobX transition events, but spy instrumentation is compiled out of production builds. In a non-__DEV__ bundle the function is a no-op that only console.warns and returns an empty disposer. It exists to tell developers why their spy listener never receives events in production.","triggerScenarios":"Calling spy(listener) (or mobx.spy) in an app bundled with NODE_ENV=production / a minified production MobX build, so __DEV__ is false and the early-return branch runs.","commonSituations":"Debugging tooling (e.g. mobx-devtools) silently inert in production; logging wrappers that call spy unconditionally; testing spy-based instrumentation against production builds of the library.","solutions":["Call spy() only in development builds, guarded by process.env.NODE_ENV !== 'production'.","If you need spy events in production, build against a development MobX bundle (not recommended for perf/size).","Replace production logging with trace()/onBecomeObserved on specific observables, which are not spy-gated.","Ignore the warning if the spy was best-effort debugging; the returned no-op disposer is safe to call."],"exampleFix":"// before\nimport { spy } from 'mobx'\nspy(event => console.log(event))\n\n// after\nimport { spy } from 'mobx'\nif (process.env.NODE_ENV !== 'production') {\n  spy(event => console.log(event))\n}","handlingStrategy":"fallback","validationCode":"function spySupported() {\n  return process.env.NODE_ENV !== 'production'\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Gate spy/devtools setup behind NODE_ENV checks.","Use onBecomeObserved/onBecomeUnobserved or trace() for production-safe diagnostics.","Never rely on spy events for application logic — they are dev-only."],"tags":["mobx","spy","production-build","devtools","no-op"],"backgroundTag":"spy-noop-in-production-build","analyzedSha":"01211a698b64ea94de8e5f276ff8235fcf8ddf96","analyzedAt":"2026-08-28T22:10:08.831Z","schemaVersion":2},"datasetVersion":"2026-08-29T02:17:18.158Z"}