@eslint/css-tree
Version:
A tool set for CSS: fast detailed parser (CSS → AST), walker (AST traversal), generator (AST → CSS) and lexer (validation and matching) based on specs and browser implementations
1,582 lines (1,361 loc) • 98.5 kB
TypeScript
/**
* @fileoverview Type definitions for @eslint/css-tree
* @author ScriptHunter7
* @license MIT
* Based on https://github.com/scripthunter7/DefinitelyTyped/blob/master/types/css-tree/index.d.ts
*/
/*
* MIT License
* Copyright (c) Microsoft Corporation.
*
* 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
*/
// FIXME: Custom context / nodes for every fork, maybe add a template for internal context
// ----------------------------------------------------------
// CSS Locations
// ----------------------------------------------------------
/**
* Represents a location within a CSS source.
*/
export interface CssLocation {
/**
* The 0-indexed character offset from the beginning of the source.
*/
offset: number;
/**
* The 1-indexed line number.
*/
line: number;
/**
* The 1-indexed column number.
*/
column: number;
}
/**
* Represents a range of locations within a CSS source.
*/
export interface CssLocationRange {
/**
* The source file name. If not provided, it will be set to `<unknown>`.
*/
source: string;
/**
* The starting location of the range.
*/
start: CssLocation;
/**
* The ending location of the range.
*/
end: CssLocation;
}
// ----------------------------------------------------------
// Linked list utils
// https://github.com/csstree/csstree/blob/master/lib/utils/List.js
// ----------------------------------------------------------
/**
* Represents an item in a linked list.
*
* @template TData - The type of data stored in the item.
*/
export interface ListItem<TData> {
/**
* The previous item in the list.
*/
prev: ListItem<TData> | null;
/**
* The next item in the list.
*/
next: ListItem<TData> | null;
/**
* The data stored in the item.
*/
data: TData;
}
/**
* A callback function used for iterating over a list.
*
* @template TData - The type of data in the list.
* @template TResult - The type of the result returned by the function.
* @template TContext - The type of the context object passed to the function. Defaults to List<TData>.
*
* @param {TData} item - The current item being iterated over.
* @param {ListItem<TData>} node - The list item associated with the current item.
* @param {List<TData>} list - The list being iterated over.
* @returns {TResult} The result of the function.
*/
export type IteratorFn<TData, TResult, TContext = List<TData>> = (
this: TContext,
item: TData,
node: ListItem<TData>,
list: List<TData>,
) => TResult;
/**
* A callback function used for filtering a list.
*
* @template TData - The type of data in the list.
* @template TResult - The type of the result returned by the function, which must extend TData.
* @template TContext - The type of the context object passed to the function. Defaults to List<TData>.
*
* @param {TData} item - The current item being iterated over.
* @param {ListItem<TData>} node - The list item associated with the current item.
* @param {List<TData>} list - The list being filtered.
* @returns {boolean} Whether the item should be included in the filtered list.
*/
export type FilterFn<TData, TResult extends TData, TContext = List<TData>> = (
this: TContext,
item: TData,
node: ListItem<TData>,
list: List<TData>,
) => item is TResult;
/**
* A callback function used for reducing a list to a single value.
*
* @template TData - The type of data in the list.
* @template TValue - The type of the accumulator value.
* @template TContext - The type of the context object passed to the function. Defaults to List<TData>.
*
* @param {TValue} accum - The accumulator value.
* @param {TData} data - The current item being iterated over.
* @param {ListItem<TData>} node - The list item associated with the current item.
* @param {List<TData>} list - The list being reduced.
* @returns {TValue} The new accumulator value.
*/
export type ReduceFn<TData, TValue, TContext = List<TData>> = (this: TContext, accum: TValue, data: TData) => TValue;
/**
* A doubly linked list implementation.
*
* ```plaintext
* list
* ┌──────┐
* ┌──────────────┼─head │
* │ │ tail─┼─────────────┐
* │ └──────┘ │
* ▼ ▼
* item item item item
* ┌──────┐ ┌──────┐ ┌──────┐ ┌──────┐
* null <──┼─prev │<───┼─prev │<───┼─prev │<───┼─prev │
* │ next─┼───>│ next─┼───>│ next─┼───>│ next─┼──> null
* ├──────┤ ├──────┤ ├──────┤ ├──────┤
* │ data │ │ data │ │ data │ │ data │
* └──────┘ └──────┘ └──────┘ └──────┘
* ```
*
* @template TData - The type of data stored in the list elements.
*/
export class List<TData> {
/**
* Creates a new empty linked list.
*/
constructor();
/**
* Static factory method for creating list items.
*
* @param data Item data.
* @returns
*/
static createItem<TData>(data: TData): ListItem<TData>;
/**
* Gets the number of items in the list.
*
* @returns {number} The number of items in the list.
*/
get size(): number;
/**
* Checks if the list is empty.
*
* @returns {boolean} True if the list is empty, false otherwise.
*/
get isEmpty(): boolean;
/**
* Gets the first item in the list.
*
* @returns {TData | null} The first item in the list, or null if the list is empty.
*/
get first(): TData | null;
/**
* Gets the last item in the list.
*
* @returns {TData | null} The last item in the list, or null if the list is empty.
*/
get last(): TData | null;
/**
* Returns an iterator for the list.
*
* @returns {IterableIterator<TData>} An iterator for the list.
*/
[Symbol.iterator](): IterableIterator<TData>;
/**
* Creates a new list from an array.
*
* @param {TData[]} array - The array to create the list from.
* @returns {List<TData>} The new list.
*/
fromArray(array: TData[]): List<TData>;
/**
* Creates a new list item.
*
* @param {TData} data - The data to store in the item.
* @returns {ListItem<TData>} The new list item.
*/
createItem(data: TData): ListItem<TData>;
/**
* Converts the list to an array.
*
* @returns {TData[]} The list as an array.
*/
toArray(): TData[];
/**
* Converts the list to a JSON array.
*
* @returns {TData[]} The list as a JSON array.
*/
toJSON(): TData[];
/**
* Iterates over each item in the list, calling the provided callback function for each item.
*
* @template TContext - The type of the context object passed to the callback function.
*
* @param {IteratorFn<TData, void, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
*/
forEach<TContext>(fn: IteratorFn<TData, void, TContext>, context: TContext): void;
forEach(fn: IteratorFn<TData, void>): void;
/**
* Iterates over each item in the list, starting from the end and moving towards the beginning, calling the provided callback function for each item.
*
* @template TContext - The type of the context object passed to the callback function.
*
* @param {IteratorFn<TData, void, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
*/
forEachRight<TContext>(fn: IteratorFn<TData, void, TContext>, context: TContext): void;
forEachRight(fn: IteratorFn<TData, void>): void;
/**
* Iterates over the items in the list starting from the specified item until the provided callback function returns true.
*
* @template TContext - The type of the context object passed to the callback function.
*
* @param {ListItem<TData>} start - The starting item for the iteration.
* @param {IteratorFn<TData, boolean, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
*/
nextUntil<TContext>(start: ListItem<TData>, fn: IteratorFn<TData, boolean, TContext>, context: TContext): void;
nextUntil(start: ListItem<TData>, fn: IteratorFn<TData, boolean>): void;
/**
* Iterates over the items in the list starting from the specified item and moving towards the beginning until the provided callback function returns true.
*
* @template TContext - The type of the context object passed to the callback function.
*
* @param {ListItem<TData>} start - The starting item for the iteration.
* @param {IteratorFn<TData, boolean, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
*/
prevUntil<TContext>(start: ListItem<TData>, fn: IteratorFn<TData, boolean, TContext>, context: TContext): void;
prevUntil(start: ListItem<TData>, fn: IteratorFn<TData, boolean>): void;
/**
* Reduces the list to a single value.
*
* @template TValue - The type of the accumulator value.
* @template TContext - The type of the context object passed to the callback function.
*
* @param {ReduceFn<TData, TValue, TContext>} fn - The callback function to be called for each item.
* @param {TValue} initialValue - The initial value of the accumulator.
* @param {TContext} context - The context object to be passed to the callback function.
* @returns {TValue} The final value of the accumulator.
*/
reduce<TValue, TContext>(fn: ReduceFn<TData, TValue, TContext>, initialValue: TValue, context: TContext): TValue;
reduce<TValue>(fn: ReduceFn<TData, TValue>, initialValue: TValue): TValue;
/**
* Reduces the list to a single value, starting from the end and moving towards the beginning.
*
* @template TValue - The type of the accumulator value.
* @template TContext - The type of the context object passed to the callback function.
*
* @param {ReduceFn<TData, TValue, TContext>} fn - The callback function to be called for each item.
* @param {TValue} initialValue - The initial value of the accumulator.
* @param {TContext} context - The context object to be passed to the callback function.
* @returns {TValue} The final value of the accumulator.
*/
reduceRight<TValue, TContext>(
fn: ReduceFn<TData, TValue, TContext>,
initialValue: TValue,
context: TContext,
): TValue;
reduceRight<TValue>(fn: ReduceFn<TData, TValue>, initialValue: TValue): TValue;
/**
* Checks if at least one item in the list satisfies the provided callback function.
*
* @template TContext - The type of the context object passed to the callback function.
*
* @param {IteratorFn<TData, boolean, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
* @returns {boolean} True if at least one item satisfies the callback function, false otherwise.
*/
some<TContext>(fn: IteratorFn<TData, boolean, TContext>, context: TContext): boolean;
some(fn: IteratorFn<TData, boolean>): boolean;
/**
* Creates a new list by applying the provided callback function to each item in the current list.
*
* @template TContext - The type of the context object passed to the callback function.
* @template TResult - The type of the elements in the new list.
*
* @param {IteratorFn<TData, TResult, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
* @returns {List<TResult>} The new list containing the transformed elements.
*/
map<TContext, TResult>(fn: IteratorFn<TData, TResult, TContext>, context: TContext): List<TResult>;
map<TResult>(fn: IteratorFn<TData, TResult>): List<TResult>;
/**
* Creates a new list containing only the items from the current list that satisfy the provided callback function.
*
* @template TContext - The type of the context object passed to the callback function.
* @template TResult - The type of the elements in the new list, which must extend TData.
*
* @param {FilterFn<TData, TResult, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
* @returns {List<TResult>} The new list containing the filtered elements.
*/
filter<TContext, TResult extends TData>(fn: FilterFn<TData, TResult, TContext>, context: TContext): List<TResult>;
filter<TResult extends TData>(fn: FilterFn<TData, TResult>): List<TResult>;
/**
* Creates a new list containing only the items from the current list that satisfy the provided callback function.
*
* @template TContext - The type of the context object passed to the callback function.
*
* @param {IteratorFn<TData, boolean, TContext>} fn - The callback function to be called for each item.
* @param {TContext} context - The context object to be passed to the callback function.
* @returns {List<TData>} The new list containing the filtered elements.
*/
filter<TContext>(fn: IteratorFn<TData, boolean, TContext>, context: TContext): List<TData>;
filter(fn: IteratorFn<TData, boolean>): List<TData>;
/**
* Removes all items from the list.
*/
clear(): void;
/**
* Creates a copy of the list.
*
* @returns {List<TData>} A copy of the list.
*/
copy(): List<TData>;
/**
* Inserts an item at the beginning of the list.
*
* @param {ListItem<TData>} item - The item to insert.
* @returns {List<TData>} The list itself.
*/
prepend(item: ListItem<TData>): List<TData>;
/**
* Inserts a new item at the beginning of the list.
*
* @param {TData} data - The data for the new item.
* @returns {List<TData>} The list itself.
*/
prependData(data: TData): List<TData>;
/**
* Inserts an item at the end of the list.
*
* @param {ListItem<TData>} item - The item to insert.
* @returns {List<TData>} The list itself.
*/
append(item: ListItem<TData>): List<TData>;
/**
* Inserts a new item at the end of the list.
*
* @param {TData} data - The data for the new item.
* @returns {List<TData>} The list itself.
*/
appendData(data: TData): List<TData>;
/**
* Inserts an item before the specified item in the list.
*
* @param {ListItem<TData>} item - The item to insert.
* @param {ListItem<TData>} before - The item before which to insert the new item.
* @returns {List<TData>} The list itself.
*/
insert(item: ListItem<TData>, before: ListItem<TData>): List<TData>;
/**
* Inserts a new item before the specified item in the list.
*
* @param {TData} data - The data for the new item.
* @param {ListItem<TData>} before - The item before which to insert the new item.
* @returns {List<TData>} The list itself.
*/
insertData(data: TData, before: ListItem<TData>): List<TData>;
/**
* Removes an item from the list.
*
* @param {ListItem<TData>} item - The item to remove.
* @returns {ListItem<TData>} The removed item, or null if the item was not found.
*/
remove(item: ListItem<TData>): ListItem<TData>;
/**
* Adds an item to the end of the list.
*
* @param {TData} item - The item to add.
*/
push(item: TData): void;
/**
* Removes the last item from the list and returns it.
*
* @returns {ListItem<TData> | undefined} The removed item, or undefined if the list is empty.
*/
pop(): ListItem<TData> | undefined;
/**
* Adds an item to the beginning of the list.
*
* @param {TData} data - The data for the new item.
*/
unshift(data: TData): void;
/**
* Removes the first item from the list and returns it.
*
* @returns {ListItem<TData> | undefined} The removed item, or undefined if the list is empty.
*/
shift(): ListItem<TData> | undefined;
/**
* Inserts a list at the beginning of this list.
*
* @param {List<TData>} list - The list to insert.
* @returns {List<TData>} The list itself.
*/
prependList(list: List<TData>): List<TData>;
/**
* Inserts a list at the end of this list.
*
* @param {List<TData>} list - The list to insert.
* @returns {List<TData>} The list itself.
*/
appendList(list: List<TData>): List<TData>;
/**
* Inserts a list before the specified item in this list.
*
* @param {List<TData>} list - The list to insert.
* @param {ListItem<TData>} before - The item before which to insert the new list.
* @returns {List<TData>} The list itself.
*/
insertList(list: List<TData>, before: ListItem<TData>): List<TData>;
/**
* Replaces an item in the list with another item or list.
*
* @param {ListItem<TData>} oldItem - The item to replace.
* @param {List<TData> | ListItem<TData>} newItemOrList - The new item or list to insert.
* @returns {List<TData>} The list itself.
*/
replace(oldItem: ListItem<TData>, newItemOrList: List<TData> | ListItem<TData>): List<TData>;
}
// ----------------------------------------------------------
// CSS Nodes
// ----------------------------------------------------------
export interface CssNodeCommon {
type: string;
loc?: CssLocationRange | null;
}
export interface CssParentNodeCommon<T extends CssNode = CssNode> extends CssNodeCommon {
children: List<T>;
}
export interface CssParentNodeCommonPlain<T extends CssNodePlain = CssNodePlain> extends CssNodeCommon {
children: T[];
}
export interface CssOptionalParentNodeCommon<T extends CssNode = CssNode> extends CssNodeCommon {
children: List<T> | null;
}
export interface CssOptionalParentNodeCommonPlain<T extends CssNodePlain = CssNodePlain> extends CssNodeCommon {
children: T[] | null;
}
export interface AnPlusB extends CssNodeCommon {
type: "AnPlusB";
a: string | null;
b: string | null;
}
export interface Atrule extends CssNodeCommon {
type: "Atrule";
name: string;
prelude: AtrulePrelude | Raw | null;
block: Block | null;
}
export interface AtrulePlain extends CssNodeCommon {
type: "Atrule";
name: string;
prelude: AtrulePreludePlain | Raw | null;
block: BlockPlain | null;
}
export interface AtrulePrelude extends CssParentNodeCommon {
type: "AtrulePrelude";
}
export interface AtrulePreludePlain extends CssParentNodeCommonPlain {
type: "AtrulePrelude";
}
export interface AttributeSelector extends CssNodeCommon {
type: "AttributeSelector";
name: Identifier;
matcher: string | null;
value: StringNode | Identifier | null;
flags: string | null;
}
export interface Block extends CssParentNodeCommon {
type: "Block";
}
export interface BlockPlain extends CssParentNodeCommonPlain {
type: "Block";
}
export interface Brackets extends CssParentNodeCommon {
type: "Brackets";
}
export interface BracketsPlain extends CssParentNodeCommonPlain {
type: "Brackets";
}
export interface CDC extends CssNodeCommon {
type: "CDC";
}
export interface CDO extends CssNodeCommon {
type: "CDO";
}
export interface ClassSelector extends CssNodeCommon {
type: "ClassSelector";
name: string;
}
export interface Combinator extends CssNodeCommon {
type: "Combinator";
name: string;
}
export interface Comment extends CssNodeCommon {
type: "Comment";
value: string;
}
export interface Condition extends CssParentNodeCommon {
type: "Condition";
kind: string;
}
export interface ConditionPlain extends CssParentNodeCommonPlain {
type: "Condition";
kind: string;
}
export interface Declaration extends CssNodeCommon {
type: "Declaration";
important: boolean | string;
property: string;
value: Value | Raw;
}
export interface DeclarationPlain extends CssNodeCommon {
type: "Declaration";
important: boolean | string;
property: string;
value: ValuePlain | Raw;
}
export interface DeclarationList extends CssParentNodeCommon {
type: "DeclarationList";
}
export interface DeclarationListPlain extends CssParentNodeCommonPlain {
type: "DeclarationList";
}
export interface Dimension extends CssNodeCommon {
type: "Dimension";
value: string;
unit: string;
}
export interface Feature extends CssNodeCommon {
type: "Feature";
name: string;
kind: string;
value: Identifier | NumberNode | Dimension | Ratio | FunctionNode | null;
}
export interface FeatureFunction extends CssNodeCommon {
type: "FeatureFunction";
feature: string;
kind: string;
value: Declaration | Selector;
}
export interface FeatureFunctionPlain extends CssNodeCommon {
type: "FeatureFunction";
feature: string;
kind: string;
value: DeclarationPlain | SelectorPlain;
}
export interface FeatureRange extends CssNodeCommon {
type: "FeatureRange";
kind: string;
left: Identifier | NumberNode | Dimension | Ratio | FunctionNode;
leftComparison: string;
middle: Identifier | NumberNode | Dimension | Ratio | FunctionNode;
rightComparison: string | null;
right: Identifier | NumberNode | Dimension | Ratio | FunctionNode | null;
}
export interface FunctionNode extends CssParentNodeCommon {
type: "Function";
name: string;
}
export interface FunctionNodePlain extends CssParentNodeCommonPlain {
type: "Function";
name: string;
}
export interface Hash extends CssNodeCommon {
type: "Hash";
value: string;
}
export interface IdSelector extends CssNodeCommon {
type: "IdSelector";
name: string;
}
export interface Identifier extends CssNodeCommon {
type: "Identifier";
name: string;
}
export interface Layer extends CssNodeCommon {
type: "Layer";
name: string;
}
export interface LayerList extends CssParentNodeCommon<Layer> {
type: "LayerList";
}
export interface LayerListPlain extends CssParentNodeCommonPlain<Layer> {
type: "LayerList";
}
export interface MediaFeature extends CssNodeCommon {
type: "MediaFeature";
name: string;
value: Identifier | NumberNode | Dimension | Ratio | null;
}
export interface MediaQuery extends CssParentNodeCommon {
type: "MediaQuery";
}
export interface MediaQueryPlain extends CssParentNodeCommonPlain {
type: "MediaQuery";
}
export interface MediaQueryList extends CssParentNodeCommon<MediaQuery> {
type: "MediaQueryList";
}
export interface MediaQueryListPlain extends CssParentNodeCommonPlain<MediaQueryPlain> {
type: "MediaQueryList";
}
export interface NestingSelector extends CssNodeCommon {
type: "NestingSelector";
}
export interface Nth extends CssNodeCommon {
type: "Nth";
nth: AnPlusB | Identifier;
selector: SelectorList | null;
}
export interface NthPlain extends CssNodeCommon {
type: "Nth";
nth: AnPlusB | Identifier;
selector: SelectorListPlain | null;
}
export interface NumberNode extends CssNodeCommon {
type: "Number";
value: string;
}
export interface Operator extends CssNodeCommon {
type: "Operator";
value: string;
}
export interface Parentheses extends CssParentNodeCommon {
type: "Parentheses";
}
export interface ParenthesesPlain extends CssParentNodeCommonPlain {
type: "Parentheses";
}
export interface Percentage extends CssNodeCommon {
type: "Percentage";
value: string;
}
export interface PseudoClassSelector extends CssOptionalParentNodeCommon {
type: "PseudoClassSelector";
name: string;
}
export interface PseudoClassSelectorPlain extends CssOptionalParentNodeCommonPlain {
type: "PseudoClassSelector";
name: string;
}
export interface PseudoElementSelector extends CssOptionalParentNodeCommon {
type: "PseudoElementSelector";
name: string;
}
export interface PseudoElementSelectorPlain extends CssOptionalParentNodeCommonPlain {
type: "PseudoElementSelector";
name: string;
}
export interface Ratio extends CssNodeCommon {
type: "Ratio";
left: string;
right: string;
}
export interface Raw extends CssNodeCommon {
type: "Raw";
value: string;
}
export interface Rule extends CssNodeCommon {
type: "Rule";
prelude: SelectorList | Raw;
block: Block;
}
export interface RulePlain extends CssNodeCommon {
type: "Rule";
prelude: SelectorListPlain | Raw;
block: BlockPlain;
}
export interface Selector extends CssParentNodeCommon {
type: "Selector";
}
export interface SelectorPlain extends CssParentNodeCommonPlain {
type: "Selector";
}
export interface SelectorList extends CssParentNodeCommon {
type: "SelectorList";
}
export interface SelectorListPlain extends CssParentNodeCommonPlain {
type: "SelectorList";
}
export interface StringNode extends CssNodeCommon {
type: "String";
value: string;
}
export interface StyleSheet extends CssParentNodeCommon {
type: "StyleSheet";
}
export interface SupportsDeclaration extends CssNodeCommon {
type: "SupportsDeclaration";
declaration: Declaration | Raw;
}
export interface StyleSheetPlain extends CssParentNodeCommonPlain {
type: "StyleSheet";
}
export interface TypeSelector extends CssNodeCommon {
type: "TypeSelector";
name: string;
}
export interface UnicodeRange extends CssNodeCommon {
type: "UnicodeRange";
value: string;
}
export interface Url extends CssNodeCommon {
type: "Url";
value: string;
}
export interface Value extends CssParentNodeCommon {
type: "Value";
}
export interface ValuePlain extends CssParentNodeCommonPlain {
type: "Value";
}
export interface WhiteSpace extends CssNodeCommon {
type: "WhiteSpace";
value: string;
}
/* IMPORTANT! If you update this, also update `CssNodePlain` */
export type CssNode =
| AnPlusB
| Atrule
| AtrulePrelude
| AttributeSelector
| Block
| Brackets
| CDC
| CDO
| ClassSelector
| Combinator
| Comment
| Condition
| Declaration
| DeclarationList
| Dimension
| Feature
| FeatureFunction
| FeatureRange
| FunctionNode
| Hash
| IdSelector
| Identifier
| Layer
| LayerList
| MediaFeature
| MediaQuery
| MediaQueryList
| NestingSelector
| Nth
| NumberNode
| Operator
| Parentheses
| Percentage
| PseudoClassSelector
| PseudoElementSelector
| Ratio
| Raw
| Rule
| Selector
| SelectorList
| StringNode
| StyleSheet
| SupportsDeclaration
| TypeSelector
| UnicodeRange
| Url
| Value
| WhiteSpace;
/* IMPORTANT! If you update this, also update `CssNode` */
export type CssNodePlain =
| AnPlusB
| AtrulePlain
| AtrulePreludePlain
| AttributeSelector
| BlockPlain
| BracketsPlain
| CDC
| CDO
| ClassSelector
| Combinator
| Comment
| ConditionPlain
| DeclarationPlain
| DeclarationListPlain
| Dimension
| Feature
| FeatureFunctionPlain
| FeatureRange
| FunctionNodePlain
| Hash
| IdSelector
| Identifier
| Layer
| LayerListPlain
| MediaFeature
| MediaQueryPlain
| MediaQueryListPlain
| NestingSelector
| NthPlain
| NumberNode
| Operator
| ParenthesesPlain
| Percentage
| PseudoClassSelectorPlain
| PseudoElementSelectorPlain
| Ratio
| Raw
| RulePlain
| SelectorPlain
| SelectorListPlain
| StringNode
| StyleSheetPlain
| SupportsDeclaration
| TypeSelector
| UnicodeRange
| Url
| ValuePlain
| WhiteSpace;
type CssNodeNames = CssNode["type"];
type AnyCssNode = CssNode | CssNodePlain;
// ----------------------------------------------------------
// Tokenizer
// https://github.com/csstree/csstree/tree/master/lib/tokenizer
// ----------------------------------------------------------
type ReadonlyRecord<K extends keyof any, T> = Readonly<Record<K, T>>;
/**
* A dictionary mapping token names (strings) to their corresponding numeric token types.
*/
export const tokenTypes: ReadonlyRecord<string, number>;
/**
* An array containing all the possible token names as strings, indexed by their numeric token types.
*/
export const tokenNames: ReadonlyArray<string>;
/**
* A callback function used during tokenization. It takes three arguments:
*
* @param token - The numeric type of the current token.
* @param start - The starting index of the token in the source string.
* @param end - The ending index (exclusive) of the token in the source string.
*/
export type CssTokenizerCallback = (token: number, start: number, end: number) => void;
/**
* Represents the API for iterating over tokens in a CSS source string.
*/
export interface TokenIterateAPI {
/**
* The name of the file being parsed.
*/
filename: string;
/**
* The CSS source string being tokenized.
*/
source: string;
/**
* The total number of tokens in the stream.
*/
tokenCount: number;
/**
* Gets the type of the token at the specified index.
*
* @param index - The index of the token.
* @returns The numeric type of the token.
*/
getTokenType(index: number): number;
/**
* Gets the name of the token type at the specified index.
*
* @param index - The index of the token.
* @returns The string name of the token type.
*/
getTokenTypeName(index: number): string;
/**
* Gets the start position of the token at the specified index.
*
* @param index - The index of the token.
* @returns The starting character position of the token.
*/
getTokenStart(index: number): number;
/**
* Gets the end position of the token at the specified index.
*
* @param index - The index of the token.
* @returns The ending character position of the token.
*/
getTokenEnd(index: number): number;
/**
* Gets the value of the token at the specified index.
*
* @param index - The index of the token.
* @returns The string value of the token.
*/
getTokenValue(index: number): string;
/**
* Gets a substring from the source string.
*
* @param start - The starting index.
* @param end - The ending index.
* @returns The substring from the source.
*/
substring(start: number, end: number): string;
/**
* A Uint32Array containing balance information for tokens.
*/
balance: Uint32Array;
/**
* Checks if a token type represents a block opener.
*
* @param type - The token type to check.
* @returns True if the token type is a block opener.
*/
isBlockOpenerTokenType(type: number): boolean;
/**
* Checks if a token type represents a block closer.
*
* @param type - The token type to check.
* @returns True if the token type is a block closer.
*/
isBlockCloserTokenType(type: number): boolean;
/**
* Gets the index of the matching pair token for a block token.
*
* @param index - The index of the block token.
* @returns The index of the matching pair token.
*/
getBlockTokenPairIndex(index: number): number;
/**
* Gets the location information for a position in the source.
*
* @param offset - The character offset in the source.
* @returns The location information.
*/
getLocation(offset: number): CssLocation;
/**
* Gets the location range information for a range in the source.
*
* @param start - The starting offset.
* @param end - The ending offset.
* @returns The location range information.
*/
getRangeLocation(start: number, end: number): CssLocationRange;
}
/**
* A function used to tokenize CSS source code.
*
* @param css - The CSS source code to tokenize.
* @param onToken - The callback function to be called for each token found in the source code.
*/
export type TokenizeFunction = (css: string, onToken: CssTokenizerCallback) => void;
/**
* Tokenizes a CSS source code string.
*
* @param css - The CSS source code to tokenize.
* @param onToken - The callback function to be called for each token found in the source code.
*/
export const tokenize: TokenizeFunction;
export interface TokenStreamDumpEntry {
idx: number;
type: string;
chunk: string;
balance: number;
}
export type TokenStreamDump = TokenStreamDumpEntry[];
export type TokenStreamIteratorFunction = (token: number, start: number, end: number, index: number) => void;
export type TokenStreamConsumeStopFunction = (charCode: number) => number;
/**
* This class represents a stream of tokens generated from a CSS string.
*/
export class TokenStream {
/**
* The original CSS source string.
*/
readonly source: string;
/**
* The offset of the first character in the source string (usually 0).
*/
readonly firstCharOffset: number;
/**
* A boolean flag indicating whether the end of the stream has been reached.
*/
readonly eof: boolean;
/**
* The total number of tokens in the stream.
*/
readonly tokenCount: number;
/**
* The index of the current token in the stream (starts at -1 before `next()` is called).
*/
readonly tokenIndex: number;
/**
* The numeric type of the current token.
*/
readonly tokenType: number;
/**
* The starting index of the current token in the source string.
*/
readonly tokenStart: number;
/**
* The ending index (exclusive) of the current token in the source string.
*/
readonly tokenEnd: number;
/**
* An internal buffer used for managing balance between opening and closing tokens.
*/
readonly balance: Uint32Array;
/**
* An internal buffer used for storing token information, including type and offset.
* The 32-bit integer at each index contains two pieces of information:
* - The starting index (inclusive) of the token within the source string is stored in the lower 24 bits of the 32-bit integer.
* - The numeric type of the token is stored in the upper 8 bits of the 32-bit integer.
*/
readonly offsetAndType: Uint32Array;
/**
* Creates a new token stream from a CSS source string.
*
* @param source - The CSS source code to tokenize.
* @param tokenize - The tokenizer function to use.
*/
constructor(source: string, tokenize: TokenizeFunction);
/**
* Resets the stream to its initial state (all properties set to their default values).
*/
reset(): void;
/**
* Sets a new source string and optionally a new tokenize function for the stream.
*
* @param source - The new CSS source code to tokenize.
* @param tokenize - The new tokenizer function to use.
*/
setSource(source?: string, tokenize?: TokenizeFunction): void;
/**
* Returns the numeric type of the token at a specific offset (relative to the current position).
*
* @param offset - The offset of the token to look up.
* @returns The numeric type of the token at the specified offset.
*/
lookupType(offset: number): number;
/**
* Returns the numeric type of the idx-th non-whitespace/comment token in the TokenStream. This method skips whitespace and comment tokens until it finds the specified non-whitespace/comment token.
*
* @param index - The index of the non-whitespace/comment token to look up (starting from 0).
* @returns The numeric type of the idx-th non-whitespace/comment token, or EOF if the index is out of bounds or if the end of the stream is reached before the specified token is found.
*/
lookupTypeNonSC(index: number): number;
/**
* Returns the starting index (inclusive) of the token at a specific offset (relative to the current position) within the TokenStream.
*
* @param offset - The offset from the current token's starting index. A positive offset indicates a position later in the stream, while a negative offset indicates a position earlier in the stream.
* @returns The starting index of the token at the specified offset, or the length of the source string if the offset is out of bounds.
*/
lookupOffset(offset: number): number;
/**
* Returns the starting index (inclusive) of the `idx`-th non-whitespace/comment token in the `TokenStream`. This method skips whitespace and comment tokens until it finds the specified non-whitespace/comment token.
*
* @param index - The index of the non-whitespace/comment token to look up (starting from 0).
* @returns The starting index of the `idx`-th non-whitespace/comment token, or `EOF` if the index is out of bounds or if the end of the stream is reached before the specified token is found.
*/
lookupOffsetNonSC(index: number): number;
/**
* Compares the value of the token at a specific offset with a given reference string and returns true if they match.
*
* @param offset - The offset from the current token's starting index. A positive offset indicates a position later in the stream, while a negative offset indicates a position earlier in the stream.
* @param referenceStr - The reference string to compare with the token value.
* @returns True if the token value matches the reference string, false otherwise.
*/
lookupValue(offset: number, referenceStr: string): boolean;
/**
* Returns the starting index (inclusive) of the token at a specific index in the `TokenStream`.
*
* @param tokenIndex - The index of the token to look up (starting from 0).
* @returns The starting index of the token at the specified index, or `EOF` if the index is out of bounds.
*/
getTokenStart(tokenIndex: number): number;
/**
* Returns the substring of the source string from the specified starting index to the current token's starting index.
*
* @param start The starting index of the substring.
* @returns The extracted substring.
*/
substrToCursor(start: number): string;
/**
* Checks if the current position is at the edge of a balanced block (e.g., before an opening parenthesis).
*
* @param pos - The position to check.
* @returns True if the position is at a balance edge, false otherwise.
*/
isBalanceEdge(pos: number): boolean;
/**
* Checks if the current token (or the token at a specific offset) is a delimiter with a specific character code.
*
* @param code - The character code to check for.
* @param offset - The offset from the current token's starting index (optional). If provided, the function checks the token at the specified offset instead of the current token.
* @returns True if the token is a delimiter with the specified character code, false otherwise.
*/
isDelim(code: number, offset?: number): boolean;
/**
* Skips a specified number of tokens forward in the stream.
*
* @param tokenCount - The number of tokens to skip.
*/
skip(tokenCount: number): void;
/**
* Moves the stream forward to the next token.
*/
next(): void;
/**
* Skips any whitespace or comment tokens until encountering a non-whitespace/comment token.
*/
skipSC(): void;
/**
* Skips tokens until a balanced block is reached, optionally stopping at a specified condition.
*
* @param startToken - The index of the starting token of the balanced block.
* @param stopConsume - A function that determines whether to stop skipping tokens. It should take a character code as input and return:
* - 1: Stop skipping immediately.
* - 2: Stop skipping and include the current token.
* - 0: Continue skipping.
*/
skipUntilBalanced(startToken: number, stopConsume: TokenStreamConsumeStopFunction): void;
/**
* Iterates over each token in the stream and calls the provided function for each token.
*
* @param fn - The function to be called for each token. It should take the following arguments:
* - token: The numeric type of the token.
* - start: The starting index of the token in the source string.
* - end: The ending index (exclusive) of the token in the source string.
* - index: The index of the token in the stream.
*/
forEachToken(fn: TokenStreamIteratorFunction): void;
/**
* Dumps the token stream data.
*
* @returns An array of token stream entries.
*/
dump(): TokenStreamDump;
}
/**
* A class that maps offsets within a source string to their corresponding line and column numbers.
*/
export class OffsetToLocation {
/**
* Sets the source string and optionally the starting offset, line, and column.
*
* @param source - The source string.
* @param startOffset The offset of the first character in the source string (default: 0).
* @param startLine - The line number of the first character in the source string (default: 1).
* @param startColumn - The column number of the first character in the source string (default: 1).
*/
setSource(source: string, startOffset?: number, startLine?: number, startColumn?: number): void;
/**
* Gets the line and column numbers for a given offset within the source string.
*
* @param offset - The offset within the source string.
* @param filename - The filename associated with the source string (optional).
* @returns A {@link CssLocation} object containing the line and column numbers.
*/
getLocation(offset: number, filename?: string): CssLocation;
/**
* Gets the line and column numbers for a range of offsets within the source string.
*
* @param start - The starting offset within the source string.
* @param end - The ending offset within the source string (exclusive).
* @param filename - The filename associated with the source string (optional).
* @returns A {@link CssLocationRange} object containing the line and column numbers for the start and end positions.
*/
getLocationRange(start: number, end: number, filename?: string): CssLocationRange;
}
// ----------------------------------------------------------
// Parser
// https://github.com/csstree/csstree/tree/master/lib/parser
// ----------------------------------------------------------
/**
* Represents an error that occurs during CSS parsing. Extends the standard `SyntaxError`
* to include additional details about the parsing error.
*/
/**
* Represents a syntax error while parsing CSS code. In the actual code,
* this is called `SyntaxError`, but that clashes with the global `SyntaxError` class.
* This isn't exported separately but rather as a member of the `parse` function.
*/
export interface SyntaxParseError extends SyntaxError {
/**
* The source code where the error occurred.
*/
source: string;
/**
* The character offset in the source code where the error occurred.
*/
offset: number;
/**
* The line number (1-indexed) in the source code where the error occurred.
*/
line: number;
/**
* The column number (1-indexed) in the source code where the error occurred.
*/
column: number;
/**
* The source code fragment around the error, including a specified number of extra lines.
* @param extraLines The number of extra lines to include in the fragment.
* @return A string containing the source code fragment around the error.
* This fragment includes the error line and the specified number of lines before and after it.
*/
sourceFragment(extraLines: number): string;
/**
* The error message formatted with the source fragment.
*/
readonly formattedMessage: string;
}
/**
* A callback function invoked when a comment is encountered during parsing.
*
* @param value - The content of the comment.
* @param loc - The location range of the comment in the source input.
*/
export type OnParseCommentCallback = (value: string, loc: CssLocationRange) => void;
/**
* A callback function invoked when a parsing error occurs.
*
* @param error - The parsing error details as a `SyntaxParseError`.
* @param fallbackNode - A fallback `CssNode` that can be used in place of the invalid input.
*/
export type OnParseErrorCallback = (error: SyntaxParseError, fallbackNode: CssNode) => void;
/**
* A callback function invoked for each token encountered during parsing.
*
* @param token - The numeric type of the token.
* @param start - The starting index of the token in the source string.
* @param end - The ending index (exclusive) of the token in the source string.
* @param index - The index of the token in the stream.
*/
export type OnTokenCallback = (this: TokenIterateAPI, token: number, start: number, end: number, index: number) => void;
/**
* Options for controlling the behavior of the CSS parser.
*/
export interface ParseOptions {
/**
* The parsing context (e.g., "stylesheet", "value").
*/
context?: string | undefined;
/**
* The at-rule name for parsing its prelude.
*/
atrule?: string | undefined;
/**
* Whether to include position information in the parsed nodes.
*/
positions?: boolean | undefined;
/**
* A callback function invoked for each comment encountered during parsing.
*/
onComment?: OnParseCommentCallback;
/**
* A callback function invoked for handling parsing errors.
*/
onParseError?: OnParseErrorCallback;
/**
* A callback function invoked for each token encountered during parsing.
*/
onToken?: OnTokenCallback;
/**
* The name of the file being parsed, used for error reporting.
*/
filename?: string | undefined;
/**
* The character offset to start parsing from in the input string.
*/
offset?: number | undefined;
/**
* The line number to start parsing from in the input string.
*/
line?: number | undefined;
/**
* The column number to start parsing from in the input string.
*/
column?: number | undefined;
/**
* Whether to parse the prelude of at-rules.
*/
parseAtrulePrelude?: boolean | undefined;
/**
* Whether to parse the prelude of rules.
*/
parseRulePrelude?: boolean | undefined;
/**
* Whether to parse CSS values.
*/
parseValue?: boolean | undefined;
/**
* Whether to parse custom property values.
*/
parseCustomProperty?: boolean | undefined;
}
/**
* Creates a new instance of a parse error.
* @param message The error message describing the syntax error.
* @param source The source code where the error occurred.
* @param offset The character offset in the source code where the error occurred.
* @param line The line number (1-indexed) in the source code where the error occurred.
* @param column The column number (1-indexed) in the source code where the error occurred.
* @param baseLine The base line number (1-indexed) for the error, used for relative positioning.
* @param baseColumn The base column number (1-indexed) for the error, used for relative positioning.
*/
export type SyntaxErrorCreator = (message: string, source: string, offset: number, line: number, column: number, baseLine?: number, baseColumn?: number) => SyntaxParseError;
/**
* A function that parses a CSS string into an abstract syntax tree (AST).
*/
export interface ParseFunction {
/**
* Parses a CSS source string into an abstract syntax tree (AST).
* @param source - The CSS source string to parse.
* @param options - Optional configuration for the parser.
* @returns The parsed CSS as a `CssNode`.
* @throws {CSSSyntaxError} If a parsing error occurs, this error will be thrown.
*/
(source: string, options?: ParseOptions): CssNode;
/**
* The error class used for parsing errors.
*/
SyntaxError: SyntaxErro