Formatter break document with single line comments
Closed this issue · 2 comments
ydaveluy commented
Hello,
When the formatter prepend/append oneSpace or noSpace on a token, it break the document if a single line is between the 2 tokens
Langium version: 3.1.0
Package name: langium-lsp
Steps To Reproduce
- Simple HelloWorld grammar
grammar HelloWorld
entry Model:
(persons+=Person | greetings+=Greeting)*;
Person:
'person' name=ID;
Greeting:
'Hello' person=[Person:ID] '!';
hidden terminal WS: /\s+/;
terminal ID: /[_a-zA-Z][\w_]*/;
hidden terminal ML_COMMENT: /\/\*[\s\S]*?\*\//;
hidden terminal SL_COMMENT: /\/\/[^\n\r]*/;
- one space between 'person' keyword and 'name' property
export class HelloFormatter extends AbstractFormatter {
protected format(node: AstNode): void {
if (ast.isPerson(node)) {
const formatter = this.getNodeFormatter(node);
formatter.property('name').prepend(Formatting.oneSpace())
}
}
}
- simple hello file with a single line comment between person and name
person //comment
John
The current behavior
After the formatting the name is moved at the end of the single line comment
person //commentJohn
The expected behavior
person //comment
John
ydaveluy commented
Here is a temporary workaround that works only if rule name is SL_COMMENT:
langium/packages/langium/src/lsp/formatter.ts
Line 230 in b2c40e3
Skip the prepend formatting if the lastNode rule is SL_COMMENT
if (!lastNode?.hidden || isLeafCstNode(lastNode) && lastNode.tokenType.name !== 'SL_COMMENT') {
const nodeEdits = this.createTextEdit(lastNode, node, prependFormatting, context);
for (const edit of nodeEdits) {
if (edit && this.insideRange(edit.range, range)) {
edits.push(edit);
}
}
}