@rohal12/spindle-lsp 0.4.0 → 0.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bin.js +396 -40
- package/dist/bin.js.map +4 -4
- package/package.json +4 -1
package/dist/bin.js
CHANGED
|
@@ -1011,6 +1011,12 @@ var init_macro_supplements = __esm({
|
|
|
1011
1011
|
name: "unwatch",
|
|
1012
1012
|
description: "Stops watching a variable.\n\nUsage: `{unwatch $var}`",
|
|
1013
1013
|
parameters: ["...text"]
|
|
1014
|
+
},
|
|
1015
|
+
unless: {
|
|
1016
|
+
name: "unless",
|
|
1017
|
+
container: true,
|
|
1018
|
+
description: "Conditionally displays its contents when the expression is falsy. The inverse of `{if}`.\n\nUsage:\n\n```\n{unless condition}\n ...\n{/unless}\n```",
|
|
1019
|
+
parameters: ["...text"]
|
|
1014
1020
|
}
|
|
1015
1021
|
};
|
|
1016
1022
|
}
|
|
@@ -2787,51 +2793,392 @@ var init_check = __esm({
|
|
|
2787
2793
|
}
|
|
2788
2794
|
});
|
|
2789
2795
|
|
|
2790
|
-
// src/plugins/format.ts
|
|
2791
|
-
function
|
|
2796
|
+
// src/plugins/format/segment.ts
|
|
2797
|
+
function splitPassages(text) {
|
|
2792
2798
|
const lines = text.split("\n");
|
|
2793
|
-
|
|
2794
|
-
|
|
2799
|
+
if (lines.length > 0 && lines[lines.length - 1] === "") {
|
|
2800
|
+
lines.pop();
|
|
2801
|
+
}
|
|
2802
|
+
const passages = [];
|
|
2803
|
+
let currentHeader = "";
|
|
2804
|
+
let bodyLines = [];
|
|
2805
|
+
let startLine = 0;
|
|
2806
|
+
function pushPassage() {
|
|
2807
|
+
if (currentHeader || bodyLines.length > 0) {
|
|
2808
|
+
while (bodyLines.length > 0 && bodyLines[bodyLines.length - 1].trim() === "") {
|
|
2809
|
+
bodyLines.pop();
|
|
2810
|
+
}
|
|
2811
|
+
passages.push({
|
|
2812
|
+
header: currentHeader,
|
|
2813
|
+
body: bodyLines.join("\n") + (bodyLines.length > 0 ? "\n" : ""),
|
|
2814
|
+
startLine
|
|
2815
|
+
});
|
|
2816
|
+
}
|
|
2817
|
+
}
|
|
2795
2818
|
for (let i = 0; i < lines.length; i++) {
|
|
2796
|
-
|
|
2797
|
-
|
|
2798
|
-
|
|
2799
|
-
|
|
2800
|
-
|
|
2801
|
-
|
|
2819
|
+
if (PASSAGE_HEADER_REGEX.test(lines[i])) {
|
|
2820
|
+
pushPassage();
|
|
2821
|
+
currentHeader = lines[i];
|
|
2822
|
+
bodyLines = [];
|
|
2823
|
+
startLine = i;
|
|
2824
|
+
} else {
|
|
2825
|
+
bodyLines.push(lines[i]);
|
|
2826
|
+
}
|
|
2827
|
+
}
|
|
2828
|
+
pushPassage();
|
|
2829
|
+
return passages;
|
|
2830
|
+
}
|
|
2831
|
+
function classifyPassage(header) {
|
|
2832
|
+
const tagMatch = header.match(/\[([^\]]*)\]/g);
|
|
2833
|
+
if (!tagMatch) return "normal";
|
|
2834
|
+
const tags = tagMatch.map((t) => t.slice(1, -1).trim().toLowerCase());
|
|
2835
|
+
if (tags.includes("script")) return "script";
|
|
2836
|
+
if (tags.includes("stylesheet")) return "stylesheet";
|
|
2837
|
+
return "normal";
|
|
2838
|
+
}
|
|
2839
|
+
function segmentRegions(body) {
|
|
2840
|
+
const lines = body.split("\n");
|
|
2841
|
+
if (lines.length > 0 && lines[lines.length - 1] === "") {
|
|
2842
|
+
lines.pop();
|
|
2843
|
+
}
|
|
2844
|
+
if (lines.length === 0) return [];
|
|
2845
|
+
const regions = [];
|
|
2846
|
+
let i = 0;
|
|
2847
|
+
while (i < lines.length) {
|
|
2848
|
+
const line = lines[i];
|
|
2849
|
+
const trimmed = line.trim();
|
|
2850
|
+
if (/^<script(\s|>)/i.test(trimmed)) {
|
|
2851
|
+
const scriptLines = [line];
|
|
2852
|
+
i++;
|
|
2853
|
+
while (i < lines.length && !/<\/script>/i.test(lines[i])) {
|
|
2854
|
+
scriptLines.push(lines[i]);
|
|
2855
|
+
i++;
|
|
2856
|
+
}
|
|
2857
|
+
if (i < lines.length) {
|
|
2858
|
+
scriptLines.push(lines[i]);
|
|
2859
|
+
i++;
|
|
2860
|
+
}
|
|
2861
|
+
regions.push({ type: "script", lines: scriptLines });
|
|
2862
|
+
continue;
|
|
2863
|
+
}
|
|
2864
|
+
if (/^<([a-zA-Z][\w-]*)/.test(trimmed)) {
|
|
2865
|
+
const tagMatch = trimmed.match(/^<([a-zA-Z][\w-]*)/);
|
|
2866
|
+
const tagName = tagMatch[1].toLowerCase();
|
|
2867
|
+
if (VOID_ELEMENTS.has(tagName) && !lines[i + 1]?.trim().startsWith("<")) {
|
|
2868
|
+
pushSpindleLine(regions, line);
|
|
2869
|
+
i++;
|
|
2870
|
+
continue;
|
|
2871
|
+
}
|
|
2872
|
+
const selfClosing = new RegExp(`</${tagName}\\s*>`, "i");
|
|
2873
|
+
if (selfClosing.test(trimmed)) {
|
|
2874
|
+
pushSpindleLine(regions, line);
|
|
2875
|
+
i++;
|
|
2876
|
+
continue;
|
|
2877
|
+
}
|
|
2878
|
+
const htmlLines = [line];
|
|
2879
|
+
let depth = 1;
|
|
2880
|
+
i++;
|
|
2881
|
+
while (i < lines.length && depth > 0) {
|
|
2882
|
+
htmlLines.push(lines[i]);
|
|
2883
|
+
const opens = (lines[i].match(new RegExp(`<${tagName}[\\s>]`, "gi")) ?? []).length;
|
|
2884
|
+
const closes = (lines[i].match(new RegExp(`</${tagName}\\s*>`, "gi")) ?? []).length;
|
|
2885
|
+
depth += opens - closes;
|
|
2886
|
+
i++;
|
|
2887
|
+
}
|
|
2888
|
+
regions.push({ type: "html", lines: htmlLines });
|
|
2889
|
+
continue;
|
|
2890
|
+
}
|
|
2891
|
+
pushSpindleLine(regions, line);
|
|
2892
|
+
i++;
|
|
2893
|
+
}
|
|
2894
|
+
return regions;
|
|
2895
|
+
}
|
|
2896
|
+
function pushSpindleLine(regions, line) {
|
|
2897
|
+
const last = regions[regions.length - 1];
|
|
2898
|
+
if (last?.type === "spindle") {
|
|
2899
|
+
last.lines.push(line);
|
|
2900
|
+
} else {
|
|
2901
|
+
regions.push({ type: "spindle", lines: [line] });
|
|
2902
|
+
}
|
|
2903
|
+
}
|
|
2904
|
+
var PASSAGE_HEADER_REGEX, VOID_ELEMENTS;
|
|
2905
|
+
var init_segment = __esm({
|
|
2906
|
+
"src/plugins/format/segment.ts"() {
|
|
2907
|
+
"use strict";
|
|
2908
|
+
PASSAGE_HEADER_REGEX = /^::\s+/;
|
|
2909
|
+
VOID_ELEMENTS = /* @__PURE__ */ new Set([
|
|
2910
|
+
"area",
|
|
2911
|
+
"base",
|
|
2912
|
+
"br",
|
|
2913
|
+
"col",
|
|
2914
|
+
"embed",
|
|
2915
|
+
"hr",
|
|
2916
|
+
"img",
|
|
2917
|
+
"input",
|
|
2918
|
+
"link",
|
|
2919
|
+
"meta",
|
|
2920
|
+
"param",
|
|
2921
|
+
"source",
|
|
2922
|
+
"track",
|
|
2923
|
+
"wbr"
|
|
2924
|
+
]);
|
|
2925
|
+
}
|
|
2926
|
+
});
|
|
2927
|
+
|
|
2928
|
+
// src/plugins/format/prettier-bridge.ts
|
|
2929
|
+
async function loadPrettier() {
|
|
2930
|
+
if (prettierLoaded) return prettier;
|
|
2931
|
+
prettierLoaded = true;
|
|
2932
|
+
try {
|
|
2933
|
+
prettier = await import("prettier");
|
|
2934
|
+
} catch {
|
|
2935
|
+
prettier = null;
|
|
2936
|
+
}
|
|
2937
|
+
return prettier;
|
|
2938
|
+
}
|
|
2939
|
+
async function getBaseConfig() {
|
|
2940
|
+
const p = await loadPrettier();
|
|
2941
|
+
if (!p) return {};
|
|
2942
|
+
try {
|
|
2943
|
+
const resolved = await p.resolveConfig(process.cwd());
|
|
2944
|
+
return { tabWidth: 2, ...resolved ?? {} };
|
|
2945
|
+
} catch {
|
|
2946
|
+
return { tabWidth: 2 };
|
|
2947
|
+
}
|
|
2948
|
+
}
|
|
2949
|
+
async function formatJS(code) {
|
|
2950
|
+
const p = await loadPrettier();
|
|
2951
|
+
if (!p) return code;
|
|
2952
|
+
try {
|
|
2953
|
+
const config = await getBaseConfig();
|
|
2954
|
+
return await p.format(code, { ...config, parser: "babel" });
|
|
2955
|
+
} catch {
|
|
2956
|
+
return code;
|
|
2957
|
+
}
|
|
2958
|
+
}
|
|
2959
|
+
async function formatCSS(code) {
|
|
2960
|
+
const p = await loadPrettier();
|
|
2961
|
+
if (!p) return code;
|
|
2962
|
+
try {
|
|
2963
|
+
const config = await getBaseConfig();
|
|
2964
|
+
return await p.format(code, { ...config, parser: "css" });
|
|
2965
|
+
} catch {
|
|
2966
|
+
return code;
|
|
2967
|
+
}
|
|
2968
|
+
}
|
|
2969
|
+
async function formatHTML(code) {
|
|
2970
|
+
const p = await loadPrettier();
|
|
2971
|
+
if (!p) return code;
|
|
2972
|
+
try {
|
|
2973
|
+
const config = await getBaseConfig();
|
|
2974
|
+
return await p.format(code, {
|
|
2975
|
+
...config,
|
|
2976
|
+
parser: "html",
|
|
2977
|
+
htmlWhitespaceSensitivity: "ignore"
|
|
2978
|
+
});
|
|
2979
|
+
} catch {
|
|
2980
|
+
return code;
|
|
2981
|
+
}
|
|
2982
|
+
}
|
|
2983
|
+
var prettier, prettierLoaded;
|
|
2984
|
+
var init_prettier_bridge = __esm({
|
|
2985
|
+
"src/plugins/format/prettier-bridge.ts"() {
|
|
2986
|
+
"use strict";
|
|
2987
|
+
prettier = null;
|
|
2988
|
+
prettierLoaded = false;
|
|
2989
|
+
}
|
|
2990
|
+
});
|
|
2991
|
+
|
|
2992
|
+
// src/plugins/format/placeholders.ts
|
|
2993
|
+
function isInsideAttribute(text, pos) {
|
|
2994
|
+
let inQuote = false;
|
|
2995
|
+
let quoteChar = "";
|
|
2996
|
+
for (let i = 0; i < pos; i++) {
|
|
2997
|
+
const ch = text[i];
|
|
2998
|
+
if (!inQuote && (ch === '"' || ch === "'") && i > 0 && text[i - 1] === "=") {
|
|
2999
|
+
inQuote = true;
|
|
3000
|
+
quoteChar = ch;
|
|
3001
|
+
} else if (inQuote && ch === quoteChar) {
|
|
3002
|
+
inQuote = false;
|
|
3003
|
+
}
|
|
3004
|
+
}
|
|
3005
|
+
return inQuote;
|
|
3006
|
+
}
|
|
3007
|
+
function replaceSpindleTokens(html) {
|
|
3008
|
+
const tokens = [];
|
|
3009
|
+
const lines = html.split("\n");
|
|
3010
|
+
const resultLines = [];
|
|
3011
|
+
for (const line of lines) {
|
|
3012
|
+
const trimmed = line.trim();
|
|
3013
|
+
SPINDLE_TOKEN_REGEX.lastIndex = 0;
|
|
3014
|
+
if (!SPINDLE_TOKEN_REGEX.test(trimmed)) {
|
|
3015
|
+
resultLines.push(line);
|
|
3016
|
+
continue;
|
|
3017
|
+
}
|
|
3018
|
+
SPINDLE_TOKEN_REGEX.lastIndex = 0;
|
|
3019
|
+
const withoutSpindle = trimmed.replace(SPINDLE_TOKEN_REGEX, "");
|
|
3020
|
+
const hasHtml = HTML_TAG_REGEX.test(withoutSpindle);
|
|
3021
|
+
if (!hasHtml) {
|
|
3022
|
+
const idx = tokens.length;
|
|
3023
|
+
tokens.push(trimmed);
|
|
3024
|
+
const indent = line.match(/^(\s*)/)?.[1] ?? "";
|
|
3025
|
+
resultLines.push(`${indent}<!--SP:${idx}-->`);
|
|
3026
|
+
} else {
|
|
3027
|
+
SPINDLE_TOKEN_REGEX.lastIndex = 0;
|
|
3028
|
+
const replaced = line.replace(SPINDLE_TOKEN_REGEX, (match, ...args2) => {
|
|
3029
|
+
const matchOffset = args2[args2.length - 2];
|
|
3030
|
+
const idx = tokens.length;
|
|
3031
|
+
tokens.push(match);
|
|
3032
|
+
if (isInsideAttribute(line, matchOffset)) {
|
|
3033
|
+
return `__SP${idx}__`;
|
|
3034
|
+
}
|
|
3035
|
+
return `<!--SP:${idx}-->`;
|
|
3036
|
+
});
|
|
3037
|
+
resultLines.push(replaced);
|
|
3038
|
+
}
|
|
3039
|
+
}
|
|
3040
|
+
return { text: resultLines.join("\n"), tokens };
|
|
3041
|
+
}
|
|
3042
|
+
function restoreSpindleTokens(text, tokens) {
|
|
3043
|
+
let result = text;
|
|
3044
|
+
for (let i = 0; i < tokens.length; i++) {
|
|
3045
|
+
result = result.replace(`<!--SP:${i}-->`, tokens[i]);
|
|
3046
|
+
result = result.replace(`__SP${i}__`, tokens[i]);
|
|
3047
|
+
}
|
|
3048
|
+
return result;
|
|
3049
|
+
}
|
|
3050
|
+
var SPINDLE_TOKEN_REGEX, HTML_TAG_REGEX;
|
|
3051
|
+
var init_placeholders = __esm({
|
|
3052
|
+
"src/plugins/format/placeholders.ts"() {
|
|
3053
|
+
"use strict";
|
|
3054
|
+
SPINDLE_TOKEN_REGEX = /(?:\{\/[A-Za-z][\w-]*\s*\}|\{(?:[#.][a-zA-Z][\w-]*\s*)*[A-Za-z][\w-]*(?:\s+(?:[^{}]|\{[^{}]*\})*)?\}|\{[$_@][a-zA-Z][\w.]*\}|\[\[(?:[^\]]*)\]\])/g;
|
|
3055
|
+
HTML_TAG_REGEX = /<\/?[a-zA-Z][\w-]*[\s>/]/;
|
|
3056
|
+
}
|
|
3057
|
+
});
|
|
3058
|
+
|
|
3059
|
+
// src/plugins/format.ts
|
|
3060
|
+
function getSupplementContainers() {
|
|
3061
|
+
const containers = /* @__PURE__ */ new Set();
|
|
3062
|
+
for (const [key, entry] of Object.entries(macro_supplements_default)) {
|
|
3063
|
+
if (entry.container) {
|
|
3064
|
+
containers.add(key.toLowerCase());
|
|
3065
|
+
}
|
|
3066
|
+
}
|
|
3067
|
+
return containers;
|
|
3068
|
+
}
|
|
3069
|
+
function detectContainersFromText(text) {
|
|
3070
|
+
const found = /* @__PURE__ */ new Set();
|
|
3071
|
+
const re = /\{\/([A-Za-z][\w-]*)\s*\}/g;
|
|
3072
|
+
let m;
|
|
3073
|
+
while ((m = re.exec(text)) !== null) {
|
|
3074
|
+
found.add(m[1].toLowerCase());
|
|
3075
|
+
}
|
|
3076
|
+
return found;
|
|
3077
|
+
}
|
|
3078
|
+
function buildDefaultIsBlock(text) {
|
|
3079
|
+
const containers = getSupplementContainers();
|
|
3080
|
+
for (const name of detectContainersFromText(text)) {
|
|
3081
|
+
containers.add(name);
|
|
3082
|
+
}
|
|
3083
|
+
return (name) => containers.has(name.toLowerCase());
|
|
3084
|
+
}
|
|
3085
|
+
async function formatDocument(text, options) {
|
|
3086
|
+
const isBlock = options?.isBlock ?? buildDefaultIsBlock(text);
|
|
3087
|
+
const isDedenting = options?.isDedentingSubMacro ?? ((name) => DEFAULT_DEDENTING.has(name.toLowerCase()));
|
|
3088
|
+
const passages = splitPassages(text);
|
|
3089
|
+
const resultLines = [];
|
|
3090
|
+
for (let pi = 0; pi < passages.length; pi++) {
|
|
3091
|
+
const passage = passages[pi];
|
|
3092
|
+
if (pi > 0 && passage.header) {
|
|
3093
|
+
const prev = passages[pi - 1];
|
|
3094
|
+
const prevBodyLineCount = prev.body ? prev.body.split("\n").length - 1 : 0;
|
|
3095
|
+
const prevEndLine = prev.startLine + (prev.header ? 1 : 0) + prevBodyLineCount;
|
|
3096
|
+
if (passage.startLine > prevEndLine) {
|
|
3097
|
+
resultLines.push("");
|
|
3098
|
+
}
|
|
3099
|
+
}
|
|
3100
|
+
if (passage.header) {
|
|
3101
|
+
const header = PASSAGE_HEADER_REGEX2.test(passage.header) ? normalizePassageHeader(passage.header) : passage.header;
|
|
3102
|
+
resultLines.push(header);
|
|
3103
|
+
}
|
|
3104
|
+
const kind = classifyPassage(passage.header);
|
|
3105
|
+
if (kind === "script") {
|
|
3106
|
+
const formatted = await formatJS(passage.body.trim());
|
|
3107
|
+
resultLines.push(formatted.trim());
|
|
3108
|
+
continue;
|
|
3109
|
+
}
|
|
3110
|
+
if (kind === "stylesheet") {
|
|
3111
|
+
const formatted = await formatCSS(passage.body.trim());
|
|
3112
|
+
resultLines.push(formatted.trim());
|
|
2802
3113
|
continue;
|
|
2803
3114
|
}
|
|
3115
|
+
const regions = segmentRegions(passage.body);
|
|
3116
|
+
for (const region of regions) {
|
|
3117
|
+
if (region.type === "script") {
|
|
3118
|
+
const firstLine = region.lines[0];
|
|
3119
|
+
const lastLine = region.lines[region.lines.length - 1];
|
|
3120
|
+
const innerLines = region.lines.slice(1, region.lines.length - 1);
|
|
3121
|
+
const innerCode = innerLines.join("\n");
|
|
3122
|
+
const formatted = await formatJS(innerCode.trim());
|
|
3123
|
+
resultLines.push(firstLine);
|
|
3124
|
+
if (formatted.trim()) {
|
|
3125
|
+
for (const fLine of formatted.trim().split("\n")) {
|
|
3126
|
+
resultLines.push(" " + fLine);
|
|
3127
|
+
}
|
|
3128
|
+
}
|
|
3129
|
+
resultLines.push(lastLine);
|
|
3130
|
+
continue;
|
|
3131
|
+
}
|
|
3132
|
+
if (region.type === "html") {
|
|
3133
|
+
const htmlText = region.lines.join("\n");
|
|
3134
|
+
const { text: placeholdered, tokens } = replaceSpindleTokens(htmlText);
|
|
3135
|
+
const formatted = await formatHTML(placeholdered);
|
|
3136
|
+
const restored = restoreSpindleTokens(formatted.trim(), tokens);
|
|
3137
|
+
for (const fLine of restored.split("\n")) {
|
|
3138
|
+
resultLines.push(fLine);
|
|
3139
|
+
}
|
|
3140
|
+
continue;
|
|
3141
|
+
}
|
|
3142
|
+
const indented = indentMacros(region.lines, isBlock, isDedenting);
|
|
3143
|
+
resultLines.push(...indented);
|
|
3144
|
+
}
|
|
3145
|
+
}
|
|
3146
|
+
let output = resultLines.map((l) => l.replace(/\s+$/, "")).join("\n");
|
|
3147
|
+
output = output.replace(/\n*$/, "\n");
|
|
3148
|
+
return output;
|
|
3149
|
+
}
|
|
3150
|
+
function indentMacros(lines, isBlock, isDedenting) {
|
|
3151
|
+
const result = [];
|
|
3152
|
+
let indentLevel = 0;
|
|
3153
|
+
for (const rawLine of lines) {
|
|
3154
|
+
const line = rawLine.replace(/\s+$/, "");
|
|
2804
3155
|
const trimmed = line.trim();
|
|
2805
3156
|
if (trimmed === "") {
|
|
2806
3157
|
result.push("");
|
|
2807
3158
|
continue;
|
|
2808
3159
|
}
|
|
2809
|
-
|
|
3160
|
+
const dedentMatch = trimmed.match(MACRO_OPEN_REGEX);
|
|
3161
|
+
if (dedentMatch && isDedenting(dedentMatch[1])) {
|
|
3162
|
+
indentLevel = Math.max(0, indentLevel - 1);
|
|
3163
|
+
result.push(indentLevel > 0 ? " ".repeat(indentLevel) + trimmed : trimmed);
|
|
3164
|
+
indentLevel++;
|
|
3165
|
+
continue;
|
|
3166
|
+
}
|
|
3167
|
+
const closeMatch = trimmed.match(MACRO_CLOSE_REGEX);
|
|
3168
|
+
if (closeMatch) {
|
|
2810
3169
|
indentLevel = Math.max(0, indentLevel - 1);
|
|
2811
3170
|
}
|
|
2812
|
-
|
|
2813
|
-
|
|
2814
|
-
if (
|
|
3171
|
+
result.push(indentLevel > 0 ? " ".repeat(indentLevel) + trimmed : trimmed);
|
|
3172
|
+
const openMatch = trimmed.match(MACRO_OPEN_REGEX);
|
|
3173
|
+
if (openMatch && isBlock(openMatch[1])) {
|
|
2815
3174
|
indentLevel++;
|
|
2816
3175
|
}
|
|
2817
3176
|
}
|
|
2818
|
-
let output = result.join("\n");
|
|
2819
|
-
output = output.replace(/\n*$/, "\n");
|
|
2820
|
-
return output;
|
|
2821
|
-
}
|
|
2822
|
-
function formatRange(text, range) {
|
|
2823
|
-
const lines = text.split("\n");
|
|
2824
|
-
const startLine = Math.max(0, range.start.line);
|
|
2825
|
-
const endLine = Math.min(lines.length - 1, range.end.line);
|
|
2826
|
-
const rangeLines = lines.slice(startLine, endLine + 1);
|
|
2827
|
-
const rangeText = rangeLines.join("\n");
|
|
2828
|
-
const formatted = formatDocument(rangeText);
|
|
2829
|
-
const formattedLines = formatted.replace(/\n$/, "").split("\n");
|
|
2830
|
-
const before = lines.slice(0, startLine);
|
|
2831
|
-
const after = lines.slice(endLine + 1);
|
|
2832
|
-
const result = [...before, ...formattedLines, ...after].join("\n");
|
|
2833
3177
|
return result;
|
|
2834
3178
|
}
|
|
3179
|
+
async function formatRange(text, _range, options) {
|
|
3180
|
+
return formatDocument(text, options);
|
|
3181
|
+
}
|
|
2835
3182
|
function normalizePassageHeader(line) {
|
|
2836
3183
|
const headerMatch = line.match(/^::\s+(.*)/);
|
|
2837
3184
|
if (!headerMatch) return line;
|
|
@@ -2851,13 +3198,18 @@ function normalizePassageHeader(line) {
|
|
|
2851
3198
|
}
|
|
2852
3199
|
return `:: ${name}${suffix}`;
|
|
2853
3200
|
}
|
|
2854
|
-
var
|
|
3201
|
+
var PASSAGE_HEADER_REGEX2, MACRO_OPEN_REGEX, MACRO_CLOSE_REGEX, DEFAULT_DEDENTING, formatPlugin;
|
|
2855
3202
|
var init_format = __esm({
|
|
2856
3203
|
"src/plugins/format.ts"() {
|
|
2857
3204
|
"use strict";
|
|
2858
|
-
|
|
2859
|
-
|
|
2860
|
-
|
|
3205
|
+
init_macro_supplements();
|
|
3206
|
+
init_segment();
|
|
3207
|
+
init_prettier_bridge();
|
|
3208
|
+
init_placeholders();
|
|
3209
|
+
PASSAGE_HEADER_REGEX2 = /^(::)\s+/;
|
|
3210
|
+
MACRO_OPEN_REGEX = /^\{(?:[#.][a-zA-Z][\w-]*\s*)*([A-Za-z][\w-]*)\b/;
|
|
3211
|
+
MACRO_CLOSE_REGEX = /^\{\/([A-Za-z][\w-]*)\b/;
|
|
3212
|
+
DEFAULT_DEDENTING = /* @__PURE__ */ new Set(["else", "elseif", "next", "case", "default"]);
|
|
2861
3213
|
formatPlugin = {
|
|
2862
3214
|
id: "format",
|
|
2863
3215
|
capabilities: {
|
|
@@ -2865,10 +3217,14 @@ var init_format = __esm({
|
|
|
2865
3217
|
documentRangeFormattingProvider: true
|
|
2866
3218
|
},
|
|
2867
3219
|
initialize(ctx) {
|
|
2868
|
-
|
|
3220
|
+
const formatOpts = {
|
|
3221
|
+
isBlock: (name) => ctx.workspace.macros.isBlock(name),
|
|
3222
|
+
isDedentingSubMacro: (name) => DEFAULT_DEDENTING.has(name.toLowerCase())
|
|
3223
|
+
};
|
|
3224
|
+
ctx.connection.onDocumentFormatting(async (params) => {
|
|
2869
3225
|
const text = ctx.workspace.documents.getText(params.textDocument.uri);
|
|
2870
3226
|
if (text === void 0) return [];
|
|
2871
|
-
const formatted = formatDocument(text);
|
|
3227
|
+
const formatted = await formatDocument(text, formatOpts);
|
|
2872
3228
|
if (formatted === text) return [];
|
|
2873
3229
|
const lines = text.split("\n");
|
|
2874
3230
|
return [{
|
|
@@ -2879,14 +3235,14 @@ var init_format = __esm({
|
|
|
2879
3235
|
newText: formatted
|
|
2880
3236
|
}];
|
|
2881
3237
|
});
|
|
2882
|
-
ctx.connection.onDocumentRangeFormatting((params) => {
|
|
3238
|
+
ctx.connection.onDocumentRangeFormatting(async (params) => {
|
|
2883
3239
|
const text = ctx.workspace.documents.getText(params.textDocument.uri);
|
|
2884
3240
|
if (text === void 0) return [];
|
|
2885
3241
|
const range = {
|
|
2886
3242
|
start: { line: params.range.start.line, character: params.range.start.character },
|
|
2887
3243
|
end: { line: params.range.end.line, character: params.range.end.character }
|
|
2888
3244
|
};
|
|
2889
|
-
const formatted = formatRange(text, range);
|
|
3245
|
+
const formatted = await formatRange(text, range, formatOpts);
|
|
2890
3246
|
if (formatted === text) return [];
|
|
2891
3247
|
const lines = text.split("\n");
|
|
2892
3248
|
return [{
|
|
@@ -2947,7 +3303,7 @@ async function runFormat(args2) {
|
|
|
2947
3303
|
for (const filePath of uniqueFiles) {
|
|
2948
3304
|
try {
|
|
2949
3305
|
const text = readFileSync5(filePath, "utf-8");
|
|
2950
|
-
const formatted = formatDocument(text);
|
|
3306
|
+
const formatted = await formatDocument(text);
|
|
2951
3307
|
if (formatted !== text) {
|
|
2952
3308
|
if (options.check) {
|
|
2953
3309
|
const relative = filePath.startsWith(cwd) ? filePath.slice(cwd.length + 1) : filePath;
|
|
@@ -3107,7 +3463,7 @@ async function startMcpServer() {
|
|
|
3107
3463
|
for (const filePath of files) {
|
|
3108
3464
|
try {
|
|
3109
3465
|
const text = readFileSync6(filePath, "utf-8");
|
|
3110
|
-
const result = formatDocument(text);
|
|
3466
|
+
const result = await formatDocument(text);
|
|
3111
3467
|
if (result !== text) {
|
|
3112
3468
|
writeFileSync2(filePath, result, "utf-8");
|
|
3113
3469
|
formatted++;
|
|
@@ -3139,7 +3495,7 @@ async function startMcpServer() {
|
|
|
3139
3495
|
for (const filePath of files) {
|
|
3140
3496
|
try {
|
|
3141
3497
|
const text = readFileSync6(filePath, "utf-8");
|
|
3142
|
-
const result = formatDocument(text);
|
|
3498
|
+
const result = await formatDocument(text);
|
|
3143
3499
|
const relativePath = filePath.startsWith(cwd) ? filePath.slice(cwd.length + 1) : filePath;
|
|
3144
3500
|
if (result !== text) {
|
|
3145
3501
|
needsFormatting.push(relativePath);
|