OpenViSTAI · Agents · Blockchain · Crypto
Menu
OPENVIST RECIPES

Redact selected configuration assignment values with JavaScript

JavaScript

Replace every value assigned to an explicit selected key while preserving the order and literal values of unselected assignments.

JavaScript code excerpt: Redact selected configuration assignment values with JavaScript. Version 0.1.0. Read the full recipe for code, sources and recorded test scope.

Replace every value assigned to an explicit selected key while preserving the order and literal values of unselected assignments. Uses saved stdin text; never reads the real process environment.

Before you start

  • Save the code as redact.cjs and run node redact.cjs with the protocol supplied on stdin. No CLI arguments are accepted. Requires Node.js 22 and only requires node:fs.
  • Provide selector keys, exactly one line containing ---, then KEY=value assignments. Empty lines and lines starting with # are ignored without trimming.
  • Keys must match ASCII [A-Za-z_][A-Za-z0-9_]{0,63}. Selectors must be unique. At most 100 selectors and 100 assignment records are accepted.
  • Input is read from descriptor 0 using readSync with a cumulative maximum of 65537 bytes; inputs larger than 65536 bytes are rejected. Strict UTF-8 decoding retains any BOM so a leading BOM can be explicitly rejected.
  • CR, NUL, other ASCII controls except LF, and DEL are rejected everywhere. The total UTF-8 length of original assignment values, including duplicates, must not exceed 1024 bytes.
  • The complete input is validated before stdout is written. Success emits exactly one JSON object followed by LF, exits 0, and leaves stderr empty. Invalid arguments, input, UTF-8, or stdin reads produce only error: invalid input followed by LF on stderr and exit 2.
  • Example stdin: TOKEN\n---\nTOKEN=example\nLABEL=hello=world\nTOKEN=\n
  • Example stdout: {"assignments":[{"key":"TOKEN","value":"[REDACTED]"},{"key":"LABEL","value":"hello=world"},{"key":"TOKEN","value":"[REDACTED]"}]} followed by LF.

Build and check

  1. Save the example as recipe.cjs.
  2. Prepare input.txt with selectors, a --- separator and literal assignments; use synthetic values while learning.
  3. Run the documented command and inspect the JSON output.
  4. Exit 2 indicates rejected input; no successful JSON result is emitted.

Limits to understand

  • This is a literal LF-only protocol, not general dotenv syntax. Quotes, spaces, backslashes, # characters, and additional equals signs in values are literal.
  • Only explicitly selected keys are redacted. Unselected values remain in output; this is not automatic secret detection or a safe-to-publish certification.
  • Assignment order and duplicates are preserved. No key-name arrays are emitted, so no key-name sorting is applicable.
  • There are no file, environment, network, subprocess, or dynamic-execution operations. Filesystem calls only read stdin and write stdout or stderr through their existing descriptors.
  • Output-write and allocation failures are outside the input-error guarantee.
  • Literal assignment subset only; no quoting rules, export syntax, interpolation, multiline values or general dotenv compatibility.
  • Unselected assignment values are emitted unchanged. Review output before sharing.
  • stdin may block until EOF; input is bounded to 65536 bytes and 100 selector / 100 assignment records. Total assignment-value bytes are limited to 1024.

Run it

node recipe.cjs < input.txt

Example input

TOKEN
---
TOKEN=secret-one
HOST=localhost
TOKEN=secret-two

Expected output

{"assignments":[{"key":"TOKEN","value":"[REDACTED]"},{"key":"HOST","value":"localhost"},{"key":"TOKEN","value":"[REDACTED]"}]}
INSPECT THE SCRIPT

Inspect, copy and run the documented checks.

This browser preview builds code locally. It does not contact an API or run the code.

Default example ready.

JavaScript example
'use strict';

const fs = require('node:fs');

function writeAll(fd, text) {
  const bytes = Buffer.from(text, 'utf8');
  let offset = 0;
  while (offset < bytes.length) {
    const written = fs.writeSync(fd, bytes, offset, bytes.length - offset);
    if (written <= 0) throw new Error('Output write failure');
    offset += written;
  }
}

function invalid() {
  throw new Error('Invalid input');
}

function readAndValidate() {
  if (process.argv.length !== 2) invalid();

  const buffer = Buffer.alloc(65537);
  let length = 0;
  while (length < buffer.length) {
    const count = fs.readSync(0, buffer, length, buffer.length - length, null);
    if (count === 0) break;
    length += count;
  }
  if (length > 65536) invalid();

  const decoder = new TextDecoder('utf-8', { fatal: true, ignoreBOM: true });
  const text = decoder.decode(buffer.subarray(0, length));
  if (text.charCodeAt(0) === 0xFEFF) invalid();
  if (/[\u0000-\u0009\u000B-\u001F\u007F]/.test(text)) invalid();

  const keyPattern = /^[A-Za-z_][A-Za-z0-9_]{0,63}$/;
  const selectors = new Set();
  const assignments = [];
  let separatorSeen = false;
  let assignmentCount = 0;
  let valueBytes = 0;

  for (const line of text.split('\n')) {
    if (line === '' || line.startsWith('#')) continue;

    if (line === '---') {
      if (separatorSeen) invalid();
      separatorSeen = true;
      continue;
    }

    if (!separatorSeen) {
      if (!keyPattern.test(line)) invalid();
      if (selectors.has(line) || selectors.size >= 100) invalid();
      selectors.add(line);
      continue;
    }

    assignmentCount += 1;
    if (assignmentCount > 100) invalid();
    const equals = line.indexOf('=');
    if (equals < 0) invalid();
    const key = line.slice(0, equals);
    const value = line.slice(equals + 1);
    if (!keyPattern.test(key)) invalid();
    valueBytes += Buffer.byteLength(value, 'utf8');
    if (valueBytes > 1024) invalid();
    assignments.push({
      key,
      value: selectors.has(key) ? '[REDACTED]' : value
    });
  }

  if (!separatorSeen) invalid();
  return { assignments };
}

let result;
try {
  result = readAndValidate();
} catch {
  writeAll(2, 'error: invalid input\n');
  process.exit(2);
}

writeAll(1, JSON.stringify(result) + '\n');
What to verify after running
  • Check the supplied example against its expected output.
  • Check all selected duplicate values are replaced; review unselected values before sharing.
  • Confirm invalid syntax and extra arguments fail without input values in diagnostics.

Request or format preview

Illustrative preview. No provider response, price or balance is fetched.

Change a setting to inspect the preview.

Official sources and related profiles

    Code license: MIT. Keep the license notice with your copy.

    Example version 0.1.0 · Documentation reviewed 2026-10-16.

    Release requires six primary fixtures, 29 original supplementary checks and one grouped Unicode regression containing ten full-program runs. Actual evidence must be recorded against the candidate. Bounded checks, not exhaustive proof.