WIP: bootstrap and partial real Solana watcher implementation

This commit is contained in:
2026-08-16 09:17:45 +00:00
commit dc23412c3f
7232 changed files with 1687637 additions and 0 deletions

View File

@@ -0,0 +1,107 @@
import * as util from "../core/util.js";
const error = () => {
const Sizable = {
string: { unit: "caràcters", verb: "contenir" },
file: { unit: "bytes", verb: "contenir" },
array: { unit: "elements", verb: "contenir" },
set: { unit: "elements", verb: "contenir" },
};
function getSizing(origin) {
return Sizable[origin] ?? null;
}
const FormatDictionary = {
regex: "entrada",
email: "adreça electrònica",
url: "URL",
emoji: "emoji",
uuid: "UUID",
uuidv4: "UUIDv4",
uuidv6: "UUIDv6",
nanoid: "nanoid",
guid: "GUID",
cuid: "cuid",
cuid2: "cuid2",
ulid: "ULID",
xid: "XID",
ksuid: "KSUID",
datetime: "data i hora ISO",
date: "data ISO",
time: "hora ISO",
duration: "durada ISO",
ipv4: "adreça IPv4",
ipv6: "adreça IPv6",
cidrv4: "rang IPv4",
cidrv6: "rang IPv6",
base64: "cadena codificada en base64",
base64url: "cadena codificada en base64url",
json_string: "cadena JSON",
e164: "número E.164",
jwt: "JWT",
template_literal: "entrada",
};
const TypeDictionary = {
nan: "NaN",
};
return (issue) => {
switch (issue.code) {
case "invalid_type": {
const expected = TypeDictionary[issue.expected] ?? issue.expected;
const receivedType = util.parsedType(issue.input);
const received = TypeDictionary[receivedType] ?? receivedType;
if (/^[A-Z]/.test(issue.expected)) {
return `Tipus invàlid: s'esperava instanceof ${issue.expected}, s'ha rebut ${received}`;
}
return `Tipus invàlid: s'esperava ${expected}, s'ha rebut ${received}`;
}
case "invalid_value":
if (issue.values.length === 1)
return `Valor invàlid: s'esperava ${util.stringifyPrimitive(issue.values[0])}`;
return `Opció invàlida: s'esperava una de ${util.joinValues(issue.values, " o ")}`;
case "too_big": {
const adj = issue.inclusive ? "com a màxim" : "menys de";
const sizing = getSizing(issue.origin);
if (sizing)
return `Massa gran: s'esperava que ${issue.origin ?? "el valor"} contingués ${adj} ${issue.maximum.toString()} ${sizing.unit ?? "elements"}`;
return `Massa gran: s'esperava que ${issue.origin ?? "el valor"} fos ${adj} ${issue.maximum.toString()}`;
}
case "too_small": {
const adj = issue.inclusive ? "com a mínim" : "més de";
const sizing = getSizing(issue.origin);
if (sizing) {
return `Massa petit: s'esperava que ${issue.origin} contingués ${adj} ${issue.minimum.toString()} ${sizing.unit}`;
}
return `Massa petit: s'esperava que ${issue.origin} fos ${adj} ${issue.minimum.toString()}`;
}
case "invalid_format": {
const _issue = issue;
if (_issue.format === "starts_with") {
return `Format invàlid: ha de començar amb "${_issue.prefix}"`;
}
if (_issue.format === "ends_with")
return `Format invàlid: ha d'acabar amb "${_issue.suffix}"`;
if (_issue.format === "includes")
return `Format invàlid: ha d'incloure "${_issue.includes}"`;
if (_issue.format === "regex")
return `Format invàlid: ha de coincidir amb el patró ${_issue.pattern}`;
return `Format invàlid per a ${FormatDictionary[_issue.format] ?? issue.format}`;
}
case "not_multiple_of":
return `Número invàlid: ha de ser múltiple de ${issue.divisor}`;
case "unrecognized_keys":
return `Clau${issue.keys.length > 1 ? "s" : ""} no reconeguda${issue.keys.length > 1 ? "s" : ""}: ${util.joinValues(issue.keys, ", ")}`;
case "invalid_key":
return `Clau invàlida a ${issue.origin}`;
case "invalid_union":
return "Entrada invàlida"; // Could also be "Tipus d'unió invàlid" but "Entrada invàlida" is more general
case "invalid_element":
return `Element invàlid a ${issue.origin}`;
default:
return `Entrada invàlida`;
}
};
};
export default function () {
return {
localeError: error(),
};
}

View File

@@ -0,0 +1,374 @@
/**
* @fileoverview Disallows or enforces spaces inside of parentheses.
* @author Jonathan Rajavuori
* @deprecated in ESLint v8.53.0
*/
"use strict";
const astUtils = require("./utils/ast-utils");
//------------------------------------------------------------------------------
// Rule Definition
//------------------------------------------------------------------------------
/** @type {import('../types').Rule.RuleModule} */
module.exports = {
meta: {
deprecated: {
message: "Formatting rules are being moved out of ESLint core.",
url: "https://eslint.org/blog/2023/10/deprecating-formatting-rules/",
deprecatedSince: "8.53.0",
availableUntil: "11.0.0",
replacedBy: [
{
message:
"ESLint Stylistic now maintains deprecated stylistic core rules.",
url: "https://eslint.style/guide/migration",
plugin: {
name: "@stylistic/eslint-plugin",
url: "https://eslint.style",
},
rule: {
name: "space-in-parens",
url: "https://eslint.style/rules/space-in-parens",
},
},
],
},
type: "layout",
docs: {
description: "Enforce consistent spacing inside parentheses",
recommended: false,
url: "https://eslint.org/docs/latest/rules/space-in-parens",
},
fixable: "whitespace",
schema: [
{
enum: ["always", "never"],
},
{
type: "object",
properties: {
exceptions: {
type: "array",
items: {
enum: ["{}", "[]", "()", "empty"],
},
uniqueItems: true,
},
},
additionalProperties: false,
},
],
messages: {
missingOpeningSpace: "There must be a space after this paren.",
missingClosingSpace: "There must be a space before this paren.",
rejectedOpeningSpace: "There should be no space after this paren.",
rejectedClosingSpace: "There should be no space before this paren.",
},
},
create(context) {
const ALWAYS = context.options[0] === "always",
exceptionsArrayOptions =
(context.options[1] && context.options[1].exceptions) || [],
options = {};
let exceptions;
if (exceptionsArrayOptions.length) {
options.braceException = exceptionsArrayOptions.includes("{}");
options.bracketException = exceptionsArrayOptions.includes("[]");
options.parenException = exceptionsArrayOptions.includes("()");
options.empty = exceptionsArrayOptions.includes("empty");
}
/**
* Produces an object with the opener and closer exception values
* @returns {Object} `openers` and `closers` exception values
* @private
*/
function getExceptions() {
const openers = [],
closers = [];
if (options.braceException) {
openers.push("{");
closers.push("}");
}
if (options.bracketException) {
openers.push("[");
closers.push("]");
}
if (options.parenException) {
openers.push("(");
closers.push(")");
}
if (options.empty) {
openers.push(")");
closers.push("(");
}
return {
openers,
closers,
};
}
//--------------------------------------------------------------------------
// Helpers
//--------------------------------------------------------------------------
const sourceCode = context.sourceCode;
/**
* Determines if a token is one of the exceptions for the opener paren
* @param {Object} token The token to check
* @returns {boolean} True if the token is one of the exceptions for the opener paren
*/
function isOpenerException(token) {
return exceptions.openers.includes(token.value);
}
/**
* Determines if a token is one of the exceptions for the closer paren
* @param {Object} token The token to check
* @returns {boolean} True if the token is one of the exceptions for the closer paren
*/
function isCloserException(token) {
return exceptions.closers.includes(token.value);
}
/**
* Determines if an opening paren is immediately followed by a required space
* @param {Object} openingParenToken The paren token
* @param {Object} tokenAfterOpeningParen The token after it
* @returns {boolean} True if the opening paren is missing a required space
*/
function openerMissingSpace(openingParenToken, tokenAfterOpeningParen) {
if (
sourceCode.isSpaceBetween(
openingParenToken,
tokenAfterOpeningParen,
)
) {
return false;
}
if (
!options.empty &&
astUtils.isClosingParenToken(tokenAfterOpeningParen)
) {
return false;
}
if (ALWAYS) {
return !isOpenerException(tokenAfterOpeningParen);
}
return isOpenerException(tokenAfterOpeningParen);
}
/**
* Determines if an opening paren is immediately followed by a disallowed space
* @param {Object} openingParenToken The paren token
* @param {Object} tokenAfterOpeningParen The token after it
* @returns {boolean} True if the opening paren has a disallowed space
*/
function openerRejectsSpace(openingParenToken, tokenAfterOpeningParen) {
if (
!astUtils.isTokenOnSameLine(
openingParenToken,
tokenAfterOpeningParen,
)
) {
return false;
}
if (tokenAfterOpeningParen.type === "Line") {
return false;
}
if (
!sourceCode.isSpaceBetween(
openingParenToken,
tokenAfterOpeningParen,
)
) {
return false;
}
if (ALWAYS) {
return isOpenerException(tokenAfterOpeningParen);
}
return !isOpenerException(tokenAfterOpeningParen);
}
/**
* Determines if a closing paren is immediately preceded by a required space
* @param {Object} tokenBeforeClosingParen The token before the paren
* @param {Object} closingParenToken The paren token
* @returns {boolean} True if the closing paren is missing a required space
*/
function closerMissingSpace(
tokenBeforeClosingParen,
closingParenToken,
) {
if (
sourceCode.isSpaceBetween(
tokenBeforeClosingParen,
closingParenToken,
)
) {
return false;
}
if (
!options.empty &&
astUtils.isOpeningParenToken(tokenBeforeClosingParen)
) {
return false;
}
if (ALWAYS) {
return !isCloserException(tokenBeforeClosingParen);
}
return isCloserException(tokenBeforeClosingParen);
}
/**
* Determines if a closer paren is immediately preceded by a disallowed space
* @param {Object} tokenBeforeClosingParen The token before the paren
* @param {Object} closingParenToken The paren token
* @returns {boolean} True if the closing paren has a disallowed space
*/
function closerRejectsSpace(
tokenBeforeClosingParen,
closingParenToken,
) {
if (
!astUtils.isTokenOnSameLine(
tokenBeforeClosingParen,
closingParenToken,
)
) {
return false;
}
if (
!sourceCode.isSpaceBetween(
tokenBeforeClosingParen,
closingParenToken,
)
) {
return false;
}
if (ALWAYS) {
return isCloserException(tokenBeforeClosingParen);
}
return !isCloserException(tokenBeforeClosingParen);
}
//--------------------------------------------------------------------------
// Public
//--------------------------------------------------------------------------
return {
Program: function checkParenSpaces(node) {
exceptions = getExceptions();
const tokens = sourceCode.tokensAndComments;
tokens.forEach((token, i) => {
const prevToken = tokens[i - 1];
const nextToken = tokens[i + 1];
// if token is not an opening or closing paren token, do nothing
if (
!astUtils.isOpeningParenToken(token) &&
!astUtils.isClosingParenToken(token)
) {
return;
}
// if token is an opening paren and is not followed by a required space
if (
token.value === "(" &&
openerMissingSpace(token, nextToken)
) {
context.report({
node,
loc: token.loc,
messageId: "missingOpeningSpace",
fix(fixer) {
return fixer.insertTextAfter(token, " ");
},
});
}
// if token is an opening paren and is followed by a disallowed space
if (
token.value === "(" &&
openerRejectsSpace(token, nextToken)
) {
context.report({
node,
loc: {
start: token.loc.end,
end: nextToken.loc.start,
},
messageId: "rejectedOpeningSpace",
fix(fixer) {
return fixer.removeRange([
token.range[1],
nextToken.range[0],
]);
},
});
}
// if token is a closing paren and is not preceded by a required space
if (
token.value === ")" &&
closerMissingSpace(prevToken, token)
) {
context.report({
node,
loc: token.loc,
messageId: "missingClosingSpace",
fix(fixer) {
return fixer.insertTextBefore(token, " ");
},
});
}
// if token is a closing paren and is preceded by a disallowed space
if (
token.value === ")" &&
closerRejectsSpace(prevToken, token)
) {
context.report({
node,
loc: {
start: prevToken.loc.end,
end: token.loc.start,
},
messageId: "rejectedClosingSpace",
fix(fixer) {
return fixer.removeRange([
prevToken.range[1],
token.range[0],
]);
},
});
}
});
},
};
},
};

View File

@@ -0,0 +1,2 @@
import type { TSESTree } from '@typescript-eslint/utils';
export declare function isNullLiteral(i: TSESTree.Node): i is TSESTree.NullLiteral;

View File

@@ -0,0 +1,93 @@
'use strict'
const test = require('node:test')
const assert = require('node:assert')
const os = require('node:os')
const { sink, once } = require('./helper')
const pino = require('../')
const { pid } = process
const hostname = os.hostname()
function testEscape (ch, key) {
test('correctly escape ' + ch, async () => {
const stream = sink()
const instance = pino({
name: 'hello'
}, stream)
instance.fatal('this contains ' + key)
const result = await once(stream, 'data')
delete result.time
assert.deepEqual(result, {
pid,
hostname,
level: 60,
name: 'hello',
msg: 'this contains ' + key
})
})
}
testEscape('\\n', '\n')
testEscape('\\/', '/')
testEscape('\\\\', '\\')
testEscape('\\r', '\r')
testEscape('\\t', '\t')
testEscape('\\b', '\b')
const toEscape = [
'\u0000', // NUL Null character
'\u0001', // SOH Start of Heading
'\u0002', // STX Start of Text
'\u0003', // ETX End-of-text character
'\u0004', // EOT End-of-transmission character
'\u0005', // ENQ Enquiry character
'\u0006', // ACK Acknowledge character
'\u0007', // BEL Bell character
'\u0008', // BS Backspace
'\u0009', // HT Horizontal tab
'\u000A', // LF Line feed
'\u000B', // VT Vertical tab
'\u000C', // FF Form feed
'\u000D', // CR Carriage return
'\u000E', // SO Shift Out
'\u000F', // SI Shift In
'\u0010', // DLE Data Link Escape
'\u0011', // DC1 Device Control 1
'\u0012', // DC2 Device Control 2
'\u0013', // DC3 Device Control 3
'\u0014', // DC4 Device Control 4
'\u0015', // NAK Negative-acknowledge character
'\u0016', // SYN Synchronous Idle
'\u0017', // ETB End of Transmission Block
'\u0018', // CAN Cancel character
'\u0019', // EM End of Medium
'\u001A', // SUB Substitute character
'\u001B', // ESC Escape character
'\u001C', // FS File Separator
'\u001D', // GS Group Separator
'\u001E', // RS Record Separator
'\u001F' // US Unit Separator
]
toEscape.forEach((key) => {
testEscape(JSON.stringify(key), key)
})
test('correctly escape `hello \\u001F world \\n \\u0022`', async () => {
const stream = sink()
const instance = pino({
name: 'hello'
}, stream)
instance.fatal('hello \u001F world \n \u0022')
const result = await once(stream, 'data')
delete result.time
assert.deepEqual(result, {
pid,
hostname,
level: 60,
name: 'hello',
msg: 'hello \u001F world \n \u0022'
})
})

View File

@@ -0,0 +1,3 @@
import { type ZodErrorMap } from "../ZodError.js";
declare const errorMap: ZodErrorMap;
export default errorMap;

View File

@@ -0,0 +1,11 @@
export * from './AST';
export * from './Config';
export * from './ESLint';
export * from './Linter';
export * from './Parser';
export * from './ParserOptions';
export * from './Processor';
export * from './Rule';
export * from './RuleTester';
export * from './Scope';
export * from './SourceCode';

View File

@@ -0,0 +1 @@
{"version":3,"file":"montgomery.d.ts","sourceRoot":"","sources":["../src/abstract/montgomery.ts"],"names":[],"mappings":"AAgBA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAM/C,KAAK,GAAG,GAAG,MAAM,GAAG,UAAU,CAAC;AAE/B,MAAM,MAAM,SAAS,GAAG;IACtB,CAAC,EAAE,MAAM,CAAC;IACV,IAAI,EAAE,QAAQ,GAAG,MAAM,CAAC;IACxB,iBAAiB,EAAE,CAAC,KAAK,EAAE,UAAU,KAAK,UAAU,CAAC;IACrD,UAAU,EAAE,CAAC,CAAC,EAAE,MAAM,KAAK,MAAM,CAAC;IAClC,WAAW,CAAC,EAAE,CAAC,WAAW,CAAC,EAAE,MAAM,KAAK,UAAU,CAAC;CACpD,CAAC;AAEF,MAAM,MAAM,cAAc,GAAG;IAC3B,UAAU,EAAE,CAAC,MAAM,EAAE,GAAG,EAAE,CAAC,EAAE,GAAG,KAAK,UAAU,CAAC;IAChD,cAAc,EAAE,CAAC,MAAM,EAAE,GAAG,KAAK,UAAU,CAAC;IAC5C,eAAe,EAAE,CAAC,UAAU,EAAE,GAAG,EAAE,UAAU,EAAE,GAAG,KAAK,UAAU,CAAC;IAClE,YAAY,EAAE,CAAC,SAAS,EAAE,GAAG,KAAK,UAAU,CAAC;IAC7C,KAAK,EAAE;QACL,eAAe,EAAE,MAAM,UAAU,CAAC;QAClC,wCAAwC;QACxC,gBAAgB,EAAE,MAAM,UAAU,CAAC;KACpC,CAAC;IACF,OAAO,EAAE,UAAU,CAAC;IACpB,OAAO,EAAE,YAAY,CAAC;IACtB,MAAM,EAAE,CAAC,IAAI,CAAC,EAAE,UAAU,KAAK;QAAE,SAAS,EAAE,UAAU,CAAC;QAAC,SAAS,EAAE,UAAU,CAAA;KAAE,CAAC;CACjF,CAAC;AACF,MAAM,MAAM,OAAO,GAAG,cAAc,CAAC;AAUrC,wBAAgB,UAAU,CAAC,QAAQ,EAAE,SAAS,GAAG,cAAc,CAyI9D"}

View File

@@ -0,0 +1,583 @@
/**
* @fileoverview A module that filters reported problems based on `eslint-disable` and `eslint-enable` comments
* @author Teddy Katz
*/
"use strict";
//------------------------------------------------------------------------------
// Typedefs
//------------------------------------------------------------------------------
/** @typedef {import("../types").Linter.LintMessage} LintMessage */
/** @typedef {import("@eslint/core").Language} Language */
/** @typedef {import("@eslint/core").Position} Position */
/** @typedef {import("@eslint/core").RulesConfig} RulesConfig */
//------------------------------------------------------------------------------
// Module Definition
//------------------------------------------------------------------------------
const escapeRegExp = require("escape-string-regexp");
const { Config } = require("../config/config.js");
/**
* Compares the locations of two objects in a source file
* @param {Position} itemA The first object
* @param {Position} itemB The second object
* @returns {number} A value less than 1 if itemA appears before itemB in the source file, greater than 1 if
* itemA appears after itemB in the source file, or 0 if itemA and itemB have the same location.
*/
function compareLocations(itemA, itemB) {
return itemA.line - itemB.line || itemA.column - itemB.column;
}
/**
* Groups a set of directives into sub-arrays by their parent comment.
* @param {Iterable<Directive>} directives Unused directives to be removed.
* @returns {Directive[][]} Directives grouped by their parent comment.
*/
function groupByParentDirective(directives) {
const groups = new Map();
for (const directive of directives) {
const {
unprocessedDirective: { parentDirective },
} = directive;
if (groups.has(parentDirective)) {
groups.get(parentDirective).push(directive);
} else {
groups.set(parentDirective, [directive]);
}
}
return [...groups.values()];
}
/**
* Creates removal details for a set of directives within the same comment.
* @param {Directive[]} directives Unused directives to be removed.
* @param {{node: Token, value: string}} parentDirective Data about the backing directive.
* @param {SourceCode} sourceCode The source code object for the file being linted.
* @returns {{ description, fix, unprocessedDirective }[]} Details for later creation of output Problems.
*/
function createIndividualDirectivesRemoval(
directives,
parentDirective,
sourceCode,
) {
/*
* Get the list of the rules text without any surrounding whitespace. In order to preserve the original
* formatting, we don't want to change that whitespace.
*
* // eslint-disable-line rule-one , rule-two , rule-three -- comment
* ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
*/
const listText = parentDirective.value.trim();
// Calculate where it starts in the source code text
const listStart = sourceCode.text.indexOf(
listText,
sourceCode.getRange(parentDirective.node)[0],
);
/*
* We can assume that `listText` contains multiple elements.
* Otherwise, this function wouldn't be called - if there is
* only one rule in the list, then the whole comment must be removed.
*/
return directives.map(directive => {
const { ruleId } = directive;
const regex = new RegExp(
String.raw`(?:^|\s*,\s*)(?<quote>['"]?)${escapeRegExp(ruleId)}\k<quote>(?:\s*,\s*|$)`,
"u",
);
const match = regex.exec(listText);
const matchedText = match[0];
const matchStart = listStart + match.index;
const matchEnd = matchStart + matchedText.length;
const firstIndexOfComma = matchedText.indexOf(",");
const lastIndexOfComma = matchedText.lastIndexOf(",");
let removalStart, removalEnd;
if (firstIndexOfComma !== lastIndexOfComma) {
/*
* Since there are two commas, this must one of the elements in the middle of the list.
* Matched range starts where the previous rule name ends, and ends where the next rule name starts.
*
* // eslint-disable-line rule-one , rule-two , rule-three -- comment
* ^^^^^^^^^^^^^^
*
* We want to remove only the content between the two commas, and also one of the commas.
*
* // eslint-disable-line rule-one , rule-two , rule-three -- comment
* ^^^^^^^^^^^
*/
removalStart = matchStart + firstIndexOfComma;
removalEnd = matchStart + lastIndexOfComma;
} else {
/*
* This is either the first element or the last element.
*
* If this is the first element, matched range starts where the first rule name starts
* and ends where the second rule name starts. This is exactly the range we want
* to remove so that the second rule name will start where the first one was starting
* and thus preserve the original formatting.
*
* // eslint-disable-line rule-one , rule-two , rule-three -- comment
* ^^^^^^^^^^^
*
* Similarly, if this is the last element, we've already matched the range we want to
* remove. The previous rule name will end where the last one was ending, relative
* to the content on the right side.
*
* // eslint-disable-line rule-one , rule-two , rule-three -- comment
* ^^^^^^^^^^^^^
*/
removalStart = matchStart;
removalEnd = matchEnd;
}
return {
description: `'${ruleId}'`,
fix: {
range: [removalStart, removalEnd],
text: "",
},
unprocessedDirective: directive.unprocessedDirective,
};
});
}
/**
* Creates a description of deleting an entire unused disable directive.
* @param {Directive[]} directives Unused directives to be removed.
* @param {Token} node The backing Comment token.
* @param {SourceCode} sourceCode The source code object for the file being linted.
* @returns {{ description, fix, unprocessedDirective }} Details for later creation of an output problem.
*/
function createDirectiveRemoval(directives, node, sourceCode) {
const range = sourceCode.getRange(node);
const ruleIds = directives
.filter(directive => directive.ruleId)
.map(directive => `'${directive.ruleId}'`);
return {
description:
ruleIds.length <= 2
? ruleIds.join(" or ")
: `${ruleIds.slice(0, ruleIds.length - 1).join(", ")}, or ${ruleIds.at(-1)}`,
fix: {
range,
text: " ",
},
unprocessedDirective: directives[0].unprocessedDirective,
};
}
/**
* Parses details from directives to create output Problems.
* @param {Iterable<Directive>} allDirectives Unused directives to be removed.
* @param {SourceCode} sourceCode The source code object for the file being linted.
* @returns {{ description, fix, unprocessedDirective }[]} Details for later creation of output Problems.
*/
function processUnusedDirectives(allDirectives, sourceCode) {
const directiveGroups = groupByParentDirective(allDirectives);
return directiveGroups.flatMap(directives => {
const { parentDirective } = directives[0].unprocessedDirective;
const remainingRuleIds = new Set(parentDirective.ruleIds);
for (const directive of directives) {
remainingRuleIds.delete(directive.ruleId);
}
return remainingRuleIds.size
? createIndividualDirectivesRemoval(
directives,
parentDirective,
sourceCode,
)
: [
createDirectiveRemoval(
directives,
parentDirective.node,
sourceCode,
),
];
});
}
/**
* Collect eslint-enable comments that are removing suppressions by eslint-disable comments.
* @param {Directive[]} directives The directives to check.
* @returns {Set<Directive>} The used eslint-enable comments
*/
function collectUsedEnableDirectives(directives) {
/**
* A Map of `eslint-enable` keyed by ruleIds that may be marked as used.
* If `eslint-enable` does not have a ruleId, the key will be `null`.
* @type {Map<string|null, Directive>}
*/
const enabledRules = new Map();
/**
* A Set of `eslint-enable` marked as used.
* It is also the return value of `collectUsedEnableDirectives` function.
* @type {Set<Directive>}
*/
const usedEnableDirectives = new Set();
/*
* Checks the directives backwards to see if the encountered `eslint-enable` is used by the previous `eslint-disable`,
* and if so, stores the `eslint-enable` in `usedEnableDirectives`.
*/
for (let index = directives.length - 1; index >= 0; index--) {
const directive = directives[index];
if (directive.type === "disable") {
if (enabledRules.size === 0) {
continue;
}
if (directive.ruleId === null) {
// If encounter `eslint-disable` without ruleId,
// mark all `eslint-enable` currently held in enabledRules as used.
// e.g.
// /* eslint-disable */ <- current directive
// /* eslint-enable rule-id1 */ <- used
// /* eslint-enable rule-id2 */ <- used
// /* eslint-enable */ <- used
for (const enableDirective of enabledRules.values()) {
usedEnableDirectives.add(enableDirective);
}
enabledRules.clear();
} else {
const enableDirective = enabledRules.get(directive.ruleId);
if (enableDirective) {
// If encounter `eslint-disable` with ruleId, and there is an `eslint-enable` with the same ruleId in enabledRules,
// mark `eslint-enable` with ruleId as used.
// e.g.
// /* eslint-disable rule-id */ <- current directive
// /* eslint-enable rule-id */ <- used
usedEnableDirectives.add(enableDirective);
} else {
const enabledDirectiveWithoutRuleId =
enabledRules.get(null);
if (enabledDirectiveWithoutRuleId) {
// If encounter `eslint-disable` with ruleId, and there is no `eslint-enable` with the same ruleId in enabledRules,
// mark `eslint-enable` without ruleId as used.
// e.g.
// /* eslint-disable rule-id */ <- current directive
// /* eslint-enable */ <- used
usedEnableDirectives.add(enabledDirectiveWithoutRuleId);
}
}
}
} else if (directive.type === "enable") {
if (directive.ruleId === null) {
// If encounter `eslint-enable` without ruleId, the `eslint-enable` that follows it are unused.
// So clear enabledRules.
// e.g.
// /* eslint-enable */ <- current directive
// /* eslint-enable rule-id *// <- unused
// /* eslint-enable */ <- unused
enabledRules.clear();
enabledRules.set(null, directive);
} else {
enabledRules.set(directive.ruleId, directive);
}
}
}
return usedEnableDirectives;
}
/**
* This is the same as the exported function, except that it
* doesn't handle disable-line and disable-next-line directives, and it always reports unused
* disable directives.
* @param {Object} options options for applying directives. This is the same as the options
* for the exported function, except that `reportUnusedDisableDirectives` is not supported
* (this function always reports unused disable directives).
* @returns {{problems: LintMessage[], unusedDirectives: LintMessage[]}} An object with a list
* of problems (including suppressed ones) and unused eslint-disable directives
*/
function applyDirectives(options) {
const problems = [];
const usedDisableDirectives = new Set();
const { sourceCode } = options;
for (const problem of options.problems) {
let disableDirectivesForProblem = [];
let nextDirectiveIndex = 0;
while (
nextDirectiveIndex < options.directives.length &&
compareLocations(options.directives[nextDirectiveIndex], problem) <=
0
) {
const directive = options.directives[nextDirectiveIndex++];
if (
directive.ruleId === null ||
directive.ruleId === problem.ruleId
) {
switch (directive.type) {
case "disable":
disableDirectivesForProblem.push(directive);
break;
case "enable":
disableDirectivesForProblem = [];
break;
// no default
}
}
}
if (disableDirectivesForProblem.length > 0) {
const suppressions = disableDirectivesForProblem.map(directive => ({
kind: "directive",
justification: directive.unprocessedDirective.justification,
}));
if (problem.suppressions) {
problem.suppressions =
problem.suppressions.concat(suppressions);
} else {
problem.suppressions = suppressions;
usedDisableDirectives.add(disableDirectivesForProblem.at(-1));
}
}
problems.push(problem);
}
const unusedDisableDirectivesToReport = options.directives.filter(
directive =>
directive.type === "disable" &&
!usedDisableDirectives.has(directive) &&
!options.rulesToIgnore.has(directive.ruleId),
);
const unusedEnableDirectivesToReport = new Set(
options.directives.filter(
directive =>
directive.unprocessedDirective.type === "enable" &&
!options.rulesToIgnore.has(directive.ruleId),
),
);
/*
* If directives has the eslint-enable directive,
* check whether the eslint-enable comment is used.
*/
if (unusedEnableDirectivesToReport.size > 0) {
for (const directive of collectUsedEnableDirectives(
options.directives,
)) {
unusedEnableDirectivesToReport.delete(directive);
}
}
const processed = processUnusedDirectives(
unusedDisableDirectivesToReport,
sourceCode,
).concat(
processUnusedDirectives(unusedEnableDirectivesToReport, sourceCode),
);
const columnOffset = options.language.columnStart === 1 ? 0 : 1;
const lineOffset = options.language.lineStart === 1 ? 0 : 1;
const unusedDirectives = processed.map(
({ description, fix, unprocessedDirective }) => {
const { parentDirective, type, line, column } =
unprocessedDirective;
let message;
if (type === "enable") {
message = description
? `Unused eslint-enable directive (no matching eslint-disable directives were found for ${description}).`
: "Unused eslint-enable directive (no matching eslint-disable directives were found).";
} else {
message = description
? `Unused eslint-disable directive (no problems were reported from ${description}).`
: "Unused eslint-disable directive (no problems were reported).";
}
const loc = sourceCode.getLoc(parentDirective.node);
return {
ruleId: null,
message,
line:
type === "disable-next-line"
? loc.start.line + lineOffset
: line,
column:
type === "disable-next-line"
? loc.start.column + columnOffset
: column,
severity:
options.reportUnusedDisableDirectives === "warn" ? 1 : 2,
...(options.disableFixes ? {} : { fix }),
};
},
);
return { problems, unusedDirectives };
}
/**
* Given a list of directive comments (i.e. metadata about eslint-disable and eslint-enable comments) and a list
* of reported problems, adds the suppression information to the problems.
* @param {Object} options Information about directives and problems
* @param {Language} options.language The language being linted.
* @param {SourceCode} options.sourceCode The source code object for the file being linted.
* @param {{
* type: ("disable"|"enable"|"disable-line"|"disable-next-line"),
* ruleId: (string|null),
* line: number,
* column: number,
* justification: string
* }} options.directives Directive comments found in the file, with one-based columns.
* Two directive comments can only have the same location if they also have the same type (e.g. a single eslint-disable
* comment for two different rules is represented as two directives).
* @param {{ruleId: (string|null), line: number, column: number}[]} options.problems
* A list of problems reported by rules, sorted by increasing location in the file, with one-based columns.
* @param {"off" | "warn" | "error"} options.reportUnusedDisableDirectives If `"warn"` or `"error"`, adds additional problems for unused directives
* @param {RulesConfig} options.configuredRules The rules configuration.
* @param {Function} options.ruleFilter A predicate function to filter which rules should be executed.
* @param {boolean} options.disableFixes If true, it doesn't make `fix` properties.
* @returns {{ruleId: (string|null), line: number, column: number, suppressions?: {kind: string, justification: string}}[]}
* An object with a list of reported problems, the suppressed of which contain the suppression information.
*/
module.exports = ({
language,
sourceCode,
directives,
disableFixes,
problems,
configuredRules,
ruleFilter,
reportUnusedDisableDirectives = "off",
}) => {
const blockDirectives = directives
.filter(
directive =>
directive.type === "disable" || directive.type === "enable",
)
.map(directive =>
Object.assign({}, directive, { unprocessedDirective: directive }),
)
.sort(compareLocations);
const lineDirectives = directives
.flatMap(directive => {
switch (directive.type) {
case "disable":
case "enable":
return [];
case "disable-line":
return [
{
type: "disable",
line: directive.line,
column: 1,
ruleId: directive.ruleId,
unprocessedDirective: directive,
},
{
type: "enable",
line: directive.line + 1,
column: 0,
ruleId: directive.ruleId,
unprocessedDirective: directive,
},
];
case "disable-next-line":
return [
{
type: "disable",
line: directive.line + 1,
column: 1,
ruleId: directive.ruleId,
unprocessedDirective: directive,
},
{
type: "enable",
line: directive.line + 2,
column: 0,
ruleId: directive.ruleId,
unprocessedDirective: directive,
},
];
default:
throw new TypeError(
`Unrecognized directive type '${directive.type}'`,
);
}
})
.sort(compareLocations);
// This determines a list of rules that are not being run by the given ruleFilter, if present.
const rulesToIgnore =
configuredRules && ruleFilter
? new Set(
Object.keys(configuredRules).filter(ruleId => {
const severity = Config.getRuleNumericSeverity(
configuredRules[ruleId],
);
// Ignore for disabled rules.
if (severity === 0) {
return false;
}
return !ruleFilter({ severity, ruleId });
}),
)
: new Set();
// If no ruleId is supplied that means this directive is applied to all rules, so we can't determine if it's unused if any rules are filtered out.
if (rulesToIgnore.size > 0) {
rulesToIgnore.add(null);
}
const blockDirectivesResult = applyDirectives({
language,
sourceCode,
problems,
directives: blockDirectives,
disableFixes,
reportUnusedDisableDirectives,
rulesToIgnore,
});
const lineDirectivesResult = applyDirectives({
language,
sourceCode,
problems: blockDirectivesResult.problems,
directives: lineDirectives,
disableFixes,
reportUnusedDisableDirectives,
rulesToIgnore,
});
return reportUnusedDisableDirectives !== "off"
? lineDirectivesResult.problems
.concat(blockDirectivesResult.unusedDirectives)
.concat(lineDirectivesResult.unusedDirectives)
.sort(compareLocations)
: lineDirectivesResult.problems;
};

View File

@@ -0,0 +1,2 @@
export declare var TypeFlags: any;
//# sourceMappingURL=typeFlags.d.ts.map

View File

@@ -0,0 +1,114 @@
declare module "node:stream/consumers" {
import { Blob, NonSharedBuffer } from "node:buffer";
import { ReadableStream } from "node:stream/web";
/**
* ```js
* import { arrayBuffer } from 'node:stream/consumers';
* import { Readable } from 'node:stream';
* import { TextEncoder } from 'node:util';
*
* const encoder = new TextEncoder();
* const dataArray = encoder.encode('hello world from consumers!');
*
* const readable = Readable.from(dataArray);
* const data = await arrayBuffer(readable);
* console.log(`from readable: ${data.byteLength}`);
* // Prints: from readable: 76
* ```
* @since v16.7.0
* @returns Fulfills with an `ArrayBuffer` containing the full contents of the stream.
*/
function arrayBuffer(stream: ReadableStream | NodeJS.ReadableStream | AsyncIterable<any>): Promise<ArrayBuffer>;
/**
* ```js
* import { blob } from 'node:stream/consumers';
*
* const dataBlob = new Blob(['hello world from consumers!']);
*
* const readable = dataBlob.stream();
* const data = await blob(readable);
* console.log(`from readable: ${data.size}`);
* // Prints: from readable: 27
* ```
* @since v16.7.0
* @returns Fulfills with a `Blob` containing the full contents of the stream.
*/
function blob(stream: ReadableStream | NodeJS.ReadableStream | AsyncIterable<any>): Promise<Blob>;
/**
* ```js
* import { buffer } from 'node:stream/consumers';
* import { Readable } from 'node:stream';
* import { Buffer } from 'node:buffer';
*
* const dataBuffer = Buffer.from('hello world from consumers!');
*
* const readable = Readable.from(dataBuffer);
* const data = await buffer(readable);
* console.log(`from readable: ${data.length}`);
* // Prints: from readable: 27
* ```
* @since v16.7.0
* @returns Fulfills with a `Buffer` containing the full contents of the stream.
*/
function buffer(stream: ReadableStream | NodeJS.ReadableStream | AsyncIterable<any>): Promise<NonSharedBuffer>;
/**
* ```js
* import { bytes } from 'node:stream/consumers';
* import { Readable } from 'node:stream';
* import { Buffer } from 'node:buffer';
*
* const dataBuffer = Buffer.from('hello world from consumers!');
*
* const readable = Readable.from(dataBuffer);
* const data = await bytes(readable);
* console.log(`from readable: ${data.length}`);
* // Prints: from readable: 27
* ```
* @since v25.6.0
* @returns Fulfills with a `Uint8Array` containing the full contents of the stream.
*/
function bytes(
stream: ReadableStream | NodeJS.ReadableStream | AsyncIterable<any>,
): Promise<NodeJS.NonSharedUint8Array>;
/**
* ```js
* import { json } from 'node:stream/consumers';
* import { Readable } from 'node:stream';
*
* const items = Array.from(
* {
* length: 100,
* },
* () => ({
* message: 'hello world from consumers!',
* }),
* );
*
* const readable = Readable.from(JSON.stringify(items));
* const data = await json(readable);
* console.log(`from readable: ${data.length}`);
* // Prints: from readable: 100
* ```
* @since v16.7.0
* @returns Fulfills with the contents of the stream parsed as a
* UTF-8 encoded string that is then passed through `JSON.parse()`.
*/
function json(stream: ReadableStream | NodeJS.ReadableStream | AsyncIterable<any>): Promise<unknown>;
/**
* ```js
* import { text } from 'node:stream/consumers';
* import { Readable } from 'node:stream';
*
* const readable = Readable.from('Hello world from consumers!');
* const data = await text(readable);
* console.log(`from readable: ${data.length}`);
* // Prints: from readable: 27
* ```
* @since v16.7.0
* @returns Fulfills with the contents of the stream parsed as a UTF-8 encoded string.
*/
function text(stream: ReadableStream | NodeJS.ReadableStream | AsyncIterable<any>): Promise<string>;
}
declare module "stream/consumers" {
export * from "node:stream/consumers";
}

View File

@@ -0,0 +1,47 @@
import * as path from 'node:path';
import path__default from 'node:path';
/**
* Constant for path separator.
*
* Always equals to `"/"`.
*/
declare const sep = "/";
declare const normalize: typeof path__default.normalize;
declare const join: typeof path__default.join;
declare const resolve: typeof path__default.resolve;
/**
* Resolves a string path, resolving '.' and '.' segments and allowing paths above the root.
*
* @param path - The path to normalise.
* @param allowAboveRoot - Whether to allow the resulting path to be above the root directory.
* @returns the normalised path string.
*/
declare function normalizeString(path: string, allowAboveRoot: boolean): string;
declare const isAbsolute: typeof path__default.isAbsolute;
declare const toNamespacedPath: typeof path__default.toNamespacedPath;
declare const extname: typeof path__default.extname;
declare const relative: typeof path__default.relative;
declare const dirname: typeof path__default.dirname;
declare const format: typeof path__default.format;
declare const basename: typeof path__default.basename;
declare const parse: typeof path__default.parse;
/**
* The `path.matchesGlob()` method determines if `path` matches the `pattern`.
* @param path The path to glob-match against.
* @param pattern The glob to check the path against.
*/
declare const matchesGlob: (path: string, pattern: string | string[]) => boolean;
type NodePath = typeof path;
/**
* The platform-specific file delimiter.
*
* Equals to `";"` in windows and `":"` in all other platforms.
*/
declare const delimiter: ";" | ":";
declare const posix: NodePath["posix"];
declare const win32: NodePath["win32"];
declare const _default: NodePath;
export { basename, _default as default, delimiter, dirname, extname, format, isAbsolute, join, matchesGlob, normalize, normalizeString, parse, posix, relative, resolve, sep, toNamespacedPath, win32 };

View File

@@ -0,0 +1,54 @@
# VSCode JSON RPC
[![NPM Version](https://img.shields.io/npm/v/vscode-jsonrpc.svg)](https://npmjs.org/package/vscode-jsonrpc)
[![NPM Downloads](https://img.shields.io/npm/dm/vscode-jsonrpc.svg)](https://npmjs.org/package/vscode-jsonrpc)
[![Build Status](https://dev.azure.com/vscode/vscode-languageserver-node/_apis/build/status%2Fvscode-languageserver-node?branchName=main)](https://dev.azure.com/vscode/vscode-languageserver-node/_build/latest?definitionId=52&branchName=main)
This npm module implements the base messaging protocol spoken between a VSCode language server and a VSCode language client.
The npm module can also be used standalone to establish a [JSON-RPC](http://www.jsonrpc.org/) channel between
a client and a server. Below an example how to setup a JSON-RPC connection. First the client side.
```ts
import * as cp from 'child_process';
import * as rpc from 'vscode-jsonrpc/node';
let childProcess = cp.spawn(...);
// Use stdin and stdout for communication:
let connection = rpc.createMessageConnection(
new rpc.StreamMessageReader(childProcess.stdout),
new rpc.StreamMessageWriter(childProcess.stdin));
let notification = new rpc.NotificationType<string, void>('testNotification');
connection.listen();
connection.sendNotification(notification, 'Hello World');
```
The server side looks very symmetrical:
```ts
import * as rpc from 'vscode-jsonrpc/node';
let connection = rpc.createMessageConnection(
new rpc.StreamMessageReader(process.stdin),
new rpc.StreamMessageWriter(process.stdout));
let notification = new rpc.NotificationType<string, void>('testNotification');
connection.onNotification(notification, (param: string) => {
console.log(param); // This prints Hello World
});
connection.listen();
```
# History
For the history please see the [main repository](https://github.com/Microsoft/vscode-languageserver-node/blob/master/README.md)
## License
[MIT](https://github.com/Microsoft/vscode-languageserver-node/blob/master/License.txt)

View File

@@ -0,0 +1 @@
{"version":3,"file":"resize-codec.d.ts","sourceRoot":"","sources":["../../src/resize-codec.ts"],"names":[],"mappings":"AAEA,OAAO,EACH,KAAK,EAGL,OAAO,EACP,OAAO,EACP,cAAc,EACd,gBAAgB,EAChB,gBAAgB,EAEnB,MAAM,SAAS,CAAC;AAIjB,KAAK,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC;AAE/B,KAAK,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC;AAE/B,KAAK,QAAQ,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC;AAE3B;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmCG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,KAAK,SAAS,MAAM,EAAE,QAAQ,SAAS,MAAM,EAC9E,OAAO,EAAE,gBAAgB,CAAC,KAAK,EAAE,KAAK,CAAC,EACvC,MAAM,EAAE,CAAC,IAAI,EAAE,KAAK,KAAK,QAAQ,GAClC,gBAAgB,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;AACrC,wBAAgB,aAAa,CAAC,QAAQ,SAAS,UAAU,EACrD,OAAO,EAAE,QAAQ,EACjB,MAAM,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,GACjC,QAAQ,CAAC;AA8BZ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmCG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,KAAK,SAAS,MAAM,EAAE,QAAQ,SAAS,MAAM,EAC9E,OAAO,EAAE,gBAAgB,CAAC,KAAK,EAAE,KAAK,CAAC,EACvC,MAAM,EAAE,CAAC,IAAI,EAAE,KAAK,KAAK,QAAQ,GAClC,gBAAgB,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;AACrC,wBAAgB,aAAa,CAAC,QAAQ,SAAS,UAAU,EACrD,OAAO,EAAE,QAAQ,EACjB,MAAM,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,GACjC,QAAQ,CAAC;AAkBZ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4CG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,GAAG,SAAS,KAAK,EAAE,KAAK,SAAS,MAAM,EAAE,QAAQ,SAAS,MAAM,EAC/F,KAAK,EAAE,cAAc,CAAC,KAAK,EAAE,GAAG,EAAE,KAAK,CAAC,EACxC,MAAM,EAAE,CAAC,IAAI,EAAE,KAAK,KAAK,QAAQ,GAClC,cAAc,CAAC,KAAK,EAAE,GAAG,EAAE,QAAQ,CAAC,CAAC;AACxC,wBAAgB,WAAW,CAAC,MAAM,SAAS,QAAQ,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,GAAG,MAAM,CAAC"}

View File

@@ -0,0 +1,2 @@
export declare var ModuleKind: any;
//# sourceMappingURL=moduleKind.d.ts.map

View File

@@ -0,0 +1,14 @@
import type { TypeOrValueSpecifier } from '../util';
export type MessageIds = 'object' | 'undef';
export type Options = [
{
allow?: TypeOrValueSpecifier[];
allowRethrowing?: boolean;
allowThrowingAny?: boolean;
allowThrowingUnknown?: boolean;
}
];
declare const _default: import("@typescript-eslint/utils/ts-eslint").RuleModule<MessageIds, Options, import("../../rules").ESLintPluginDocs, import("@typescript-eslint/utils/ts-eslint").RuleListener> & {
name: string;
};
export default _default;

View File

@@ -0,0 +1,18 @@
This software is released under the MIT license:
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

View File

@@ -0,0 +1,494 @@
'use strict'
let Comment = require('./comment')
let Declaration = require('./declaration')
let Node = require('./node')
let { isClean, my } = require('./symbols')
let AtRule, parse, Root, Rule
function cleanSource(nodes) {
let stack = nodes.slice()
while (stack.length > 0) {
let node = stack.pop()
delete node.source
if (node.nodes) {
node.nodes = node.nodes.slice()
for (let i of node.nodes) stack.push(i)
}
}
return nodes.slice()
}
function markTreeDirty(node) {
let stack = [node]
while (stack.length > 0) {
let next = stack.pop()
next[isClean] = false
if (next.proxyOf.nodes) {
for (let i of next.proxyOf.nodes) stack.push(i)
}
}
}
class Container extends Node {
get first() {
if (!this.proxyOf.nodes) return undefined
return this.proxyOf.nodes[0]
}
get last() {
if (!this.proxyOf.nodes) return undefined
return this.proxyOf.nodes[this.proxyOf.nodes.length - 1]
}
append(...children) {
for (let child of children) {
let nodes = this.normalize(child, this.last)
for (let node of nodes) this.proxyOf.nodes.push(node)
}
this.markDirty()
return this
}
cleanRaws(keepBetween) {
let stack = [this]
while (stack.length > 0) {
let node = stack.pop()
if (node !== this && node.cleanRaws !== Container.prototype.cleanRaws) {
// Subclass with own logic; let it handle its subtree
node.cleanRaws(keepBetween)
continue
}
Node.prototype.cleanRaws.call(node, keepBetween)
if (node.nodes) {
for (let child of node.nodes) stack.push(child)
}
}
}
each(callback) {
if (!this.proxyOf.nodes) return undefined
let iterator = this.getIterator()
let index, result
while (this.indexes[iterator] < this.proxyOf.nodes.length) {
index = this.indexes[iterator]
result = callback(this.proxyOf.nodes[index], index)
if (result === false) break
this.indexes[iterator] += 1
}
delete this.indexes[iterator]
return result
}
every(condition) {
return this.nodes.every(condition)
}
getIterator() {
if (!this.lastEach) this.lastEach = 0
if (!this.indexes) this.indexes = {}
this.lastEach += 1
let iterator = this.lastEach
this.indexes[iterator] = 0
return iterator
}
getProxyProcessor() {
return {
get(node, prop) {
if (prop === 'proxyOf') {
return node
} else if (!node[prop]) {
return node[prop]
} else if (
prop === 'each' ||
(typeof prop === 'string' && prop.startsWith('walk'))
) {
return (...args) => {
return node[prop](
...args.map(i => {
if (typeof i === 'function') {
return (child, index) => i(child.toProxy(), index)
} else {
return i
}
})
)
}
} else if (prop === 'every' || prop === 'some') {
return cb => {
return node[prop]((child, ...other) =>
cb(child.toProxy(), ...other)
)
}
} else if (prop === 'root') {
return () => node.root().toProxy()
} else if (prop === 'nodes') {
return node.nodes.map(i => i.toProxy())
} else if (prop === 'first' || prop === 'last') {
return node[prop].toProxy()
} else {
return node[prop]
}
},
set(node, prop, value) {
if (node[prop] === value) return true
node[prop] = value
if (prop === 'name' || prop === 'params' || prop === 'selector') {
node.markDirty()
}
return true
}
}
}
index(child) {
if (typeof child === 'number') return child
if (child.proxyOf) child = child.proxyOf
return this.proxyOf.nodes.indexOf(child)
}
insertAfter(exist, add) {
let existIndex = this.index(exist)
let nodes = this.normalize(add, this.proxyOf.nodes[existIndex]).reverse()
existIndex = this.index(exist)
for (let node of nodes) this.proxyOf.nodes.splice(existIndex + 1, 0, node)
let index
for (let id in this.indexes) {
index = this.indexes[id]
if (existIndex < index) {
this.indexes[id] = index + nodes.length
}
}
this.markDirty()
return this
}
insertBefore(exist, add) {
let existIndex = this.index(exist)
let type = existIndex === 0 ? 'prepend' : false
let nodes = this.normalize(
add,
this.proxyOf.nodes[existIndex],
type
).reverse()
existIndex = this.index(exist)
for (let node of nodes) this.proxyOf.nodes.splice(existIndex, 0, node)
let index
for (let id in this.indexes) {
index = this.indexes[id]
if (existIndex <= index) {
this.indexes[id] = index + nodes.length
}
}
this.markDirty()
return this
}
normalize(nodes, sample) {
if (typeof nodes === 'string') {
nodes = cleanSource(parse(nodes).nodes)
} else if (typeof nodes === 'undefined') {
nodes = []
} else if (Array.isArray(nodes)) {
nodes = nodes.slice(0)
for (let i of nodes) {
if (i.parent) i.parent.removeChild(i, 'ignore')
}
} else if (nodes.type === 'root' && this.type !== 'document') {
nodes = nodes.nodes.slice(0)
for (let i of nodes) {
if (i.parent) i.parent.removeChild(i, 'ignore')
}
} else if (nodes.type) {
nodes = [nodes]
} else if (nodes.prop) {
if (typeof nodes.value === 'undefined') {
throw new Error('Value field is missed in node creation')
} else if (typeof nodes.value !== 'string') {
nodes.value = String(nodes.value)
}
nodes = [new Declaration(nodes)]
} else if (nodes.selector || nodes.selectors) {
nodes = [new Rule(nodes)]
} else if (nodes.name) {
nodes = [new AtRule(nodes)]
} else if (nodes.text) {
nodes = [new Comment(nodes)]
} else {
throw new Error('Unknown node type in node creation')
}
let processed = nodes.map(i => {
/* c8 ignore next */
if (!i[my]) Container.rebuild(i)
i = i.proxyOf
if (i.parent) i.parent.removeChild(i)
if (i[isClean]) markTreeDirty(i)
if (!i.raws) i.raws = {}
if (typeof i.raws.before === 'undefined') {
if (sample && typeof sample.raws.before !== 'undefined') {
i.raws.before = sample.raws.before.replace(/\S/g, '')
}
}
i.parent = this.proxyOf
return i
})
return processed
}
prepend(...children) {
children = children.reverse()
for (let child of children) {
let nodes = this.normalize(child, this.first, 'prepend').reverse()
for (let node of nodes) this.proxyOf.nodes.unshift(node)
for (let id in this.indexes) {
this.indexes[id] = this.indexes[id] + nodes.length
}
}
this.markDirty()
return this
}
push(child) {
child.parent = this
this.proxyOf.nodes.push(child)
return this
}
removeAll() {
for (let node of this.proxyOf.nodes) node.parent = undefined
this.proxyOf.nodes = []
this.markDirty()
return this
}
removeChild(child) {
child = this.index(child)
this.proxyOf.nodes[child].parent = undefined
this.proxyOf.nodes.splice(child, 1)
let index
for (let id in this.indexes) {
index = this.indexes[id]
if (index >= child) {
this.indexes[id] = index - 1
}
}
this.markDirty()
return this
}
replaceValues(pattern, opts, callback) {
if (!callback) {
callback = opts
opts = {}
}
this.walkDecls(decl => {
if (opts.props && !opts.props.includes(decl.prop)) return
if (opts.fast && !decl.value.includes(opts.fast)) return
decl.value = decl.value.replace(pattern, callback)
})
this.markDirty()
return this
}
some(condition) {
return this.nodes.some(condition)
}
walk(callback) {
if (!this.proxyOf.nodes) return undefined
// An explicit stack instead of recursive `each()` calls to survive
// deeply nested trees. Each frame keeps a live `indexes` slot, so
// insertion and removal during the walk behave like `each()`: the
// slot stays at the current child until its subtree is finished.
let stack = [{ iterator: this.getIterator(), node: this.proxyOf }]
while (stack.length > 0) {
let { iterator, node } = stack[stack.length - 1]
let index = node.indexes[iterator]
if (index >= node.proxyOf.nodes.length) {
delete node.indexes[iterator]
stack.pop()
let parent = stack[stack.length - 1]
// Finish the parents step for the child subtree we just left
if (parent) parent.node.indexes[parent.iterator] += 1
continue
}
let child = node.proxyOf.nodes[index]
let result
try {
result = callback(child, index)
} catch (e) {
throw child.addToError(e)
}
if (result === false) {
for (let opened of stack) {
delete opened.node.indexes[opened.iterator]
}
return false
}
if (child.walk && child.proxyOf.nodes) {
stack.push({ iterator: child.getIterator(), node: child })
} else {
node.indexes[iterator] += 1
}
}
return undefined
}
walkAtRules(name, callback) {
if (!callback) {
callback = name
return this.walk((child, i) => {
if (child.type === 'atrule') {
return callback(child, i)
}
})
}
if (name instanceof RegExp) {
return this.walk((child, i) => {
if (child.type === 'atrule' && name.test(child.name)) {
return callback(child, i)
}
})
}
return this.walk((child, i) => {
if (child.type === 'atrule' && child.name === name) {
return callback(child, i)
}
})
}
walkComments(callback) {
return this.walk((child, i) => {
if (child.type === 'comment') {
return callback(child, i)
}
})
}
walkDecls(prop, callback) {
if (!callback) {
callback = prop
return this.walk((child, i) => {
if (child.type === 'decl') {
return callback(child, i)
}
})
}
if (prop instanceof RegExp) {
return this.walk((child, i) => {
if (child.type === 'decl' && prop.test(child.prop)) {
return callback(child, i)
}
})
}
return this.walk((child, i) => {
if (child.type === 'decl' && child.prop === prop) {
return callback(child, i)
}
})
}
walkRules(selector, callback) {
if (!callback) {
callback = selector
return this.walk((child, i) => {
if (child.type === 'rule') {
return callback(child, i)
}
})
}
if (selector instanceof RegExp) {
return this.walk((child, i) => {
if (child.type === 'rule' && selector.test(child.selector)) {
return callback(child, i)
}
})
}
return this.walk((child, i) => {
if (child.type === 'rule' && child.selector === selector) {
return callback(child, i)
}
})
}
}
Container.registerParse = dependant => {
parse = dependant
}
Container.registerRule = dependant => {
Rule = dependant
}
Container.registerAtRule = dependant => {
AtRule = dependant
}
Container.registerRoot = dependant => {
Root = dependant
}
module.exports = Container
Container.default = Container
/* c8 ignore start */
Container.rebuild = node => {
let stack = [node]
while (stack.length > 0) {
let next = stack.pop()
if (next.type === 'atrule') {
Object.setPrototypeOf(next, AtRule.prototype)
} else if (next.type === 'rule') {
Object.setPrototypeOf(next, Rule.prototype)
} else if (next.type === 'decl') {
Object.setPrototypeOf(next, Declaration.prototype)
} else if (next.type === 'comment') {
Object.setPrototypeOf(next, Comment.prototype)
} else if (next.type === 'root') {
Object.setPrototypeOf(next, Root.prototype)
}
next[my] = true
if (next.nodes) {
for (let child of next.nodes) stack.push(child)
}
}
}
/* c8 ignore stop */

View File

@@ -0,0 +1,91 @@
import { join } from 'node:path'
import { tmpdir } from 'node:os'
import pinoPretty from 'pino-pretty'
// Test both default ("Pino") and named ("pino") imports.
import Pino, { type LoggerOptions, type StreamEntry, pino, multistream, transport } from '../../pino'
const destination = join(
tmpdir(),
'_' + Math.random().toString(36).substr(2, 9)
)
// Single
const transport1 = transport({
target: 'pino-pretty',
options: { some: 'options for', the: 'transport' }
})
const logger = pino(transport1)
logger.setBindings({ some: 'bindings' })
logger.info('test2')
logger.flush()
const loggerDefault = Pino(transport1)
loggerDefault.setBindings({ some: 'bindings' })
loggerDefault.info('test2')
loggerDefault.flush()
const transport2 = transport({
target: 'pino-pretty',
})
const logger2 = pino(transport2)
logger2.info('test2')
const logger2Default = Pino(transport2)
logger2Default.info('test2')
// Multiple
const transports = transport({
targets: [
{
level: 'info',
target: 'pino-pretty',
options: { some: 'options for', the: 'transport' }
},
{
level: 'trace',
target: 'pino/file',
options: { destination }
}
]
})
const loggerMulti = pino(transports)
loggerMulti.info('test2')
// custom levels
const customLevels = {
customDebug: 1,
info: 2,
customNetwork: 3,
customError: 4,
}
type CustomLevels = keyof typeof customLevels
const pinoOpts = {
useOnlyCustomLevels: true,
customLevels,
level: 'customDebug',
} satisfies LoggerOptions
const multistreamOpts = {
dedupe: true,
levels: customLevels
}
const streams: StreamEntry<CustomLevels>[] = [
{ level: 'customDebug', stream: pinoPretty() },
{ level: 'info', stream: pinoPretty() },
{ level: 'customNetwork', stream: pinoPretty() },
{ level: 'customError', stream: pinoPretty() },
]
const loggerCustomLevel = pino(pinoOpts, multistream(streams, multistreamOpts))
loggerCustomLevel.customDebug('test3')
loggerCustomLevel.info('test4')
loggerCustomLevel.customError('test5')
loggerCustomLevel.customNetwork('test6')
const loggerCustomLevelDefault = Pino(pinoOpts, multistream(streams, multistreamOpts))
loggerCustomLevelDefault.customDebug('test3')
loggerCustomLevelDefault.info('test4')
loggerCustomLevelDefault.customError('test5')
loggerCustomLevelDefault.customNetwork('test6')

View File

@@ -0,0 +1,53 @@
/**
* @fileoverview Rule to flag octal escape sequences in string literals.
* @author Ian Christian Myers
*/
"use strict";
//------------------------------------------------------------------------------
// Rule Definition
//------------------------------------------------------------------------------
/** @type {import('../types').Rule.RuleModule} */
module.exports = {
meta: {
type: "suggestion",
docs: {
description: "Disallow octal escape sequences in string literals",
recommended: false,
url: "https://eslint.org/docs/latest/rules/no-octal-escape",
},
schema: [],
messages: {
octalEscapeSequence:
"Don't use octal: '\\{{sequence}}'. Use '\\u....' instead.",
},
},
create(context) {
return {
Literal(node) {
if (typeof node.value !== "string") {
return;
}
// \0 represents a valid NULL character if it isn't followed by a digit.
const match = node.raw.match(
/^(?:[^\\]|\\.)*?\\([0-3][0-7]{1,2}|[4-7][0-7]|0(?=[89])|[1-7])/su,
);
if (match) {
context.report({
node,
messageId: "octalEscapeSequence",
data: { sequence: match[1] },
});
}
},
};
},
};

View File

@@ -0,0 +1,52 @@
import _typeof from "./typeof.js";
import setPrototypeOf from "./setPrototypeOf.js";
import inherits from "./inherits.js";
function _wrapRegExp() {
_wrapRegExp = function _wrapRegExp(e, r) {
return new BabelRegExp(e, void 0, r);
};
var e = RegExp.prototype,
r = new WeakMap();
function BabelRegExp(e, t, p) {
var o = RegExp(e, t);
return r.set(o, p || r.get(e)), setPrototypeOf(o, BabelRegExp.prototype);
}
function buildGroups(e, t) {
var p = r.get(t);
return Object.keys(p).reduce(function (r, t) {
var o = p[t];
if ("number" == typeof o) r[t] = e[o];else {
for (var i = 0; void 0 === e[o[i]] && i + 1 < o.length;) i++;
r[t] = e[o[i]];
}
return r;
}, Object.create(null));
}
return inherits(BabelRegExp, RegExp), BabelRegExp.prototype.exec = function (r) {
var t = e.exec.call(this, r);
if (t) {
t.groups = buildGroups(t, this);
var p = t.indices;
p && (p.groups = buildGroups(p, this));
}
return t;
}, BabelRegExp.prototype[Symbol.replace] = function (t, p) {
if ("string" == typeof p) {
var o = r.get(this);
return e[Symbol.replace].call(this, t, p.replace(/\$<([^>]+)(>|$)/g, function (e, r, t) {
if ("" === t) return e;
var p = o[r];
return Array.isArray(p) ? "$" + p.join("$") : "number" == typeof p ? "$" + p : "";
}));
}
if ("function" == typeof p) {
var i = this;
return e[Symbol.replace].call(this, t, function () {
var e = arguments;
return "object" != _typeof(e[e.length - 1]) && (e = [].slice.call(e)).push(buildGroups(e, i)), p.apply(this, e);
});
}
return e[Symbol.replace].call(this, t, p);
}, _wrapRegExp.apply(this, arguments);
}
export { _wrapRegExp as default };

View File

@@ -0,0 +1,76 @@
"use strict";
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
Object.defineProperty(exports, "__esModule", { value: true });
exports.getContextualType = getContextualType;
const ts = __importStar(require("typescript"));
/**
* Returns the contextual type of a given node.
* Contextual type is the type of the target the node is going into.
* i.e. the type of a called function's parameter, or the defined type of a variable declaration
*/
function getContextualType(checker, node) {
const parent = node.parent;
if (ts.isCallExpression(parent) || ts.isNewExpression(parent)) {
if (node === parent.expression) {
// is the callee, so has no contextual type
return;
}
}
else if (ts.isVariableDeclaration(parent) ||
ts.isPropertyDeclaration(parent) ||
ts.isParameter(parent)) {
return parent.type ? checker.getTypeFromTypeNode(parent.type) : undefined;
}
else if (ts.isJsxExpression(parent)) {
return checker.getContextualType(parent);
}
else if (ts.isIdentifier(node) &&
(ts.isPropertyAssignment(parent) ||
ts.isShorthandPropertyAssignment(parent))) {
return checker.getContextualType(node);
}
else if (ts.isBinaryExpression(parent) &&
parent.operatorToken.kind === ts.SyntaxKind.EqualsToken &&
parent.right === node) {
// is RHS of assignment
return checker.getTypeAtLocation(parent.left);
}
else if (![ts.SyntaxKind.JsxExpression, ts.SyntaxKind.TemplateSpan].includes(parent.kind)) {
// parent is not something we know we can get the contextual type of
return;
}
// TODO - support return statement checking
return checker.getContextualType(node);
}

View File

@@ -0,0 +1 @@
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/utils.ts"],"names":[],"mappings":"AAAA,OAAO,EAKH,gBAAgB,EAChB,gBAAgB,EAGnB,MAAM,qBAAqB,CAAC;AAG7B,OAAO,EAAU,iBAAiB,EAAE,MAAM,UAAU,CAAC;AAErD,KAAK,wBAAwB,CAAC,KAAK,SAAS,MAAM,IAAI;IAClD,MAAM,CAAC,EAAE,iBAAiB,CAAC;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,KAAK,CAAC;CACf,CAAC;AAEF,KAAK,yBAAyB,CAAC,KAAK,EAAE,KAAK,SAAS,MAAM,IAAI,wBAAwB,CAAC,KAAK,CAAC,GAAG;IAC5F,KAAK,CAAC,EAAE,CAAC,MAAM,GAAG,MAAM,EAAE,MAAM,GAAG,MAAM,CAAC,CAAC;IAC3C,GAAG,EAAE,CAAC,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,KAAK,EAAE,YAAY,CAAC,EAAE,OAAO,KAAK,IAAI,CAAC;CACvE,CAAC;AAEF,KAAK,yBAAyB,CAAC,GAAG,EAAE,KAAK,SAAS,MAAM,IAAI,wBAAwB,CAAC,KAAK,CAAC,GAAG;IAC1F,GAAG,EAAE,CAAC,IAAI,EAAE,QAAQ,EAAE,YAAY,CAAC,EAAE,OAAO,KAAK,GAAG,CAAC;CACxD,CAAC;AAMF,wBAAgB,oBAAoB,CAAC,KAAK,SAAS,MAAM,GAAG,MAAM,EAAE,KAAK,SAAS,MAAM,EACpF,KAAK,EAAE,yBAAyB,CAAC,KAAK,EAAE,KAAK,CAAC,GAC/C,gBAAgB,CAAC,KAAK,EAAE,KAAK,CAAC,CAahC;AAED,wBAAgB,oBAAoB,CAAC,GAAG,SAAS,MAAM,GAAG,MAAM,EAAE,KAAK,SAAS,MAAM,EAClF,KAAK,EAAE,yBAAyB,CAAC,GAAG,EAAE,KAAK,CAAC,GAC7C,gBAAgB,CAAC,GAAG,EAAE,KAAK,CAAC,CAU9B"}

View File

@@ -0,0 +1,6 @@
# undici-types
This package is a dual-publish of the [undici](https://www.npmjs.com/package/undici) library types. The `undici` package **still contains types**. This package is for users who _only_ need undici types (such as for `@types/node`). It is published alongside every release of `undici`, so you can always use the same version.
- [GitHub nodejs/undici](https://github.com/nodejs/undici)
- [Undici Documentation](https://undici.nodejs.org/#/)

View File

@@ -0,0 +1,22 @@
"use strict";
module.exports = function (it) {
const { pluginId, plugins } = it;
let result = `ESLint couldn't determine the plugin "${pluginId}" uniquely.
`;
for (const { filePath, importerName } of plugins) {
result += `
- ${filePath} (loaded in "${importerName}")`;
}
result += `
Please remove the "plugins" setting from either config or remove either plugin installation.
If you still can't figure out the problem, please see https://eslint.org/docs/latest/use/troubleshooting.
`;
return result;
};

View File

@@ -0,0 +1,11 @@
import { c as createCLI } from './chunks/cac.DdICfEr1.js';
import '@vitest/utils/helpers';
import 'events';
import 'pathe';
import 'tinyrainbow';
import './chunks/env.D4Lgay0q.js';
import 'std-env';
import './chunks/constants.CPYnjOGj.js';
import 'node:assert';
createCLI().parse();

View File

@@ -0,0 +1,162 @@
/**
* Helpers.
*/
var s = 1000;
var m = s * 60;
var h = m * 60;
var d = h * 24;
var w = d * 7;
var y = d * 365.25;
/**
* Parse or format the given `val`.
*
* Options:
*
* - `long` verbose formatting [false]
*
* @param {String|Number} val
* @param {Object} [options]
* @throws {Error} throw an error if val is not a non-empty string or a number
* @return {String|Number}
* @api public
*/
module.exports = function (val, options) {
options = options || {};
var type = typeof val;
if (type === 'string' && val.length > 0) {
return parse(val);
} else if (type === 'number' && isFinite(val)) {
return options.long ? fmtLong(val) : fmtShort(val);
}
throw new Error(
'val is not a non-empty string or a valid number. val=' +
JSON.stringify(val)
);
};
/**
* Parse the given `str` and return milliseconds.
*
* @param {String} str
* @return {Number}
* @api private
*/
function parse(str) {
str = String(str);
if (str.length > 100) {
return;
}
var match = /^(-?(?:\d+)?\.?\d+) *(milliseconds?|msecs?|ms|seconds?|secs?|s|minutes?|mins?|m|hours?|hrs?|h|days?|d|weeks?|w|years?|yrs?|y)?$/i.exec(
str
);
if (!match) {
return;
}
var n = parseFloat(match[1]);
var type = (match[2] || 'ms').toLowerCase();
switch (type) {
case 'years':
case 'year':
case 'yrs':
case 'yr':
case 'y':
return n * y;
case 'weeks':
case 'week':
case 'w':
return n * w;
case 'days':
case 'day':
case 'd':
return n * d;
case 'hours':
case 'hour':
case 'hrs':
case 'hr':
case 'h':
return n * h;
case 'minutes':
case 'minute':
case 'mins':
case 'min':
case 'm':
return n * m;
case 'seconds':
case 'second':
case 'secs':
case 'sec':
case 's':
return n * s;
case 'milliseconds':
case 'millisecond':
case 'msecs':
case 'msec':
case 'ms':
return n;
default:
return undefined;
}
}
/**
* Short format for `ms`.
*
* @param {Number} ms
* @return {String}
* @api private
*/
function fmtShort(ms) {
var msAbs = Math.abs(ms);
if (msAbs >= d) {
return Math.round(ms / d) + 'd';
}
if (msAbs >= h) {
return Math.round(ms / h) + 'h';
}
if (msAbs >= m) {
return Math.round(ms / m) + 'm';
}
if (msAbs >= s) {
return Math.round(ms / s) + 's';
}
return ms + 'ms';
}
/**
* Long format for `ms`.
*
* @param {Number} ms
* @return {String}
* @api private
*/
function fmtLong(ms) {
var msAbs = Math.abs(ms);
if (msAbs >= d) {
return plural(ms, msAbs, d, 'day');
}
if (msAbs >= h) {
return plural(ms, msAbs, h, 'hour');
}
if (msAbs >= m) {
return plural(ms, msAbs, m, 'minute');
}
if (msAbs >= s) {
return plural(ms, msAbs, s, 'second');
}
return ms + ' ms';
}
/**
* Pluralization helper.
*/
function plural(ms, msAbs, n, name) {
var isPlural = msAbs >= n * 1.5;
return Math.round(ms / n) + ' ' + name + (isPlural ? 's' : '');
}

View File

@@ -0,0 +1,187 @@
/**
* Experimental KDF for AES.
*/
import { hkdf } from './hkdf.ts';
import { pbkdf2 as _pbkdf2 } from './pbkdf2.ts';
import { scrypt as _scrypt } from './scrypt.ts';
import { sha256 } from './sha256.ts';
import { abytes, bytesToHex, clean, createView, hexToBytes, kdfInputToBytes } from './utils.ts';
// A tiny KDF for various applications like AES key-gen.
// Uses HKDF in a non-standard way, so it's not "KDF-secure", only "PRF-secure".
// Which is good enough: assume sha2-256 retained preimage resistance.
const SCRYPT_FACTOR = 2 ** 19;
const PBKDF2_FACTOR = 2 ** 17;
// Scrypt KDF
export function scrypt(password: string, salt: string): Uint8Array {
return _scrypt(password, salt, { N: SCRYPT_FACTOR, r: 8, p: 1, dkLen: 32 });
}
// PBKDF2-HMAC-SHA256
export function pbkdf2(password: string, salt: string): Uint8Array {
return _pbkdf2(sha256, password, salt, { c: PBKDF2_FACTOR, dkLen: 32 });
}
// Combines two 32-byte byte arrays
function xor32(a: Uint8Array, b: Uint8Array): Uint8Array {
abytes(a, 32);
abytes(b, 32);
const arr = new Uint8Array(32);
for (let i = 0; i < 32; i++) {
arr[i] = a[i] ^ b[i];
}
return arr;
}
function strHasLength(str: string, min: number, max: number): boolean {
return typeof str === 'string' && str.length >= min && str.length <= max;
}
/**
* Derives main seed. Takes a lot of time. Prefer `eskdf` method instead.
*/
export function deriveMainSeed(username: string, password: string): Uint8Array {
if (!strHasLength(username, 8, 255)) throw new Error('invalid username');
if (!strHasLength(password, 8, 255)) throw new Error('invalid password');
// Declared like this to throw off minifiers which auto-convert .fromCharCode(1) to actual string.
// String with non-ascii may be problematic in some envs
const codes = { _1: 1, _2: 2 };
const sep = { s: String.fromCharCode(codes._1), p: String.fromCharCode(codes._2) };
const scr = scrypt(password + sep.s, username + sep.s);
const pbk = pbkdf2(password + sep.p, username + sep.p);
const res = xor32(scr, pbk);
clean(scr, pbk);
return res;
}
type AccountID = number | string;
/**
* Converts protocol & accountId pair to HKDF salt & info params.
*/
function getSaltInfo(protocol: string, accountId: AccountID = 0) {
// Note that length here also repeats two lines below
// We do an additional length check here to reduce the scope of DoS attacks
if (!(strHasLength(protocol, 3, 15) && /^[a-z0-9]{3,15}$/.test(protocol))) {
throw new Error('invalid protocol');
}
// Allow string account ids for some protocols
const allowsStr = /^password\d{0,3}|ssh|tor|file$/.test(protocol);
let salt: Uint8Array; // Extract salt. Default is undefined.
if (typeof accountId === 'string') {
if (!allowsStr) throw new Error('accountId must be a number');
if (!strHasLength(accountId, 1, 255))
throw new Error('accountId must be string of length 1..255');
salt = kdfInputToBytes(accountId);
} else if (Number.isSafeInteger(accountId)) {
if (accountId < 0 || accountId > Math.pow(2, 32) - 1) throw new Error('invalid accountId');
// Convert to Big Endian Uint32
salt = new Uint8Array(4);
createView(salt).setUint32(0, accountId, false);
} else {
throw new Error('accountId must be a number' + (allowsStr ? ' or string' : ''));
}
const info = kdfInputToBytes(protocol);
return { salt, info };
}
type OptsLength = { keyLength: number };
type OptsMod = { modulus: bigint };
type KeyOpts = undefined | OptsLength | OptsMod;
function countBytes(num: bigint): number {
if (typeof num !== 'bigint' || num <= BigInt(128)) throw new Error('invalid number');
return Math.ceil(num.toString(2).length / 8);
}
/**
* Parses keyLength and modulus options to extract length of result key.
* If modulus is used, adds 64 bits to it as per FIPS 186 B.4.1 to combat modulo bias.
*/
function getKeyLength(options: KeyOpts): number {
if (!options || typeof options !== 'object') return 32;
const hasLen = 'keyLength' in options;
const hasMod = 'modulus' in options;
if (hasLen && hasMod) throw new Error('cannot combine keyLength and modulus options');
if (!hasLen && !hasMod) throw new Error('must have either keyLength or modulus option');
// FIPS 186 B.4.1 requires at least 64 more bits
const l = hasMod ? countBytes(options.modulus) + 8 : options.keyLength;
if (!(typeof l === 'number' && l >= 16 && l <= 8192)) throw new Error('invalid keyLength');
return l;
}
/**
* Converts key to bigint and divides it by modulus. Big Endian.
* Implements FIPS 186 B.4.1, which removes 0 and modulo bias from output.
*/
function modReduceKey(key: Uint8Array, modulus: bigint): Uint8Array {
const _1 = BigInt(1);
const num = BigInt('0x' + bytesToHex(key)); // check for ui8a, then bytesToNumber()
const res = (num % (modulus - _1)) + _1; // Remove 0 from output
if (res < _1) throw new Error('expected positive number'); // Guard against bad values
const len = key.length - 8; // FIPS requires 64 more bits = 8 bytes
const hex = res.toString(16).padStart(len * 2, '0'); // numberToHex()
const bytes = hexToBytes(hex);
if (bytes.length !== len) throw new Error('invalid length of result key');
return bytes;
}
// We are not using classes because constructor cannot be async
export interface ESKDF {
/**
* Derives a child key. Child key will not be associated with any
* other child key because of properties of underlying KDF.
*
* @param protocol - 3-15 character protocol name
* @param accountId - numeric identifier of account
* @param options - `keyLength: 64` or `modulus: 41920438n`
* @example deriveChildKey('aes', 0)
*/
deriveChildKey: (protocol: string, accountId: AccountID, options?: KeyOpts) => Uint8Array;
/**
* Deletes the main seed from eskdf instance
*/
expire: () => void;
/**
* Account fingerprint
*/
fingerprint: string;
}
/**
* ESKDF
* @param username - username, email, or identifier, min: 8 characters, should have enough entropy
* @param password - password, min: 8 characters, should have enough entropy
* @example
* const kdf = await eskdf('example-university', 'beginning-new-example');
* const key = kdf.deriveChildKey('aes', 0);
* console.log(kdf.fingerprint);
* kdf.expire();
*/
export async function eskdf(username: string, password: string): Promise<ESKDF> {
// We are using closure + object instead of class because
// we want to make `seed` non-accessible for any external function.
let seed: Uint8Array | undefined = deriveMainSeed(username, password);
function deriveCK(protocol: string, accountId: AccountID = 0, options?: KeyOpts): Uint8Array {
abytes(seed, 32);
const { salt, info } = getSaltInfo(protocol, accountId); // validate protocol & accountId
const keyLength = getKeyLength(options); // validate options
const key = hkdf(sha256, seed!, salt, info, keyLength);
// Modulus has already been validated
return options && 'modulus' in options ? modReduceKey(key, options.modulus) : key;
}
function expire() {
if (seed) seed.fill(1);
seed = undefined;
}
// prettier-ignore
const fingerprint = Array.from(deriveCK('fingerprint', 0))
.slice(0, 6)
.map((char) => char.toString(16).padStart(2, '0').toUpperCase())
.join(':');
return Object.freeze({ deriveChildKey: deriveCK, expire, fingerprint });
}

View File

@@ -0,0 +1,93 @@
import * as core from "./core.js";
import * as errors from "./errors.js";
import * as util from "./util.js";
export const _parse = (_Err) => (schema, value, _ctx, _params) => {
const ctx = _ctx ? { ..._ctx, async: false } : { async: false };
const result = schema._zod.run({ value, issues: [] }, ctx);
if (result instanceof Promise) {
throw new core.$ZodAsyncError();
}
if (result.issues.length) {
const e = new (_params?.Err ?? _Err)(result.issues.map((iss) => util.finalizeIssue(iss, ctx, core.config())));
util.captureStackTrace(e, _params?.callee);
throw e;
}
return result.value;
};
export const parse = /* @__PURE__*/ _parse(errors.$ZodRealError);
export const _parseAsync = (_Err) => async (schema, value, _ctx, params) => {
const ctx = _ctx ? { ..._ctx, async: true } : { async: true };
let result = schema._zod.run({ value, issues: [] }, ctx);
if (result instanceof Promise)
result = await result;
if (result.issues.length) {
const e = new (params?.Err ?? _Err)(result.issues.map((iss) => util.finalizeIssue(iss, ctx, core.config())));
util.captureStackTrace(e, params?.callee);
throw e;
}
return result.value;
};
export const parseAsync = /* @__PURE__*/ _parseAsync(errors.$ZodRealError);
export const _safeParse = (_Err) => (schema, value, _ctx) => {
const ctx = _ctx ? { ..._ctx, async: false } : { async: false };
const result = schema._zod.run({ value, issues: [] }, ctx);
if (result instanceof Promise) {
throw new core.$ZodAsyncError();
}
return result.issues.length
? {
success: false,
error: new (_Err ?? errors.$ZodError)(result.issues.map((iss) => util.finalizeIssue(iss, ctx, core.config()))),
}
: { success: true, data: result.value };
};
export const safeParse = /* @__PURE__*/ _safeParse(errors.$ZodRealError);
export const _safeParseAsync = (_Err) => async (schema, value, _ctx) => {
const ctx = _ctx ? { ..._ctx, async: true } : { async: true };
let result = schema._zod.run({ value, issues: [] }, ctx);
if (result instanceof Promise)
result = await result;
return result.issues.length
? {
success: false,
error: new _Err(result.issues.map((iss) => util.finalizeIssue(iss, ctx, core.config()))),
}
: { success: true, data: result.value };
};
export const safeParseAsync = /* @__PURE__*/ _safeParseAsync(errors.$ZodRealError);
export const _encode = (_Err) => (schema, value, _ctx) => {
const ctx = _ctx ? { ..._ctx, direction: "backward" } : { direction: "backward" };
return _parse(_Err)(schema, value, ctx);
};
export const encode = /* @__PURE__*/ _encode(errors.$ZodRealError);
export const _decode = (_Err) => (schema, value, _ctx) => {
return _parse(_Err)(schema, value, _ctx);
};
export const decode = /* @__PURE__*/ _decode(errors.$ZodRealError);
export const _encodeAsync = (_Err) => async (schema, value, _ctx) => {
const ctx = _ctx ? { ..._ctx, direction: "backward" } : { direction: "backward" };
return _parseAsync(_Err)(schema, value, ctx);
};
export const encodeAsync = /* @__PURE__*/ _encodeAsync(errors.$ZodRealError);
export const _decodeAsync = (_Err) => async (schema, value, _ctx) => {
return _parseAsync(_Err)(schema, value, _ctx);
};
export const decodeAsync = /* @__PURE__*/ _decodeAsync(errors.$ZodRealError);
export const _safeEncode = (_Err) => (schema, value, _ctx) => {
const ctx = _ctx ? { ..._ctx, direction: "backward" } : { direction: "backward" };
return _safeParse(_Err)(schema, value, ctx);
};
export const safeEncode = /* @__PURE__*/ _safeEncode(errors.$ZodRealError);
export const _safeDecode = (_Err) => (schema, value, _ctx) => {
return _safeParse(_Err)(schema, value, _ctx);
};
export const safeDecode = /* @__PURE__*/ _safeDecode(errors.$ZodRealError);
export const _safeEncodeAsync = (_Err) => async (schema, value, _ctx) => {
const ctx = _ctx ? { ..._ctx, direction: "backward" } : { direction: "backward" };
return _safeParseAsync(_Err)(schema, value, ctx);
};
export const safeEncodeAsync = /* @__PURE__*/ _safeEncodeAsync(errors.$ZodRealError);
export const _safeDecodeAsync = (_Err) => async (schema, value, _ctx) => {
return _safeParseAsync(_Err)(schema, value, _ctx);
};
export const safeDecodeAsync = /* @__PURE__*/ _safeDecodeAsync(errors.$ZodRealError);

View File

@@ -0,0 +1,16 @@
declare module 'timers' {
function setTimeout(callback: (...args: any[]) => void, ms: number, ...args: any[]): NodeJS.Timeout;
namespace setTimeout {
function __promisify__(ms: number): Promise<void>;
function __promisify__<T>(ms: number, value: T): Promise<T>;
}
function clearTimeout(timeoutId: NodeJS.Timeout | string | number | undefined): void;
function setInterval(callback: (...args: any[]) => void, ms: number, ...args: any[]): NodeJS.Timeout;
function clearInterval(intervalId: NodeJS.Timeout | string | number | undefined): void;
function setImmediate(callback: (...args: any[]) => void, ...args: any[]): NodeJS.Immediate;
namespace setImmediate {
function __promisify__(): Promise<void>;
function __promisify__<T>(value: T): Promise<T>;
}
function clearImmediate(immediateId: NodeJS.Immediate | undefined): void;
}

View File

@@ -0,0 +1,11 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.RuleTester = void 0;
/* eslint-disable @typescript-eslint/no-deprecated */
const eslint_1 = require("eslint");
/**
* @deprecated Use `@typescript-eslint/rule-tester` instead.
*/
class RuleTester extends eslint_1.RuleTester {
}
exports.RuleTester = RuleTester;

View File

@@ -0,0 +1,854 @@
// @flow
type Exclude<A, B> = A;
// see https://gist.github.com/thecotne/6e5969f4aaf8f253985ed36b30ac9fe0
type $FlowGen$If<X: boolean, Then, Else = empty> = $Call<
((true, Then, Else) => Then) & ((false, Then, Else) => Else),
X,
Then,
Else
>;
type $FlowGen$Assignable<A, B> = $Call<
((...r: [B]) => true) & ((...r: [A]) => false),
A
>;
import type {
Angle,
CssColor,
Rule,
CustomProperty,
EnvironmentVariable,
Function,
Image,
LengthValue,
MediaQuery,
Declaration,
Ratio,
Resolution,
Selector,
SupportsCondition,
Time,
Token,
TokenOrValue,
UnknownAtRule,
Url,
Variable,
StyleRule,
DeclarationBlock,
ParsedComponent,
Multiplier,
StyleSheet,
Location2,
} from "./ast.js.flow";
import { Targets, Features } from "./targets.js.flow";
declare export * from "./ast.js.flow";
declare export { Targets, Features };
export type TransformOptions<C: CustomAtRules> = {|
/**
* The filename being transformed. Used for error messages and source maps.
*/
filename: string,
/**
* The source code to transform.
*/
code: Uint8Array,
/**
* Whether to enable minification.
*/
minify?: boolean,
/**
* Whether to output a source map.
*/
sourceMap?: boolean,
/**
* An input source map to extend.
*/
inputSourceMap?: string,
/**
* An optional project root path, used as the source root in the output source map.
* Also used to generate relative paths for sources used in CSS module hashes.
*/
projectRoot?: string,
/**
* The browser targets for the generated code.
*/
targets?: Targets,
/**
* Features that should always be compiled, even when supported by targets.
*/
include?: number,
/**
* Features that should never be compiled, even when unsupported by targets.
*/
exclude?: number,
/**
* Whether to enable parsing various draft syntax.
*/
drafts?: Drafts,
/**
* Whether to enable various non-standard syntax.
*/
nonStandard?: NonStandard,
/**
* Whether to compile this file as a CSS module.
*/
cssModules?: boolean | CSSModulesConfig,
/**
* Whether to analyze dependencies (e.g. string).
* When enabled, string dependencies
* are replaced with hashed placeholders that can be replaced with the final
* urls later (after bundling). Dependencies are returned as part of the result.
*/
analyzeDependencies?: boolean | DependencyOptions,
/**
* Replaces user action pseudo classes with class names that can be applied from JavaScript.
* This is useful for polyfills, for example.
*/
pseudoClasses?: PseudoClasses,
/**
* A list of class names, ids, and custom identifiers (e.g. @keyframes) that are known
* to be unused. These will be removed during minification. Note that these are not
* selectors but individual names (without any . or # prefixes).
*/
unusedSymbols?: string[],
/**
* Whether to ignore invalid rules and declarations rather than erroring.
* When enabled, warnings are returned, and the invalid rule or declaration is
* omitted from the output code.
*/
errorRecovery?: boolean,
/**
* An AST visitor object. This allows custom transforms or analysis to be implemented in JavaScript.
* Multiple visitors can be composed into one using the string function.
* For optimal performance, visitors should be as specific as possible about what types of values
* they care about so that JavaScript has to be called as little as possible.
*/
visitor?: Visitor<C> | VisitorFunction<C>,
/**
* Defines how to parse custom CSS at-rules. Each at-rule can have a prelude, defined using a CSS
* [syntax string](https://drafts.css-houdini.org/css-properties-values-api/#syntax-strings), and
* a block body. The body can be a declaration list, rule list, or style block as defined in the
* [css spec](https://drafts.csswg.org/css-syntax/#declaration-rule-list).
*/
customAtRules?: C,
|};
declare type PropertyStart =
| "-"
| "_"
| "a"
| "b"
| "c"
| "d"
| "e"
| "f"
| "g"
| "h"
| "i"
| "j"
| "k"
| "l"
| "m"
| "n"
| "o"
| "p"
| "q"
| "r"
| "s"
| "t"
| "u"
| "v"
| "w"
| "x"
| "y"
| "z";
export type ReturnedDeclaration =
| Declaration
| {|
/**
* The property name.
*/
property: string,
/**
* The raw string value for the declaration.
*/
raw: string,
|};
export type ReturnedMediaQuery =
| MediaQuery
| {|
/**
* The raw string value for the media query.
*/
raw: string,
|};
declare type FindByType<Union, Name> = $FlowGen$If<
$FlowGen$Assignable<
Union,
{|
type: Name,
|}
>,
Union,
empty
>;
export type ReturnedRule = Rule<ReturnedDeclaration, ReturnedMediaQuery>;
declare type RequiredValue<Rule> = $FlowGen$If<
$FlowGen$Assignable<
Rule,
{|
value: { [key: string]: any },
|}
>,
$FlowGen$If<
$FlowGen$Assignable<$PropertyType<Rule, "value">, StyleRule>,
{|
...Rule,
...{|
value: {|
...Required<StyleRule>,
...{|
declarations: Required<DeclarationBlock>,
|},
|},
|},
|},
{|
...Rule,
...{|
value: Required<$PropertyType<Rule, "value">>,
|},
|}
>,
Rule
>;
declare type RuleVisitor<R = RequiredValue<Rule>> = (
rule: R
) => ReturnedRule | ReturnedRule[] | void;
declare type MappedRuleVisitors = $ObjMapi<
{ [k: Exclude<$PropertyType<Rule, "type">, "unknown" | "custom">]: any },
<Name>(Name) => RuleVisitor<RequiredValue<FindByType<Rule, Name>>>
>;
declare type UnknownVisitors<T> = {
[name: string]: RuleVisitor<T>,
};
declare type CustomVisitors<T: CustomAtRules> = $ObjMapi<
T,
<Name>(Name) => RuleVisitor<CustomAtRule<Name, $ElementType<T, Name>>>
>;
declare type AnyCustomAtRule<C: CustomAtRules> = $ElementType<
$ObjMapi<C, <Key>(Key) => CustomAtRule<Key, $ElementType<C, Key>>>,
$Keys<C>
>;
declare type RuleVisitors<C: CustomAtRules> = {|
...MappedRuleVisitors,
...{|
unknown?:
| UnknownVisitors<UnknownAtRule>
| $Diff<
RuleVisitor<UnknownAtRule>,
{ [key: $Keys<CallableFunction>]: any }
>,
custom?:
| CustomVisitors<C>
| $Diff<
RuleVisitor<AnyCustomAtRule<C>>,
{ [key: $Keys<CallableFunction>]: any }
>,
|},
|};
declare type PreludeTypes = Exclude<
$PropertyType<ParsedComponent, "type">,
"literal" | "repeated" | "token"
>;
declare type SyntaxString = string | string;
declare type ComponentTypes = $ObjMapi<
{ [k: PreludeTypes]: any },
<Key>(Key) => FindByType<ParsedComponent, Key>
>;
declare type Repetitions = $ObjMapi<
{ [k: PreludeTypes]: any },
<Key>(Key) => {|
type: "repeated",
value: {|
components: FindByType<ParsedComponent, Key>[],
multiplier: Multiplier,
|},
|}
>;
declare type MappedPrelude = {| ...ComponentTypes, ...Repetitions |};
declare type MappedBody<P: $PropertyType<CustomAtRuleDefinition, "body">> =
$FlowGen$If<$FlowGen$Assignable<P, "style-block">, "rule-list", P>;
declare type CustomAtRule<N, R: CustomAtRuleDefinition> = {|
name: N,
prelude: $FlowGen$If<
$FlowGen$Assignable<$PropertyType<R, "prelude">, $Keys<MappedPrelude>>,
$ElementType<MappedPrelude, $PropertyType<R, "prelude">>,
ParsedComponent
>,
body: FindByType<CustomAtRuleBody, MappedBody<$PropertyType<R, "body">>>,
loc: Location2,
|};
declare type CustomAtRuleBody =
| {|
type: "declaration-list",
value: Required<DeclarationBlock>,
|}
| {|
type: "rule-list",
value: RequiredValue<Rule>[],
|};
declare type FindProperty<Union, Name> = $FlowGen$If<
$FlowGen$Assignable<
Union,
{|
property: Name,
|}
>,
Union,
empty
>;
declare type DeclarationVisitor<P = Declaration> = (
property: P
) => ReturnedDeclaration | ReturnedDeclaration[] | void;
declare type MappedDeclarationVisitors = $ObjMapi<
{
[k: Exclude<
$PropertyType<Declaration, "property">,
"unparsed" | "custom"
>]: any,
},
<Name>(
Name
) => DeclarationVisitor<
FindProperty<Declaration, Name> | FindProperty<Declaration, "unparsed">
>
>;
declare type CustomPropertyVisitors = {
[name: string]: DeclarationVisitor<CustomProperty>,
};
declare type DeclarationVisitors = {|
...MappedDeclarationVisitors,
...{|
custom?: CustomPropertyVisitors | DeclarationVisitor<CustomProperty>,
|},
|};
declare type RawValue = {|
/**
* A raw string value which will be parsed like CSS.
*/
raw: string,
|};
declare type TokenReturnValue = TokenOrValue | TokenOrValue[] | RawValue | void;
declare type TokenVisitor = (token: Token) => TokenReturnValue;
declare type VisitableTokenTypes =
| "ident"
| "at-keyword"
| "hash"
| "id-hash"
| "string"
| "number"
| "percentage"
| "dimension";
declare type TokenVisitors = $ObjMapi<
{ [k: VisitableTokenTypes]: any },
<Name>(Name) => (token: FindByType<Token, Name>) => TokenReturnValue
>;
declare type FunctionVisitor = (fn: Function) => TokenReturnValue;
declare type EnvironmentVariableVisitor = (
env: EnvironmentVariable
) => TokenReturnValue;
declare type EnvironmentVariableVisitors = {
[name: string]: EnvironmentVariableVisitor,
};
export type Visitor<C: CustomAtRules> = {|
StyleSheet?: (
stylesheet: StyleSheet
) => StyleSheet<ReturnedDeclaration, ReturnedMediaQuery> | void,
StyleSheetExit?: (
stylesheet: StyleSheet
) => StyleSheet<ReturnedDeclaration, ReturnedMediaQuery> | void,
Rule?: RuleVisitor<> | RuleVisitors<C>,
RuleExit?: RuleVisitor<> | RuleVisitors<C>,
Declaration?: DeclarationVisitor<> | DeclarationVisitors,
DeclarationExit?: DeclarationVisitor<> | DeclarationVisitors,
Url?: (url: Url) => Url | void,
Color?: (color: CssColor) => CssColor | void,
Image?: (image: Image) => Image | void,
ImageExit?: (image: Image) => Image | void,
Length?: (length: LengthValue) => LengthValue | void,
Angle?: (angle: Angle) => Angle | void,
Ratio?: (ratio: Ratio) => Ratio | void,
Resolution?: (resolution: Resolution) => Resolution | void,
Time?: (time: Time) => Time | void,
CustomIdent?: (ident: string) => string | void,
DashedIdent?: (ident: string) => string | void,
MediaQuery?: (
query: MediaQuery
) => ReturnedMediaQuery | ReturnedMediaQuery[] | void,
MediaQueryExit?: (
query: MediaQuery
) => ReturnedMediaQuery | ReturnedMediaQuery[] | void,
SupportsCondition?: (condition: SupportsCondition) => SupportsCondition,
SupportsConditionExit?: (condition: SupportsCondition) => SupportsCondition,
Selector?: (selector: Selector) => Selector | Selector[] | void,
Token?: TokenVisitor | TokenVisitors,
Function?:
| FunctionVisitor
| {
[name: string]: FunctionVisitor,
},
FunctionExit?:
| FunctionVisitor
| {
[name: string]: FunctionVisitor,
},
Variable?: (variable: Variable) => TokenReturnValue,
VariableExit?: (variable: Variable) => TokenReturnValue,
EnvironmentVariable?:
| EnvironmentVariableVisitor
| EnvironmentVariableVisitors,
EnvironmentVariableExit?:
| EnvironmentVariableVisitor
| EnvironmentVariableVisitors,
|};
export type VisitorDependency = FileDependency | GlobDependency;
export type VisitorOptions = {|
addDependency: (dep: VisitorDependency) => void,
|};
export type VisitorFunction<C: CustomAtRules> = (
options: VisitorOptions
) => Visitor<C>;
export type CustomAtRules = {|
[name: string]: CustomAtRuleDefinition,
|};
export type CustomAtRuleDefinition = {|
/**
* Defines the syntax for a custom at-rule prelude. The value should be a
* CSS [syntax string](https://drafts.css-houdini.org/css-properties-values-api/#syntax-strings)
* representing the types of values that are accepted. This property may be omitted or
* set to null to indicate that no prelude is accepted.
*/
prelude?: SyntaxString | null,
/**
* Defines the type of body contained within the at-rule block.
* - declaration-list: A CSS declaration list, as in a style rule.
* - rule-list: A list of CSS rules, as supported within a non-nested
* at-rule such as string.
* - style-block: Both a declaration list and rule list, as accepted within
* a nested at-rule within a style rule (e.g. string inside a style rule
* with directly nested declarations).
*/
body?: "declaration-list" | "rule-list" | "style-block" | null,
|};
export type DependencyOptions = {|
/**
* Whether to preserve string rules rather than removing them.
*/
preserveImports?: boolean,
|};
export type BundleOptions<C: CustomAtRules> = $Diff<
TransformOptions<C>,
{| code: any |}
>;
export type BundleAsyncOptions<C: CustomAtRules> = {|
...$Exact<BundleOptions<C>>,
resolver?: Resolver,
|};
declare type MaybePromise<T> = T | Promise<T>;
/**
* Custom resolver to use when loading CSS files.
*/
export type Resolver = {|
/**
* Read the given file and return its contents as a string.
*/
read?: (file: string) => string | Promise<string>,
/**
* Resolve the given CSS import specifier from the provided originating file to a
* path which gets passed to string.
*/
resolve?: (
specifier: string,
originatingFile: string
) => MaybePromise<
| string
| {|
external: string,
|}
>,
|};
export type Drafts = {|
/**
* Whether to enable @custom-media rules.
*/
customMedia?: boolean,
/**
* Whether to enable the scroll navigation controls.
* https://drafts.csswg.org/css-overflow-5/#scroll-navigation
*/
scrollNavigationControls?: boolean,
|};
export type NonStandard = {|
/**
* Whether to enable the non-standard >>> and /deep/ selector combinators used by Angular and Vue.
*/
deepSelectorCombinator?: boolean,
|};
export type PseudoClasses = {|
hover?: string,
active?: string,
focus?: string,
focusVisible?: string,
focusWithin?: string,
|};
export type TransformResult = {|
/**
* The transformed code.
*/
code: Uint8Array,
/**
* The generated source map, if enabled.
*/
map: Uint8Array | void,
/**
* CSS module exports, if enabled.
*/
exports: CSSModuleExports | void,
/**
* CSS module references, if string is enabled.
*/
references: CSSModuleReferences,
/**
* string dependencies, if enabled.
*/
dependencies: Dependency[] | void,
/**
* Warnings that occurred during compilation.
*/
warnings: Warning[],
|};
export type Warning = {|
message: string,
type: string,
value?: any,
loc: ErrorLocation,
|};
export type CSSModulesConfig = {|
/**
* The pattern to use when renaming class names and other identifiers. Default is string.
*/
pattern?: string,
/**
* Whether to rename dashed identifiers, e.g. custom properties.
*/
dashedIdents?: boolean,
/**
* Whether to enable hashing for string.
*/
animation?: boolean,
/**
* Whether to enable hashing for CSS grid identifiers.
*/
grid?: boolean,
/**
* Whether to enable hashing for string names.
*/
container?: boolean,
/**
* Whether to enable hashing for custom identifiers.
*/
customIdents?: boolean,
/**
* Whether to require at least one class or id selector in each rule.
*/
pure?: boolean,
|};
export type CSSModuleExports = {
/**
* Maps exported (i.e. original) names to local names.
*/
[name: string]: CSSModuleExport,
};
export type CSSModuleExport = {|
/**
* The local (compiled) name for this export.
*/
name: string,
/**
* Whether the export is referenced in this file.
*/
isReferenced: boolean,
/**
* Other names that are composed by this export.
*/
composes: CSSModuleReference[],
|};
export type CSSModuleReferences = {
/**
* Maps placeholder names to references.
*/
[name: string]: DependencyCSSModuleReference,
};
export type CSSModuleReference =
| LocalCSSModuleReference
| GlobalCSSModuleReference
| DependencyCSSModuleReference;
export type LocalCSSModuleReference = {|
type: "local",
/**
* The local (compiled) name for the reference.
*/
name: string,
|};
export type GlobalCSSModuleReference = {|
type: "global",
/**
* The referenced global name.
*/
name: string,
|};
export type DependencyCSSModuleReference = {|
type: "dependency",
/**
* The name to reference within the dependency.
*/
name: string,
/**
* The dependency specifier for the referenced file.
*/
specifier: string,
|};
export type Dependency =
| ImportDependency
| UrlDependency
| FileDependency
| GlobDependency;
export type ImportDependency = {|
type: "import",
/**
* The url of the string dependency.
*/
url: string,
/**
* The media query for the string rule.
*/
media: string | null,
/**
* The string rule.
*/
supports: string | null,
/**
* The source location where the string rule was found.
*/
loc: SourceLocation,
/**
* The placeholder that the import was replaced with.
*/
placeholder: string,
|};
export type UrlDependency = {|
type: "url",
/**
* The url of the dependency.
*/
url: string,
/**
* The source location where the string was found.
*/
loc: SourceLocation,
/**
* The placeholder that the url was replaced with.
*/
placeholder: string,
|};
export type FileDependency = {|
type: "file",
filePath: string,
|};
export type GlobDependency = {|
type: "glob",
glob: string,
|};
export type SourceLocation = {|
/**
* The file path in which the dependency exists.
*/
filePath: string,
/**
* The start location of the dependency.
*/
start: Location,
/**
* The end location (inclusive) of the dependency.
*/
end: Location,
|};
export type Location = {|
/**
* The line number (1-based).
*/
line: number,
/**
* The column number (0-based).
*/
column: number,
|};
export type ErrorLocation = {|
...$Exact<Location>,
filename: string,
|};
/**
* Compiles a CSS file, including optionally minifying and lowering syntax to the given
* targets. A source map may also be generated, but this is not enabled by default.
*/
declare export function transform<C: CustomAtRules>(
options: TransformOptions<C>
): TransformResult;
export type TransformAttributeOptions = {|
/**
* The filename in which the style attribute appeared. Used for error messages and dependencies.
*/
filename?: string,
/**
* The source code to transform.
*/
code: Uint8Array,
/**
* Whether to enable minification.
*/
minify?: boolean,
/**
* The browser targets for the generated code.
*/
targets?: Targets,
/**
* Whether to analyze string dependencies.
* When enabled, string dependencies are replaced with hashed placeholders
* that can be replaced with the final urls later (after bundling).
* Dependencies are returned as part of the result.
*/
analyzeDependencies?: boolean,
/**
* Whether to ignore invalid rules and declarations rather than erroring.
* When enabled, warnings are returned, and the invalid rule or declaration is
* omitted from the output code.
*/
errorRecovery?: boolean,
/**
* An AST visitor object. This allows custom transforms or analysis to be implemented in JavaScript.
* Multiple visitors can be composed into one using the string function.
* For optimal performance, visitors should be as specific as possible about what types of values
* they care about so that JavaScript has to be called as little as possible.
*/
visitor?: Visitor<empty> | VisitorFunction<empty>,
|};
export type TransformAttributeResult = {|
/**
* The transformed code.
*/
code: Uint8Array,
/**
* string dependencies, if enabled.
*/
dependencies: Dependency[] | void,
/**
* Warnings that occurred during compilation.
*/
warnings: Warning[],
|};
/**
* Compiles a single CSS declaration list, such as an inline style attribute in HTML.
*/
declare export function transformStyleAttribute(
options: TransformAttributeOptions
): TransformAttributeResult;
/**
* Converts a browserslist result into targets that can be passed to lightningcss.
* @param browserslist the result of calling string
*/
declare export function browserslistToTargets(browserslist: string[]): Targets;
/**
* Bundles a CSS file and its dependencies, inlining @import rules.
*/
declare export function bundle<C: CustomAtRules>(
options: BundleOptions<C>
): TransformResult;
/**
* Bundles a CSS file and its dependencies asynchronously, inlining @import rules.
*/
declare export function bundleAsync<C: CustomAtRules>(
options: BundleAsyncOptions<C>
): Promise<TransformResult>;
/**
* Composes multiple visitor objects into a single one.
*/
declare export function composeVisitors<C: CustomAtRules>(
visitors: (Visitor<C> | VisitorFunction<C>)[]
): Visitor<C> | VisitorFunction<C>;

View File

@@ -0,0 +1,38 @@
{
"name": "escape-string-regexp",
"version": "4.0.0",
"description": "Escape RegExp special characters",
"license": "MIT",
"repository": "sindresorhus/escape-string-regexp",
"funding": "https://github.com/sponsors/sindresorhus",
"author": {
"name": "Sindre Sorhus",
"email": "sindresorhus@gmail.com",
"url": "https://sindresorhus.com"
},
"engines": {
"node": ">=10"
},
"scripts": {
"test": "xo && ava && tsd"
},
"files": [
"index.js",
"index.d.ts"
],
"keywords": [
"escape",
"regex",
"regexp",
"regular",
"expression",
"string",
"special",
"characters"
],
"devDependencies": {
"ava": "^1.4.1",
"tsd": "^0.11.0",
"xo": "^0.28.3"
}
}