mirror of
https://github.com/nodejs/node.git
synced 2025-12-28 07:50:41 +00:00
PR-URL: https://github.com/nodejs/node/pull/61006 Reviewed-By: Luigi Pinca <luigipinca@gmail.com> Reviewed-By: Colin Ihrig <cjihrig@gmail.com> Reviewed-By: Erick Wendel <erick.workspace@gmail.com>
127 lines
4.6 KiB
JavaScript
127 lines
4.6 KiB
JavaScript
'use strict';
|
|
const common = require('../common');
|
|
if (process.config.variables.node_without_node_options)
|
|
common.skip('missing NODE_OPTIONS support');
|
|
|
|
// Test options specified by env variable.
|
|
|
|
const assert = require('assert');
|
|
const fs = require('fs');
|
|
const path = require('path');
|
|
|
|
const rootDir = path.resolve(__dirname, '..', '..');
|
|
const cliMd = path.join(rootDir, 'doc', 'api', 'cli.md');
|
|
const cliText = fs.readFileSync(cliMd, { encoding: 'utf8' });
|
|
|
|
const internalApiMd = path.join(rootDir, 'doc', 'contributing', 'internal-api.md');
|
|
const internalApiText = fs.readFileSync(internalApiMd, { encoding: 'utf8' });
|
|
|
|
const nodeOptionsCC = fs.readFileSync(path.resolve(rootDir, 'src', 'node_options.cc'), 'utf8');
|
|
const addOptionRE = /AddOption[\s\n\r]*\([\s\n\r]*"([^"]+)"(.*?)\);/gs;
|
|
|
|
const nodeOptionsText = cliText.match(/<!-- node-options-node start -->(.*)<!-- node-options-others end -->/s)[1];
|
|
const v8OptionsText = cliText.match(/<!-- v8-options start -->(.*)<!-- v8-options end -->/s)[1];
|
|
|
|
const manPage = path.join(rootDir, 'doc', 'node.1');
|
|
const manPageText = fs.readFileSync(manPage, { encoding: 'utf8' });
|
|
|
|
// Documented in /doc/api/deprecations.md
|
|
const deprecated = [
|
|
'--debug',
|
|
'--debug-brk',
|
|
];
|
|
|
|
|
|
const manPagesOptions = new Set();
|
|
|
|
for (const [, envVar] of manPageText.matchAll(/\.It Fl (-[a-zA-Z0-9._-]+)/g)) {
|
|
manPagesOptions.add(envVar);
|
|
}
|
|
|
|
for (const [, envVar, config] of nodeOptionsCC.matchAll(addOptionRE)) {
|
|
const hasTrueAsDefaultValue = /,\s*(?:true|HAVE_[A-Z_]+)\s*$/.test(config);
|
|
const isInNodeOption = config.includes('kAllowedInEnvvar') && !config.includes('kDisallowedInEnvvar');
|
|
const isV8Option = config.includes('V8Option{}');
|
|
const isNoOp = config.includes('NoOp{}');
|
|
|
|
if (
|
|
envVar.startsWith('[') ||
|
|
deprecated.includes(envVar) ||
|
|
isNoOp
|
|
) {
|
|
// assert(!manPagesOptions.has(envVar.slice(1)), `Option ${envVar} should not be documented`)
|
|
manPagesOptions.delete(envVar.slice(1));
|
|
continue;
|
|
}
|
|
|
|
// Internal API options are documented in /doc/contributing/internal-api.md
|
|
if (new RegExp(`####.*\`${RegExp.escape(envVar)}[[=\\s\\b\`]`).test(internalApiText)) {
|
|
manPagesOptions.delete(envVar.slice(1));
|
|
continue;
|
|
}
|
|
|
|
// CLI options
|
|
if (!isV8Option && !hasTrueAsDefaultValue) {
|
|
if (!new RegExp(`###.*\`${RegExp.escape(envVar)}[[=\\s\\b\`]`).test(cliText)) {
|
|
assert.fail(`Should have option ${envVar} documented`);
|
|
} else {
|
|
manPagesOptions.delete(envVar.slice(1));
|
|
}
|
|
}
|
|
|
|
if (!hasTrueAsDefaultValue && new RegExp(`###.*\`--no${RegExp.escape(envVar.slice(1))}[[=\\s\\b\`]`).test(cliText)) {
|
|
assert.fail(`Should not have option --no${envVar.slice(1)} documented`);
|
|
}
|
|
|
|
if (!isV8Option && hasTrueAsDefaultValue) {
|
|
if (!new RegExp(`###.*\`--no${RegExp.escape(envVar.slice(1))}[[=\\s\\b\`]`).test(cliText)) {
|
|
assert.fail(`Should have option --no${envVar.slice(1)} documented`);
|
|
} else {
|
|
manPagesOptions.delete(`-no${envVar.slice(1)}`);
|
|
}
|
|
}
|
|
|
|
// NODE_OPTIONS
|
|
if (isInNodeOption && !hasTrueAsDefaultValue &&
|
|
!new RegExp(`\`${RegExp.escape(envVar)}\``).test(nodeOptionsText)) {
|
|
assert.fail(`Should have option ${envVar} in NODE_OPTIONS documented`);
|
|
}
|
|
|
|
if (isInNodeOption && hasTrueAsDefaultValue && !new RegExp(`\`--no${RegExp.escape(envVar.slice(1))}\``).test(cliText)) {
|
|
assert.fail(`Should have option --no${envVar.slice(1)} in NODE_OPTIONS documented`);
|
|
}
|
|
|
|
if (!hasTrueAsDefaultValue && new RegExp(`\`--no${RegExp.escape(envVar.slice(1))}\``).test(cliText)) {
|
|
assert.fail(`Should not have option --no${envVar.slice(1)} in NODE_OPTIONS documented`);
|
|
}
|
|
|
|
// V8 options
|
|
if (isV8Option) {
|
|
if (!new RegExp(`###.*\`${RegExp.escape(envVar)}[[=\\s\\b\`]`).test(v8OptionsText)) {
|
|
assert.fail(`Should have option ${envVar} in V8 options documented`);
|
|
} else {
|
|
manPagesOptions.delete(envVar.slice(1));
|
|
}
|
|
}
|
|
}
|
|
|
|
{
|
|
const sections = /^## (.+)$/mg;
|
|
const cliOptionPattern = /^### (?:`-\w.*`, )?`([^`]+)`/mg;
|
|
let match;
|
|
let previousIndex = 0;
|
|
do {
|
|
const sectionTitle = match?.[1];
|
|
match = sections.exec(cliText);
|
|
const filteredCLIText = cliText.slice(previousIndex, match?.index);
|
|
const options = Array.from(filteredCLIText.matchAll(cliOptionPattern), (match) => match[1]);
|
|
assert.deepStrictEqual(options, options.toSorted(), `doc/api/cli.md ${sectionTitle} subsections are not in alphabetical order`);
|
|
previousIndex = match?.index;
|
|
} while (match);
|
|
}
|
|
|
|
// add alias handling
|
|
manPagesOptions.delete('-trace-events-enabled');
|
|
|
|
assert.strictEqual(manPagesOptions.size, 0, `Man page options not documented: ${[...manPagesOptions]}`);
|