{"record":{"id":"9b5bdd208f2feea1","repo":"mochajs/mocha","slug":"sync-skip-aborting-execution","errorCode":null,"errorMessage":"sync skip; aborting execution","messagePattern":"sync skip; aborting execution","errorType":"exception","errorClass":"PendingError","httpStatus":null,"severity":"warning","filePath":"lib/runnable.js","lineNumber":140,"sourceCode":"      return this._slow;\n    }\n    if (typeof ms === \"string\") {\n      ms = milliseconds(ms);\n    }\n    debug(\"slow %d\", ms);\n    this._slow = ms;\n    return this;\n  }\n\n  /**\n   * Halt and mark as pending.\n   *\n   * @memberof Mocha.Runnable\n   * @public\n   */\n  skip() {\n    this.pending = true;\n    throw new PendingError(\"sync skip; aborting execution\");\n  }\n\n  /**\n   * Check if this runnable or its parent suite is marked as pending.\n   *\n   * @private\n   */\n  isPending() {\n    return this.pending || (this.parent && this.parent.isPending());\n  }\n\n  /**\n   * Return `true` if this Runnable has failed.\n   * @return {boolean}\n   * @private\n   */\n  isFailed() {\n    return !this.isPending() && this.state === Runnable.constants.STATE_FAILED;","sourceCodeStart":122,"sourceCodeEnd":158,"githubUrl":"https://github.com/mochajs/mocha/blob/6bcbee4fd9a95351cedf0fdcb14c7d696486bc5a/lib/runnable.js#L122-L158","documentation":"`Runnable.prototype.skip()` marks the test as pending and throws a `PendingError` to immediately abort the test body's synchronous execution; Mocha's internal error handler recognizes it and reports the test as skipped rather than failed. Seeing this message as a raw failure means the pending sentinel escaped Mocha's handling.","triggerScenarios":"Calling `this.skip()` inside a test body or hook; Mocha's `--bail`/uncaught-exception plumbing failing to swallow the PendingError (e.g. `this.skip()` used where no runnable context exists); user code catching and rethrowing the sentinel across a boundary Mocha doesn't inspect.","commonSituations":"Dynamic skipping in tests (`if (!condition) this.skip()`); calling `this.skip()` inside a `before` hook of a suite-level skip; wrapping test functions in custom async wrappers that rethrow errors after Mocha's handler ran.","solutions":["Prefer `it.skip`/`describe.skip` or `this.skip()` only inside a running test/hook where Mocha can intercept it.","Don't catch-and-rethrow errors thrown inside test bodies without re-checking `err instanceof PendingError` (or checking `this.isPending()`).","For conditional skipping in async tests, use the async pattern (`this.skip()` in a promise chain) or set `this.pending` via a helper that Mocha supports.","If this surfaces as a test failure rather than a skip, check for custom wrappers/uncaught handlers swallowing or rethrowing PendingError."],"exampleFix":"// before\nwrap(function (done) {\n  if (!support) this.skip(); // rethrown by wrapper -> surfaces as failure\n});\n\n// after\nit('does x', function () {\n  if (!support) return this.skip();\n  // rest of test\n});","handlingStrategy":"try-catch","validationCode":"if (this.isPending?.()) return; // already skipped, don't call skip again\nif (!ctx || typeof ctx.skip !== 'function') {\n  throw new Error('this.skip() only valid inside a runnable test/hook');\n}","typeGuard":"const isPendingError = (err) => err instanceof Error && (err.message === 'sync skip; aborting execution' || err.message === 'async skip; aborting execution');","tryCatchPattern":"try {\n  runTestBody();\n} catch (err) {\n  if (isPendingError(err)) {\n    markTestPending(test);\n    return; // treat as skip, not failure\n  }\n  throw err;\n}","preventionTips":["Call this.skip() only inside a running test body or hook.","Prefer static it.skip/describe.skip for compile-time-known skips.","Avoid custom wrappers that catch and rethrow test-body errors blindly.","Return immediately after this.skip() so no code runs afterward."],"tags":["test-execution","skip","pending"],"backgroundTag":"test-skipped-sentinel","analyzedSha":"6bcbee4fd9a95351cedf0fdcb14c7d696486bc5a","analyzedAt":"2026-09-01T03:41:47.182Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}