ima-parse
Version:
Easy Simple Parser, that only requires a Grammar JSON to output an AST.
96 lines (95 loc) • 2.91 kB
TypeScript
import { CharCode } from "../helpers/charCodeHelpers";
type DefinitionPartBase = {
type: string;
key?: string;
description?: string;
optional?: boolean;
};
/**
* Basically // comments and "texts"
*/
export type DefinitionText = DefinitionPartBase & {
type: "text";
key: string;
startPhrase?: string;
endPhrase: string;
excludeEndPhrase?: boolean;
};
/**
* Modifiers where the order doesn't matter. If the order matters, use separate definitions.
*/
export type DefinitionModifiers = DefinitionPartBase & {
type: "modifiers";
phrases: string[];
singular?: boolean;
key?: never;
};
/**
* Alternative paths that can only contain simple definition parts. This is to allow more flexibility but still restrict the complexity.
* The parts of all the paths will be added to the typings of the containing rule with optionality.
*/
export type DefinitionPaths = DefinitionPartBase & {
type: "paths";
paths: SimpleDefinitionPart[][];
key?: never;
};
/**
* A required keyword/character that provides structure to the rule that's being defined.
* Optional? No, always required.
*/
export type DefinitionKeyword = DefinitionPartBase & {
type: "keyword";
phrase: string;
optional?: false;
key?: never;
};
/**
* A number definition. Need other types of characters in front or behind? Use paths and/or modifiers.
* Optional? No, always required.
*/
export type DefinitionNumber = DefinitionPartBase & {
type: "number";
key: string;
optional?: false;
};
/**
* Identifier that can be a word that contains letters, numbers and underscores.
* Optional? No, always required.
*/
export type DefinitionIdentifier = DefinitionPartBase & {
type: "identifier";
key: string;
optional?: false;
};
/**
* Rules that always are a child of another rule.
*/
export type DefinitionRules = DefinitionPartBase & {
type: "rules";
key: string;
rules: GrammarRule[] | (() => GrammarRule[]);
optional: boolean;
/** Only allow one of the rules once */
singular?: boolean;
/** Phrase that separates the rules */
separatorPhrase?: string;
separatorOptional?: boolean;
};
export type SimpleDefinitionPart = DefinitionIdentifier | DefinitionModifiers | DefinitionKeyword | DefinitionText | DefinitionNumber;
export type DefinitionPart = SimpleDefinitionPart | DefinitionRules | DefinitionPaths;
/**
* Define a 'rule' that can be referred to from other rules (where you allow it). Make sure that the definition parts within are
* NON-ambiguous! All array definitions are parsed in order, so take that into account when defining.
*/
export type GrammarRule = {
name: string;
definition: DefinitionPart[];
};
export type Grammar = {
TopLevel: GrammarRule;
global: DefinitionRules;
wordChars?: CharCode[];
numberChars?: CharCode[];
validChars?: CharCode[];
};
export {};