UNPKG

langium-cli

Version:

CLI for Langium - the language engineering tool

74 lines 3.33 kB
/****************************************************************************** * Copyright 2023 TypeFox GmbH * This program and the accompanying materials are made available under the * terms of the MIT License, which is available in the project root. ******************************************************************************/ import { GrammarAST, GrammarUtils, RegExpUtils } from 'langium'; import { expandToNode, joinToNode, toString } from 'langium/generate'; import { collectKeywords } from '../langium-util.js'; const idRegex = /^[a-zA-Z_]+$/; export function generatePrismHighlighting(grammar, config) { const highlighter = {}; const keywords = collectKeywords(grammar); const terminals = getTerminals(grammar); const modifier = config.caseInsensitive ? 'i' : ''; const commentTerminals = terminals.filter(GrammarUtils.isCommentTerminal); if (commentTerminals.length === 1) { highlighter.comment = { pattern: GrammarUtils.terminalRegex(commentTerminals[0]).toString(), greedy: true }; } else if (commentTerminals.length > 0) { highlighter.comment = commentTerminals.map(e => ({ pattern: GrammarUtils.terminalRegex(e).toString(), greedy: true })); } const stringTerminal = terminals.find(e => e.name.toLowerCase() === 'string'); if (stringTerminal) { highlighter.string = { pattern: GrammarUtils.terminalRegex(stringTerminal).toString(), greedy: true }; } const filteredKeywords = keywords.filter(e => idRegex.test(e)).sort((a, b) => b.length - a.length).map(RegExpUtils.escapeRegExp); highlighter.keyword = { pattern: `/\\b(${filteredKeywords.join('|')})\\b/${modifier}` }; return generate(highlighter, config.id); } function generate(highlighter, languageId) { return toString(expandToNode ` // This file is generated using a best effort guess for your language. // It is not guaranteed contain all expected prism syntax highlighting rules. // For more documentation, take a look at https://prismjs.com/extending.html' Prism.languages["${languageId}"] = { ${joinToNode(Object.entries(highlighter), ([name, value]) => { const propertyName = !idRegex.test(name) ? `"${name}"` : name; return Array.isArray(value) ? expandToNode ` ${propertyName}: [ ${joinToNode(value, generateElement, { separator: ',', appendNewLineIfNotEmpty: true })} ] ` : expandToNode ` ${propertyName}: ${generateElement(value)} `; }, { separator: ',', appendNewLineIfNotEmpty: true })} }; `.appendNewLine()); } function generateElement(element) { const props = [ `pattern: ${element.pattern}`, element.greedy ? 'greedy: true' : undefined ].filter(Boolean); return expandToNode ` { ${joinToNode(props, { separator: ',', appendNewLineIfNotEmpty: true })} } `; } function getTerminals(grammar) { return grammar.rules.filter(GrammarAST.isTerminalRule); } //# sourceMappingURL=prism-generator.js.map