Ejemplo
@jest/console 29.7.0: redirect and format log streams using CustomConsole and NullConsole
Muestra verificada para npm @jest/console 29.7.0: redirect and format log streams using CustomConsole and NullConsole. El contrato se ejecutó en node 22 …
sha256:57ac63876189c56e86f10a844b9ddd2578febf6d0bfff4c49a33c26daff6eec6
Esta red ofrece una sola cosa: una muestra que compila. La ejecutó en un sandbox y guardó el recibo firmado. No califica ni garantiza nada: si el mismo código compila donde estás no es algo que haya medido.
Cuántas claves de firma distintas presentaron un recibo de contrato aprobado. Una es solo el autor; más de una significa que alguien más también lo compiló. Una clave se genera sola y no tiene identidad registrada detrás, así que cuenta claves, no personas.
MIT-0
Evidencia de ejecución
El entorno declarado y las ejecuciones firmadas se muestran por separado, para que veas exactamente qué ejecutó esta muestra y dónde.
- Base de evidencia
- Contrato firmado aprobado
- Recibos de verificación
- 1
- Claves de firma que lo compilaron
- 1
Entorno declarado
node 22.23 linux 24 · ubuntu · glibc 2.39 x64 node 22.23 javascript npm 10
Entornos de las ejecuciones de verificación
| Entorno | Contrato | Etapas | Ejecución |
|---|---|---|---|
| node 22 · linux alpine/x64 · docker ed25519:c1973797be207ac4 | PASS | compile:SKIPPED · contract:PASS · load:PASS · resolve:PASS CONTAINER_RUN · node-typescript@1node:22-alpine@sha256:c610fcdfb1d5… |
2026-08-27 |
Caso
HOW- Objetivo
- redirect and format log streams using CustomConsole and NullConsole
- Paquetes
- Símbolos
-
- CustomConsole
- NullConsole
- Entorno
- node 22.23.2
- Creado
- 2026-08-27T17:57:13Z
Contrato
- CustomConsole routes stdout methods (log, info, debug, dir, dirxml) to custom stdout stream and stderr methods (warn, error) to custom stderr stream
- CustomConsole applies custom formatBuffer transformations to all emitted stdout and stderr messages
- CustomConsole indents grouped logs according to groupDepth and bolds group and groupCollapsed titles
- CustomConsole tracks named timers with time, timeLog, and timeEnd, and named counters with count and countReset
- CustomConsole.assert intercepts AssertionError on falsy conditions and logs to stderr without throwing while passing truthy conditions silently
- CustomConsole.getBuffer always returns undefined
- NullConsole requires writable streams in constructor and throws ERR_CONSOLE_WRITABLE_STREAM if instantiated without arguments
- NullConsole silences all console methods including log, info, warn, error, debug, assert, and timers without emitting output to streams
Archivos
- PROMPT.md
- csx.json
- index.js
- package-lock.json
- package.json
- spec.json
- test/contract.js
Código fuente
Clean-room public code sample — generation instructions
Write a brand-new, minimal, self-contained code sample in this clean-room directory.
Do not copy, paraphrase, or reference any existing project source. Work only from this spec.
A csx.json manifest scaffold already exists. Do not recreate it from memory. Preserve its case.goal, packages and symbols; fill its empty case.contract with exact assertions and correct its environment, commands and verifierAdapter for the files you generate.
Goal: redirect and format log streams using CustomConsole and NullConsole
Kind: HOW
Use EXACTLY these public packages and versions:
- pkg:npm/%40jest/console@29.7.0
Demonstrate these symbols/APIs:
- CustomConsole
- NullConsole
Rules:
- One focused purpose; the smallest project that proves the goal.
- Include a contract test (test/contract.*) that runs OFFLINE and exits 0 exactly when the goal behavior works.
- Pin every dependency with a lockfile so resolution is reproducible.
- No secrets, credentials, or tokens. No real URLs (only example.com or localhost). No absolute paths.
- No personal names, emails, company names, or project identifiers of any kind.
- No binaries and no generated output (node_modules, dist, target, venv, .git, .env).
- Keep it under 200 files and 256KB packed.
{"case":{"caseId":"case:sha256:cb00aa8fc25cfb290fc0358d63d12cddb3c026d3dfe0855220fb7781af54f664","constraints":{"executionContext":"node"},"contract":["CustomConsole routes stdout methods (log, info, debug, dir, dirxml) to custom stdout stream and stderr methods (warn, error) to custom stderr stream","CustomConsole applies custom formatBuffer transformations to all emitted stdout and stderr messages","CustomConsole indents grouped logs according to groupDepth and bolds group and groupCollapsed titles","CustomConsole tracks named timers with time, timeLog, and timeEnd, and named counters with count and countReset","CustomConsole.assert intercepts AssertionError on falsy conditions and logs to stderr without throwing while passing truthy conditions silently","CustomConsole.getBuffer always returns undefined","NullConsole requires writable streams in constructor and throws ERR_CONSOLE_WRITABLE_STREAM if instantiated without arguments","NullConsole silences all console methods including log, info, warn, error, debug, assert, and timers without emitting output to streams"],"goal":"redirect and format log streams using CustomConsole and NullConsole","kind":"HOW","packages":["pkg:npm/%40jest/console@29.7.0"],"schemaVersion":1,"symbols":["CustomConsole","NullConsole"]},"contractCommand":["node","test/contract.js"],"environment":{"arch":"x64","distro":"ubuntu","ecosystem":"npm","executionContext":"node","language":"javascript","libc":"glibc","libcVersion":"2.39","moduleSystem":"cjs","os":"linux","osVersionBucket":"24","packageManager":"npm","packageManagerVersion":"10.9.8","runtime":"node","runtimeVersion":"22.23.2","schemaVersion":1},"license":"MIT-0","packages":["pkg:npm/%40jest/console@29.7.0"],"schemaVersion":1,"subject":"pkg:npm/%40jest/console@29.7.0","symbols":["CustomConsole","NullConsole"],"verifierAdapter":"node-typescript@1"}
'use strict';
const { Writable } = require('stream');
const { CustomConsole, NullConsole } = require('@jest/console');
/**
* Creates an in-memory writable stream that collects written chunks.
* @returns {{ stream: Writable, getOutput: () => string, getChunks: () => string[], clear: () => void }}
*/
function createMemoryStream() {
const chunks = [];
const stream = new Writable({
write(chunk, encoding, callback) {
chunks.push(chunk.toString());
callback();
}
});
return {
stream,
getOutput: () => chunks.join(''),
getChunks: () => [...chunks],
clear: () => {
chunks.length = 0;
}
};
}
/**
* Creates a CustomConsole instance with custom or default memory streams.
* @param {object} [options]
* @param {NodeJS.WritableStream} [options.stdout] - Destination stream for standard messages.
* @param {NodeJS.WritableStream} [options.stderr] - Destination stream for error messages.
* @param {Function} [options.formatBuffer] - Formatter function: (type, message) => string.
* @returns {CustomConsole}
*/
function createCustomConsole(options = {}) {
const stdout = options.stdout || createMemoryStream().stream;
const stderr = options.stderr || createMemoryStream().stream;
const formatBuffer = options.formatBuffer || ((_type, message) => message);
return new CustomConsole(stdout, stderr, formatBuffer);
}
/**
* Creates a NullConsole instance with default or custom streams.
* Note: NullConsole requires Writable streams in constructor (inherited from Console).
* @param {NodeJS.WritableStream} [stdout] - Optional stdout stream.
* @param {NodeJS.WritableStream} [stderr] - Optional stderr stream.
* @returns {NullConsole}
*/
function createNullConsole(stdout, stderr) {
const devNull = () =>
new Writable({
write(_chunk, _encoding, callback) {
callback();
}
});
return new NullConsole(stdout || devNull(), stderr || devNull());
}
/**
* Executes a callback with console redirected through CustomConsole and returns captured stdout/stderr.
* @param {Function} fn - Function to execute: (customConsole) => any
* @param {Function} [formatBuffer] - Optional message formatter.
* @returns {{ result: any, stdout: string, stderr: string }}
*/
function captureCustomStreamOutput(fn, formatBuffer) {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const customConsole = new CustomConsole(stdoutMem.stream, stderrMem.stream, formatBuffer);
const originalConsole = global.console;
let result;
try {
global.console = customConsole;
result = fn(customConsole);
} finally {
global.console = originalConsole;
}
return {
result,
stdout: stdoutMem.getOutput(),
stderr: stderrMem.getOutput()
};
}
module.exports = {
CustomConsole,
NullConsole,
createMemoryStream,
createCustomConsole,
createNullConsole,
captureCustomStreamOutput
};
{
"name": "sample-jest-console-custom",
"version": "1.0.0",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "sample-jest-console-custom",
"version": "1.0.0",
"license": "MIT-0",
"dependencies": {
"@jest/console": "29.7.0"
}
},
"node_modules/@babel/code-frame": {
"version": "7.29.7",
"resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.7.tgz",
"integrity": "sha512-Aup7aUOfpbAUg2ROOJN6Iw5f9DMBlzu0mIkm/malLQFN/YQgO48wCj0Kxa3sEHJvPVFg7siR+qRInwXd2qhQKw==",
"license": "MIT",
"dependencies": {
"@babel/helper-validator-identifier": "^7.29.7",
"js-tokens": "^4.0.0",
"picocolors": "^1.1.1"
},
"engines": {
"node": ">=6.9.0"
}
},
"node_modules/@babel/helper-validator-identifier": {
"version": "7.29.7",
"resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.29.7.tgz",
"integrity": "sha512-qehxGkRj55h/ff8EMaJ+cYhyaKlHIxqYDn682wQD7RNp9UujOQsHog2uS0r2vzr4pW+sXf90NeeayjcNaX3fFg==",
"license": "MIT",
"engines": {
"node": ">=6.9.0"
}
},
"node_modules/@jest/console": {
"version": "29.7.0",
"resolved": "https://registry.npmjs.org/@jest/console/-/console-29.7.0.tgz",
"integrity": "sha512-5Ni4CU7XHQi32IJ398EEP4RrB8eV09sXP2ROqD4bksHrnTree52PsxvX8tpL8LvTZ3pFzXyPbNQReSN41CAhOg==",
"license": "MIT",
"dependencies": {
"@jest/types": "^29.6.3",
"@types/node": "*",
"chalk": "^4.0.0",
"jest-message-util": "^29.7.0",
"jest-util": "^29.7.0",
"slash": "^3.0.0"
},
"engines": {
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
}
},
"node_modules/@jest/schemas": {
"version": "29.6.3",
"resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.6.3.tgz",
"integrity": "sha512-mo5j5X+jIZmJQveBKeS/clAueipV7KgiX1vMgCxam1RNYiqE1w62n0/tJJnHtjW8ZHcQco5gY85jA3mi0L+nSA==",
"license": "MIT",
"dependencies": {
"@sinclair/typebox": "^0.27.8"
},
"engines": {
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
}
},
"node_modules/@jest/types": {
"version": "29.6.3",
"resolved": "https://registry.npmjs.org/@jest/types/-/types-29.6.3.tgz",
"integrity": "sha512-u3UPsIilWKOM3F9CXtrG8LEJmNxwoCQC/XVj4IKYXvvpx7QIi/Kg1LI5uDmDpKlac62NUtX7eLjRh+jVZcLOzw==",
"license": "MIT",
"dependencies": {
"@jest/schemas": "^29.6.3",
"@types/istanbul-lib-coverage": "^2.0.0",
"@types/istanbul-reports": "^3.0.0",
"@types/node": "*",
"@types/yargs": "^17.0.8",
"chalk": "^4.0.0"
},
"engines": {
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
}
},
"node_modules/@sinclair/typebox": {
"version": "0.27.12",
"resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.27.12.tgz",
"integrity": "sha512-hhyNJ+nbR6ZR7pToHvllEFun9TL0sbL+tk/ON75lo+Xas054uez98qRbsuNt7MBCyZKK4+8Yli/OAGZhmfBZ/g==",
"license": "MIT"
},
"node_modules/@types/istanbul-lib-coverage": {
"version": "2.0.6",
"resolved": "https://registry.npmjs.org/@types/istanbul-lib-coverage/-/istanbul-lib-coverage-2.0.6.tgz",
"integrity": "sha512-2QF/t/auWm0lsy8XtKVPG19v3sSOQlJe/YHZgfjb/KBBHOGSV+J2q/S671rcq9uTBrLAXmZpqJiaQbMT+zNU1w==",
"license": "MIT"
},
"node_modules/@types/istanbul-lib-report": {
"version": "3.0.3",
"resolved": "https://registry.npmjs.org/@types/istanbul-lib-report/-/istanbul-lib-report-3.0.3.tgz",
"integrity": "sha512-NQn7AHQnk/RSLOxrBbGyJM/aVQ+pjj5HCgasFxc0K/KhoATfQ/47AyUl15I2yBUpihjmas+a+VJBOqecrFH+uA==",
"license": "MIT",
"dependencies": {
"@types/istanbul-lib-coverage": "*"
}
},
"node_modules/@types/istanbul-reports": {
"version": "3.0.4",
"resolved": "https://registry.npmjs.org/@types/istanbul-reports/-/istanbul-reports-3.0.4.tgz",
"integrity": "sha512-pk2B1NWalF9toCRu6gjBzR69syFjP4Od8WRAX+0mmf9lAjCRicLOWc+ZrxZHx/0XRjotgkF9t6iaMJ+aXcOdZQ==",
"license": "MIT",
"dependencies": {
"@types/istanbul-lib-report": "*"
}
},
"node_modules/@types/node": {
"version": "26.4.0",
"resolved": "https://registry.npmjs.org/@types/node/-/node-26.4.0.tgz",
"integrity": "sha512-faiGnoIrLH/V8cibOMEAZ8pMw6oXqSukl29ra4mN8GdaB2ZewzeaLj+INpV5N+Z1eKWzY+IzaIZH2EIR6YZRNQ==",
"license": "MIT",
"dependencies": {
"undici-types": "~8.3.0"
}
},
"node_modules/@types/stack-utils": {
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@types/stack-utils/-/stack-utils-2.0.3.tgz",
"integrity": "sha512-9aEbYZ3TbYMznPdcdr3SmIrLXwC/AKZXQeCf9Pgao5CKb8CyHuEX5jzWPTkvregvhRJHcpRO6BFoGW9ycaOkYw==",
"license": "MIT"
},
"node_modules/@types/yargs": {
"version": "17.0.35",
"resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.35.tgz",
"integrity": "sha512-qUHkeCyQFxMXg79wQfTtfndEC+N9ZZg76HJftDJp+qH2tV7Gj4OJi7l+PiWwJ+pWtW8GwSmqsDj/oymhrTWXjg==",
"license": "MIT",
"dependencies": {
"@types/yargs-parser": "*"
}
},
"node_modules/@types/yargs-parser": {
"version": "21.0.3",
"resolved": "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-21.0.3.tgz",
"integrity": "sha512-I4q9QU9MQv4oEOz4tAHJtNz1cwuLxn2F3xcc2iV5WdqLPpUnj30aUuxt1mAxYTG+oe8CZMV/+6rU4S4gRDzqtQ==",
"license": "MIT"
},
"node_modules/ansi-styles": {
"version": "4.3.0",
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
"integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
"license": "MIT",
"dependencies": {
"color-convert": "^2.0.1"
},
"engines": {
"node": ">=8"
},
"funding": {
"url": "https://github.com/chalk/ansi-styles?sponsor=1"
}
},
"node_modules/braces": {
"version": "3.0.3",
"resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz",
"integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==",
"license": "MIT",
"dependencies": {
"fill-range": "^7.1.1"
},
"engines": {
"node": ">=8"
}
},
"node_modules/chalk": {
"version": "4.1.2",
"resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz",
"integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==",
"license": "MIT",
"dependencies": {
"ansi-styles": "^4.1.0",
"supports-color": "^7.1.0"
},
"engines": {
"node": ">=10"
},
"funding": {
"url": "https://github.com/chalk/chalk?sponsor=1"
}
},
"node_modules/ci-info": {
"version": "3.9.0",
"resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.9.0.tgz",
"integrity": "sha512-NIxF55hv4nSqQswkAeiOi1r83xy8JldOFDTWiug55KBu9Jnblncd2U6ViHmYgHf01TPZS77NJBhBMKdWj9HQMQ==",
"funding": [
{
"type": "github",
"url": "https://github.com/sponsors/sibiraj-s"
}
],
"license": "MIT",
"engines": {
"node": ">=8"
}
},
"node_modules/color-convert": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz",
"integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==",
"license": "MIT",
"dependencies": {
"color-name": "~1.1.4"
},
"engines": {
"node": ">=7.0.0"
}
},
"node_modules/color-name": {
"version": "1.1.4",
"resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz",
"integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==",
"license": "MIT"
},
"node_modules/escape-string-regexp": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-2.0.0.tgz",
"integrity": "sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w==",
"license": "MIT",
"engines": {
"node": ">=8"
}
},
"node_modules/fill-range": {
"version": "7.1.1",
"resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz",
"integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==",
"license": "MIT",
"dependencies": {
"to-regex-range": "^5.0.1"
},
"engines": {
"node": ">=8"
}
},
"node_modules/graceful-fs": {
"version": "4.2.11",
"resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz",
"integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==",
"license": "ISC"
},
"node_modules/has-flag": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
"license": "MIT",
"engines": {
"node": ">=8"
}
},
"node_modules/is-number": {
"version": "7.0.0",
"resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz",
"integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==",
"license": "MIT",
"engines": {
"node": ">=0.12.0"
}
},
"node_modules/jest-message-util": {
"version": "29.7.0",
"resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-29.7.0.tgz",
"integrity": "sha512-GBEV4GRADeP+qtB2+6u61stea8mGcOT4mCtrYISZwfu9/ISHFJ/5zOMXYbpBE9RsS5+Gb63DW4FgmnKJ79Kf6w==",
"license": "MIT",
"dependencies": {
"@babel/code-frame": "^7.12.13",
"@jest/types": "^29.6.3",
"@types/stack-utils": "^2.0.0",
"chalk": "^4.0.0",
"graceful-fs": "^4.2.9",
"micromatch": "^4.0.4",
"pretty-format": "^29.7.0",
"slash": "^3.0.0",
"stack-utils": "^2.0.3"
},
"engines": {
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
}
},
"node_modules/jest-util": {
"version": "29.7.0",
"resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.7.0.tgz",
"integrity": "sha512-z6EbKajIpqGKU56y5KBUgy1dt1ihhQJgWzUlZHArA/+X2ad7Cb5iF+AK1EWVL/Bo7Rz9uurpqw6SiBCefUbCGA==",
"license": "MIT",
"dependencies": {
"@jest/types": "^29.6.3",
"@types/node": "*",
"chalk": "^4.0.0",
"ci-info": "^3.2.0",
"graceful-fs": "^4.2.9",
"picomatch": "^2.2.3"
},
"engines": {
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
}
},
"node_modules/js-tokens": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz",
"integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==",
"license": "MIT"
},
"node_modules/micromatch": {
"version": "4.0.8",
"resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz",
"integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==",
"license": "MIT",
"dependencies": {
"braces": "^3.0.3",
"picomatch": "^2.3.1"
},
"engines": {
"node": ">=8.6"
}
},
"node_modules/picocolors": {
"version": "1.1.1",
"resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz",
"integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==",
"license": "ISC"
},
"node_modules/picomatch": {
"version": "2.3.2",
"resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.2.tgz",
"integrity": "sha512-V7+vQEJ06Z+c5tSye8S+nHUfI51xoXIXjHQ99cQtKUkQqqO1kO/KCJUfZXuB47h/YBlDhah2H3hdUGXn8ie0oA==",
"license": "MIT",
"engines": {
"node": ">=8.6"
},
"funding": {
"url": "https://github.com/sponsors/jonschlinkert"
}
},
"node_modules/pretty-format": {
"version": "29.7.0",
"resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.7.0.tgz",
"integrity": "sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==",
"license": "MIT",
"dependencies": {
"@jest/schemas": "^29.6.3",
"ansi-styles": "^5.0.0",
"react-is": "^18.0.0"
},
"engines": {
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
}
},
"node_modules/pretty-format/node_modules/ansi-styles": {
"version": "5.2.0",
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz",
"integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==",
"license": "MIT",
"engines": {
"node": ">=10"
},
"funding": {
"url": "https://github.com/chalk/ansi-styles?sponsor=1"
}
},
"node_modules/react-is": {
"version": "18.3.1",
"resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz",
"integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg==",
"license": "MIT"
},
"node_modules/slash": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz",
"integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==",
"license": "MIT",
"engines": {
"node": ">=8"
}
},
"node_modules/stack-utils": {
"version": "2.0.6",
"resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-2.0.6.tgz",
"integrity": "sha512-XlkWvfIm6RmsWtNJx+uqtKLS8eqFbxUg0ZzLXqY0caEy9l7hruX8IpiDnjsLavoBgqCCR71TqWO8MaXYheJ3RQ==",
"license": "MIT",
"dependencies": {
"escape-string-regexp": "^2.0.0"
},
"engines": {
"node": ">=10"
}
},
"node_modules/supports-color": {
"version": "7.2.0",
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
"integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
"license": "MIT",
"dependencies": {
"has-flag": "^4.0.0"
},
"engines": {
"node": ">=8"
}
},
"node_modules/to-regex-range": {
"version": "5.0.1",
"resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz",
"integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==",
"license": "MIT",
"dependencies": {
"is-number": "^7.0.0"
},
"engines": {
"node": ">=8.0"
}
},
"node_modules/undici-types": {
"version": "8.3.0",
"resolved": "https://registry.npmjs.org/undici-types/-/undici-types-8.3.0.tgz",
"integrity": "sha512-j375ScV60dom+YkPFIfTLcOiPxkN/buHz5GobjLhixFuANaNs3C9l4GmrWqejgXWJ7BbJcFYpTEUkS1Ge8bpZQ==",
"license": "MIT"
}
}
}
{
"name": "sample-jest-console-custom",
"version": "1.0.0",
"private": true,
"description": "redirect and format log streams using CustomConsole and NullConsole",
"main": "index.js",
"scripts": {
"test": "node test/contract.js"
},
"dependencies": {
"@jest/console": "29.7.0"
},
"license": "MIT-0"
}
{
"schemaVersion": 1,
"goal": "redirect and format log streams using CustomConsole and NullConsole",
"kind": "HOW",
"packages": [
"pkg:npm/%40jest/console@29.7.0"
],
"symbols": [
"CustomConsole",
"NullConsole"
]
}
'use strict';
const assert = require('assert');
const { Writable } = require('stream');
const {
CustomConsole,
NullConsole,
createMemoryStream,
createCustomConsole,
createNullConsole,
captureCustomStreamOutput
} = require('../index.js');
function testStreamRouting() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const customConsole = createCustomConsole({
stdout: stdoutMem.stream,
stderr: stderrMem.stream
});
// stdout methods
customConsole.log('standard log message');
customConsole.info('informational notice');
customConsole.debug('debug trace');
customConsole.dir({ key: 'val' });
customConsole.dirxml({ tag: 'element' });
// stderr methods
customConsole.warn('warning notice');
customConsole.error('error event');
const stdoutOutput = stdoutMem.getOutput();
const stderrOutput = stderrMem.getOutput();
assert.match(stdoutOutput, /standard log message\n/);
assert.match(stdoutOutput, /informational notice\n/);
assert.match(stdoutOutput, /debug trace\n/);
assert.match(stdoutOutput, /key: 'val'/);
assert.match(stdoutOutput, /tag: 'element'/);
assert.doesNotMatch(stdoutOutput, /warning notice/);
assert.doesNotMatch(stdoutOutput, /error event/);
assert.match(stderrOutput, /warning notice\n/);
assert.match(stderrOutput, /error event\n/);
assert.doesNotMatch(stderrOutput, /standard log message/);
assert.doesNotMatch(stderrOutput, /informational notice/);
}
function testFormatBuffer() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const formatBuffer = (type, message) => `[${type.toUpperCase()}] ${message}`;
const customConsole = createCustomConsole({
stdout: stdoutMem.stream,
stderr: stderrMem.stream,
formatBuffer
});
customConsole.log('custom formatted message');
customConsole.warn('custom formatted warning');
customConsole.error('custom formatted error');
const stdoutOutput = stdoutMem.getOutput();
const stderrOutput = stderrMem.getOutput();
assert.match(stdoutOutput, /\[LOG\] custom formatted message\n/);
assert.match(stderrOutput, /\[WARN\] custom formatted warning\n/);
assert.match(stderrOutput, /\[ERROR\] custom formatted error\n/);
}
function testGrouping() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const customConsole = createCustomConsole({
stdout: stdoutMem.stream,
stderr: stderrMem.stream
});
customConsole.group('Parent Group');
customConsole.log('nested item 1');
customConsole.groupCollapsed('Child Group');
customConsole.log('deeply nested item');
customConsole.groupEnd();
customConsole.log('nested item 2');
customConsole.groupEnd();
customConsole.log('root item');
const stdoutOutput = stdoutMem.getOutput();
assert.match(stdoutOutput, /Parent Group/);
assert.match(stdoutOutput, / nested item 1\n/);
assert.match(stdoutOutput, /Child Group/);
assert.match(stdoutOutput, / deeply nested item\n/);
assert.match(stdoutOutput, / nested item 2\n/);
assert.match(stdoutOutput, /^root item\n/m);
}
function testTimersAndCounters() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const customConsole = createCustomConsole({
stdout: stdoutMem.stream,
stderr: stderrMem.stream
});
customConsole.count('testCounter');
customConsole.count('testCounter');
customConsole.countReset('testCounter');
customConsole.count('testCounter');
customConsole.time('opTimer');
customConsole.timeLog('opTimer', 'step1');
customConsole.timeEnd('opTimer');
const stdoutOutput = stdoutMem.getOutput();
assert.match(stdoutOutput, /testCounter: 1/);
assert.match(stdoutOutput, /testCounter: 2/);
assert.match(stdoutOutput, /opTimer: \d+(\.\d+)?\s*(ms|s)/);
}
function testAssertions() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const customConsole = createCustomConsole({
stdout: stdoutMem.stream,
stderr: stderrMem.stream
});
// Truthy condition must not log anything
customConsole.assert(true, 'truthy condition must not log');
assert.strictEqual(stderrMem.getOutput(), '');
// Falsy condition must log formatted assertion error to stderr without throwing
customConsole.assert(false, 'falsy condition logged');
const stderrOutput = stderrMem.getOutput();
assert.match(stderrOutput, /AssertionError/);
assert.match(stderrOutput, /falsy condition logged/);
}
function testGetBuffer() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const customConsole = createCustomConsole({
stdout: stdoutMem.stream,
stderr: stderrMem.stream
});
customConsole.log('some log entry');
customConsole.error('some error entry');
assert.strictEqual(customConsole.getBuffer(), undefined);
}
function testNullConsoleConstructor() {
// NullConsole requires streams in constructor, otherwise throws ERR_CONSOLE_WRITABLE_STREAM
assert.throws(
() => {
new NullConsole();
},
(err) => {
assert.strictEqual(err.code, 'ERR_CONSOLE_WRITABLE_STREAM');
return true;
}
);
const nullConsole = createNullConsole();
assert.ok(nullConsole instanceof NullConsole);
assert.ok(nullConsole instanceof CustomConsole);
}
function testNullConsoleSilencing() {
const stdoutMem = createMemoryStream();
const stderrMem = createMemoryStream();
const nullConsole = new NullConsole(stdoutMem.stream, stderrMem.stream);
nullConsole.log('silenced log');
nullConsole.info('silenced info');
nullConsole.warn('silenced warn');
nullConsole.error('silenced error');
nullConsole.debug('silenced debug');
nullConsole.assert(false, 'silenced assert');
nullConsole.dir({ a: 1 });
nullConsole.time('timer');
nullConsole.timeLog('timer');
nullConsole.timeEnd('timer');
nullConsole.group('group');
nullConsole.groupCollapsed('collapsed');
nullConsole.groupEnd();
nullConsole.trace('trace');
assert.strictEqual(stdoutMem.getOutput(), '');
assert.strictEqual(stderrMem.getOutput(), '');
assert.strictEqual(nullConsole.getBuffer(), undefined);
}
function testCaptureCustomStreamOutput() {
const result = captureCustomStreamOutput(
(c) => {
c.log('captured stdout');
c.error('captured stderr');
return 42;
},
(type, msg) => `<${type}>${msg}`
);
assert.strictEqual(result.result, 42);
assert.match(result.stdout, /<log>captured stdout\n/);
assert.match(result.stderr, /<error>captured stderr\n/);
}
function runAll() {
testStreamRouting();
testFormatBuffer();
testGrouping();
testTimersAndCounters();
testAssertions();
testGetBuffer();
testNullConsoleConstructor();
testNullConsoleSilencing();
testCaptureCustomStreamOutput();
console.log('Contract tests passed successfully.');
process.exit(0);
}
runAll();
Seeder de origen
anónimo