Files
languageservices/actions-languageservice/src/utils/transform.ts
T
Christopher Schleiden 97d50f74af Clean up transform function
2023-01-10 16:05:50 -08:00

75 lines
2.2 KiB
TypeScript

import {Position, TextDocument} from "vscode-languageserver-textdocument";
import {Range} from "vscode-languageserver-types";
const PLACEHOLDER_KEY = "key";
// Transform a document to work around YAML parsing issues
// Based on `_transform` in https://github.com/cschleiden/github-actions-parser/blob/main/src/lib/parser/complete.ts#L311
export function transform(doc: TextDocument, pos: Position): [TextDocument, Position] {
let offset = doc.offsetAt(pos);
const lineRange: Range = {
start: {line: pos.line, character: 0},
end: {line: pos.line, character: Number.MAX_SAFE_INTEGER}
};
let line = doc.getText(lineRange);
// If the line includes a new-line char, strip that out
const newLinePos = line.indexOf("\n");
if (newLinePos >= 0) {
line = line.substring(0, newLinePos);
}
lineRange.end.character = line.length;
const linePos = pos.character;
// Special case for Actions, if this line contains an expression marker, do _not_ transform. This is
// an ugly fix for auto-completion in multi-line YAML strings. At this point in the process, we cannot
// determine if a line is in such a multi-line string.
if (line.indexOf("${{") !== -1) {
return [doc, pos];
}
const containsColon = line.indexOf(":") !== -1;
if (!containsColon) {
const trimmedLine = line.trim();
if (trimmedLine === "" || trimmedLine === "-") {
// Pos in sequence or empty line
let spacer = "";
if (trimmedLine === "-" && !line.endsWith(" ")) {
spacer = " ";
offset++;
}
line =
line.substring(0, linePos) +
spacer +
PLACEHOLDER_KEY +
(trimmedLine === "-" ? "" : ":") +
line.substring(linePos);
// Adjust pos by one to prevent a sequence node being marked as active
offset++;
} else if (!trimmedLine.startsWith("-")) {
// Add `:` to end of line
line = line + ":";
}
}
const newDoc = TextDocument.create(doc.uri, doc.languageId, doc.version, doc.getText());
TextDocument.update(
newDoc,
[
{
range: lineRange,
text: line
}
],
newDoc.version + 1
);
return [newDoc, newDoc.positionAt(offset)];
}