@stackpress/idea-parser
Version:
Parses ideas to AST and readable JSON.
79 lines (78 loc) • 2.58 kB
JavaScript
import Exception from '../Exception.js';
import AbstractTree from './AbstractTree.js';
import EnumTree from './EnumTree.js';
import PropTree from './PropTree.js';
import TypeTree from './TypeTree.js';
import ModelTree from './ModelTree.js';
import PluginTree from './PluginTree.js';
import UseTree from './UseTree.js';
export default class SchemaTree extends AbstractTree {
static definitions(lexer) {
EnumTree.definitions(lexer);
PropTree.definitions(lexer);
TypeTree.definitions(lexer);
ModelTree.definitions(lexer);
PluginTree.definitions(lexer);
UseTree.definitions(lexer);
return lexer;
}
static parse(code) {
return new this().parse(code);
}
_enumTree;
_propTree;
_typeTree;
_modelTree;
_pluginTree;
_useTree;
constructor(lexer) {
super(lexer);
this._enumTree = new EnumTree(this._lexer);
this._propTree = new PropTree(this._lexer);
this._typeTree = new TypeTree(this._lexer);
this._modelTree = new ModelTree(this._lexer);
this._pluginTree = new PluginTree(this._lexer);
this._useTree = new UseTree(this._lexer);
}
parse(code, start = 0) {
this._lexer.load(code, start);
this.noncode();
const body = [];
for (const token of this.dotryall(() => this._enumTree.enum(), () => this._propTree.prop(), () => this._typeTree.type(), () => this._modelTree.model(), () => this._pluginTree.plugin(), () => this._useTree.use())) {
body.push(token);
this.noncode();
}
if (this._lexer.index < code.length) {
const remainder = code.substring(this._lexer.index, this._lexer.nextSpace()).trim();
if (remainder.length) {
throw Exception
.for(`Unexpected token %s`, remainder.replace(/[\n\r]/g, ' ').trim())
.withPosition(this._lexer.index, this._lexer.nextSpace());
}
}
return {
type: 'Program',
kind: 'schema',
start: 0,
end: this._lexer.index,
body
};
}
*dotryall(...all) {
let token;
do {
token = undefined;
for (const callback of all) {
try {
token = callback();
if (token) {
yield token;
break;
}
}
catch (error) { }
}
} while (token);
}
}
;