@spyglassmc/language-server 0.4.7 → 0.4.8
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/lib/server.js +34 -40
- package/lib/util/toLS.js +23 -53
- package/package.json +5 -5
package/lib/server.js
CHANGED
|
@@ -53,7 +53,7 @@ connection.onInitialize(async (params) => {
|
|
|
53
53
|
}
|
|
54
54
|
try {
|
|
55
55
|
service = new core.Service({
|
|
56
|
-
isDebugging: initializationOptions?.inDevelopmentMode
|
|
56
|
+
isDebugging: initializationOptions?.inDevelopmentMode,
|
|
57
57
|
logger,
|
|
58
58
|
profilers: new core.ProfilerFactory(logger, [
|
|
59
59
|
'cache#load',
|
|
@@ -69,20 +69,18 @@ connection.onInitialize(async (params) => {
|
|
|
69
69
|
projectRoot: core.fileUtil.ensureEndingSlash(workspaceFolders[0].uri),
|
|
70
70
|
},
|
|
71
71
|
});
|
|
72
|
-
service.project
|
|
73
|
-
.on('documentErrored', async ({ errors, uri, version }) => {
|
|
72
|
+
service.project.on('documentErrored', async ({ errors, uri, version }) => {
|
|
74
73
|
try {
|
|
75
74
|
await connection.sendDiagnostics({
|
|
76
75
|
diagnostics: toLS.diagnostics(errors),
|
|
77
|
-
uri
|
|
78
|
-
version
|
|
76
|
+
uri,
|
|
77
|
+
version,
|
|
79
78
|
});
|
|
80
79
|
}
|
|
81
80
|
catch (e) {
|
|
82
81
|
console.error('[sendDiagnostics]', e);
|
|
83
82
|
}
|
|
84
|
-
})
|
|
85
|
-
.on('ready', () => {
|
|
83
|
+
}).on('ready', () => {
|
|
86
84
|
progressReporter?.done();
|
|
87
85
|
});
|
|
88
86
|
await service.project.init();
|
|
@@ -96,24 +94,19 @@ connection.onInitialize(async (params) => {
|
|
|
96
94
|
showCacheRoot: true,
|
|
97
95
|
};
|
|
98
96
|
const ans = {
|
|
99
|
-
serverInfo: {
|
|
100
|
-
name: 'Spyglass Language Server',
|
|
101
|
-
},
|
|
97
|
+
serverInfo: { name: 'Spyglass Language Server' },
|
|
102
98
|
capabilities: {
|
|
103
99
|
colorProvider: {},
|
|
104
|
-
completionProvider: {
|
|
105
|
-
triggerCharacters: service.project.meta.getTriggerCharacters(),
|
|
106
|
-
},
|
|
100
|
+
completionProvider: { triggerCharacters: service.project.meta.getTriggerCharacters() },
|
|
107
101
|
declarationProvider: {},
|
|
108
102
|
definitionProvider: {},
|
|
109
103
|
implementationProvider: {},
|
|
110
|
-
|
|
104
|
+
// TODO: re-enable this
|
|
105
|
+
// documentFormattingProvider: {},
|
|
111
106
|
referencesProvider: {},
|
|
112
107
|
typeDefinitionProvider: {},
|
|
113
108
|
documentHighlightProvider: {},
|
|
114
|
-
documentSymbolProvider: {
|
|
115
|
-
label: 'Spyglass',
|
|
116
|
-
},
|
|
109
|
+
documentSymbolProvider: { label: 'Spyglass' },
|
|
117
110
|
hoverProvider: {},
|
|
118
111
|
inlayHintProvider: {},
|
|
119
112
|
semanticTokensProvider: {
|
|
@@ -122,25 +115,15 @@ connection.onInitialize(async (params) => {
|
|
|
122
115
|
full: { delta: false },
|
|
123
116
|
range: true,
|
|
124
117
|
},
|
|
125
|
-
signatureHelpProvider: {
|
|
126
|
-
|
|
127
|
-
},
|
|
128
|
-
textDocumentSync: {
|
|
129
|
-
change: ls.TextDocumentSyncKind.Incremental,
|
|
130
|
-
openClose: true,
|
|
131
|
-
},
|
|
118
|
+
signatureHelpProvider: { triggerCharacters: [' '] },
|
|
119
|
+
textDocumentSync: { change: ls.TextDocumentSyncKind.Incremental, openClose: true },
|
|
132
120
|
workspaceSymbolProvider: {},
|
|
133
|
-
experimental: {
|
|
134
|
-
spyglassmc: customCapabilities,
|
|
135
|
-
},
|
|
121
|
+
experimental: { spyglassmc: customCapabilities },
|
|
136
122
|
},
|
|
137
123
|
};
|
|
138
124
|
if (capabilities.workspace?.workspaceFolders) {
|
|
139
125
|
ans.capabilities.workspace = {
|
|
140
|
-
workspaceFolders: {
|
|
141
|
-
supported: true,
|
|
142
|
-
changeNotifications: true,
|
|
143
|
-
},
|
|
126
|
+
workspaceFolders: { supported: true, changeNotifications: true },
|
|
144
127
|
};
|
|
145
128
|
}
|
|
146
129
|
return ans;
|
|
@@ -190,8 +173,7 @@ connection.onCompletion(async ({ textDocument: { uri }, position, context }) =>
|
|
|
190
173
|
const { doc, node } = docAndNode;
|
|
191
174
|
const offset = toCore.offset(position, doc);
|
|
192
175
|
const items = service.complete(node, doc, offset, context?.triggerCharacter);
|
|
193
|
-
return items.map((item) => toLS.completionItem(item, doc, offset, capabilities.textDocument?.completion?.completionItem
|
|
194
|
-
?.insertReplaceSupport));
|
|
176
|
+
return items.map((item) => toLS.completionItem(item, doc, offset, capabilities.textDocument?.completion?.completionItem?.insertReplaceSupport));
|
|
195
177
|
});
|
|
196
178
|
connection.onRequest('spyglassmc/dataHackPubify', ({ initialism }) => {
|
|
197
179
|
return service.dataHackPubify(initialism);
|
|
@@ -202,7 +184,10 @@ connection.onDeclaration(async ({ textDocument: { uri }, position }) => {
|
|
|
202
184
|
return undefined;
|
|
203
185
|
}
|
|
204
186
|
const { doc, node } = docAndNode;
|
|
205
|
-
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
187
|
+
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
188
|
+
'declaration',
|
|
189
|
+
'definition',
|
|
190
|
+
]);
|
|
206
191
|
return toLS.locationLink(ans, doc, capabilities.textDocument?.declaration?.linkSupport);
|
|
207
192
|
});
|
|
208
193
|
connection.onDefinition(async ({ textDocument: { uri }, position }) => {
|
|
@@ -211,7 +196,12 @@ connection.onDefinition(async ({ textDocument: { uri }, position }) => {
|
|
|
211
196
|
return undefined;
|
|
212
197
|
}
|
|
213
198
|
const { doc, node } = docAndNode;
|
|
214
|
-
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
199
|
+
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
200
|
+
'definition',
|
|
201
|
+
'declaration',
|
|
202
|
+
'implementation',
|
|
203
|
+
'typeDefinition',
|
|
204
|
+
]);
|
|
215
205
|
return toLS.locationLink(ans, doc, capabilities.textDocument?.definition?.linkSupport);
|
|
216
206
|
});
|
|
217
207
|
connection.onImplementation(async ({ textDocument: { uri }, position }) => {
|
|
@@ -220,10 +210,13 @@ connection.onImplementation(async ({ textDocument: { uri }, position }) => {
|
|
|
220
210
|
return undefined;
|
|
221
211
|
}
|
|
222
212
|
const { doc, node } = docAndNode;
|
|
223
|
-
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
213
|
+
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
214
|
+
'implementation',
|
|
215
|
+
'definition',
|
|
216
|
+
]);
|
|
224
217
|
return toLS.locationLink(ans, doc, capabilities.textDocument?.implementation?.linkSupport);
|
|
225
218
|
});
|
|
226
|
-
connection.onReferences(async ({ textDocument: { uri }, position, context: { includeDeclaration }
|
|
219
|
+
connection.onReferences(async ({ textDocument: { uri }, position, context: { includeDeclaration } }) => {
|
|
227
220
|
const docAndNode = await service.project.ensureClientManagedChecked(uri);
|
|
228
221
|
if (!docAndNode) {
|
|
229
222
|
return undefined;
|
|
@@ -238,7 +231,9 @@ connection.onTypeDefinition(async ({ textDocument: { uri }, position }) => {
|
|
|
238
231
|
return undefined;
|
|
239
232
|
}
|
|
240
233
|
const { doc, node } = docAndNode;
|
|
241
|
-
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
234
|
+
const ans = await service.getSymbolLocations(node, doc, toCore.offset(position, doc), [
|
|
235
|
+
'typeDefinition',
|
|
236
|
+
]);
|
|
242
237
|
return toLS.locationLink(ans, doc, capabilities.textDocument?.typeDefinition?.linkSupport);
|
|
243
238
|
});
|
|
244
239
|
connection.onDocumentHighlight(async ({ textDocument: { uri }, position }) => {
|
|
@@ -256,8 +251,7 @@ connection.onDocumentSymbol(async ({ textDocument: { uri } }) => {
|
|
|
256
251
|
return undefined;
|
|
257
252
|
}
|
|
258
253
|
const { doc, node } = docAndNode;
|
|
259
|
-
return toLS.documentSymbolsFromTables([service.project.symbols.global, ...core.AstNode.getLocalsToLeaves(node)], doc, capabilities.textDocument?.documentSymbol
|
|
260
|
-
?.hierarchicalDocumentSymbolSupport, capabilities.textDocument?.documentSymbol?.symbolKind?.valueSet);
|
|
254
|
+
return toLS.documentSymbolsFromTables([service.project.symbols.global, ...core.AstNode.getLocalsToLeaves(node)], doc, capabilities.textDocument?.documentSymbol?.hierarchicalDocumentSymbolSupport, capabilities.textDocument?.documentSymbol?.symbolKind?.valueSet);
|
|
261
255
|
});
|
|
262
256
|
connection.onHover(async ({ textDocument: { uri }, position }) => {
|
|
263
257
|
const docAndNode = await service.project.ensureClientManagedChecked(uri);
|
package/lib/util/toLS.js
CHANGED
|
@@ -35,9 +35,7 @@ export function diagnostic(error) {
|
|
|
35
35
|
(ans.tags ??= [])?.push(ls.DiagnosticTag.Unnecessary);
|
|
36
36
|
}
|
|
37
37
|
if (error.info?.codeAction) {
|
|
38
|
-
ans.data = {
|
|
39
|
-
codeAction: error.info?.codeAction,
|
|
40
|
-
};
|
|
38
|
+
ans.data = { codeAction: error.info?.codeAction };
|
|
41
39
|
}
|
|
42
40
|
if (error.info?.related) {
|
|
43
41
|
ans.relatedInformation = error.info?.related.map((v) => ({
|
|
@@ -63,14 +61,12 @@ export function diagnosticSeverity(severity) {
|
|
|
63
61
|
}
|
|
64
62
|
}
|
|
65
63
|
export function documentHighlight(locations) {
|
|
66
|
-
return locations?.locations
|
|
67
|
-
|
|
68
|
-
|
|
64
|
+
return locations?.locations?.filter((loc) => loc.posRange)?.map((loc) => ({
|
|
65
|
+
range: loc.posRange,
|
|
66
|
+
}));
|
|
69
67
|
}
|
|
70
68
|
export function documentSelector(meta) {
|
|
71
|
-
const ans = meta
|
|
72
|
-
.getLanguages()
|
|
73
|
-
.map((id) => ({ language: id }));
|
|
69
|
+
const ans = meta.getLanguages().map((id) => ({ language: id }));
|
|
74
70
|
return ans;
|
|
75
71
|
}
|
|
76
72
|
export function documentSymbol(symbol, symLoc, doc, hierarchicalSupport, supportedKinds = []) {
|
|
@@ -85,8 +81,7 @@ export function documentSymbol(symbol, symLoc, doc, hierarchicalSupport, support
|
|
|
85
81
|
};
|
|
86
82
|
}
|
|
87
83
|
export function documentSymbols(map = {}, doc, hierarchicalSupport, supportedKinds = []) {
|
|
88
|
-
return Object.values(map)
|
|
89
|
-
.map((s) => [
|
|
84
|
+
return Object.values(map).map((s) => [
|
|
90
85
|
s,
|
|
91
86
|
[
|
|
92
87
|
...(s.declaration ?? []),
|
|
@@ -94,25 +89,17 @@ export function documentSymbols(map = {}, doc, hierarchicalSupport, supportedKin
|
|
|
94
89
|
...(s.implementation ?? []),
|
|
95
90
|
...(s.typeDefinition ?? []),
|
|
96
91
|
].find((l) => l.uri === doc.uri),
|
|
97
|
-
])
|
|
98
|
-
.filter(([_s, l]) => !!l)
|
|
99
|
-
.map(([s, l]) => documentSymbol(s, l, doc, hierarchicalSupport, supportedKinds));
|
|
92
|
+
]).filter(([_s, l]) => !!l).map(([s, l]) => documentSymbol(s, l, doc, hierarchicalSupport, supportedKinds));
|
|
100
93
|
}
|
|
101
94
|
export function documentSymbolsFromTable(table, doc, hierarchicalSupport, supportedKinds = []) {
|
|
102
|
-
return Object.values(table)
|
|
103
|
-
.map((m) => documentSymbols(m, doc, hierarchicalSupport, supportedKinds))
|
|
104
|
-
.flat();
|
|
95
|
+
return Object.values(table).map((m) => documentSymbols(m, doc, hierarchicalSupport, supportedKinds)).flat();
|
|
105
96
|
}
|
|
106
97
|
export function documentSymbolsFromTables(tables, doc, hierarchicalSupport, supportedKinds = []) {
|
|
107
|
-
return tables
|
|
108
|
-
.map((t) => documentSymbolsFromTable(t, doc, hierarchicalSupport, supportedKinds))
|
|
98
|
+
return tables.map((t) => documentSymbolsFromTable(t, doc, hierarchicalSupport, supportedKinds))
|
|
109
99
|
.flat();
|
|
110
100
|
}
|
|
111
101
|
export function hover(hover, doc) {
|
|
112
|
-
const ans = {
|
|
113
|
-
contents: markupContent(hover.markdown),
|
|
114
|
-
range: range(hover.range, doc),
|
|
115
|
-
};
|
|
102
|
+
const ans = { contents: markupContent(hover.markdown), range: range(hover.range, doc) };
|
|
116
103
|
return ans;
|
|
117
104
|
}
|
|
118
105
|
export function inlayHint(hint, doc) {
|
|
@@ -128,8 +115,8 @@ export function inlayHints(hints, doc) {
|
|
|
128
115
|
}
|
|
129
116
|
export function completionItem(completion, doc, requestedOffset, insertReplaceSupport) {
|
|
130
117
|
const insertText = completion.insertText ?? completion.label;
|
|
131
|
-
const canInsertReplace = insertReplaceSupport
|
|
132
|
-
![core.CR, core.LF, core.CRLF].includes(insertText);
|
|
118
|
+
const canInsertReplace = insertReplaceSupport
|
|
119
|
+
&& ![core.CR, core.LF, core.CRLF].includes(insertText);
|
|
133
120
|
const textEdit = canInsertReplace
|
|
134
121
|
? ls.InsertReplaceEdit.create(insertText,
|
|
135
122
|
/* insert */ range(core.Range.create(completion.range.start, requestedOffset), doc),
|
|
@@ -145,17 +132,12 @@ export function completionItem(completion, doc, requestedOffset, insertReplaceSu
|
|
|
145
132
|
textEdit,
|
|
146
133
|
insertTextFormat: InsertTextFormat.Snippet,
|
|
147
134
|
insertTextMode: ls.InsertTextMode.adjustIndentation,
|
|
148
|
-
...(completion.deprecated
|
|
149
|
-
? { tags: [ls.CompletionItemTag.Deprecated] }
|
|
150
|
-
: {}),
|
|
135
|
+
...(completion.deprecated ? { tags: [ls.CompletionItemTag.Deprecated] } : {}),
|
|
151
136
|
};
|
|
152
137
|
return ans;
|
|
153
138
|
}
|
|
154
139
|
export function location(location) {
|
|
155
|
-
return {
|
|
156
|
-
uri: location.uri,
|
|
157
|
-
range: location.posRange,
|
|
158
|
-
};
|
|
140
|
+
return { uri: location.uri, range: location.posRange };
|
|
159
141
|
}
|
|
160
142
|
export function locationLink(locations, doc, linkSupport) {
|
|
161
143
|
return locations?.locations
|
|
@@ -170,10 +152,7 @@ export function locationLink(locations, doc, linkSupport) {
|
|
|
170
152
|
: undefined;
|
|
171
153
|
}
|
|
172
154
|
export function markupContent(value) {
|
|
173
|
-
return {
|
|
174
|
-
kind: ls.MarkupKind.Markdown,
|
|
175
|
-
value: value,
|
|
176
|
-
};
|
|
155
|
+
return { kind: ls.MarkupKind.Markdown, value };
|
|
177
156
|
}
|
|
178
157
|
export function position(offset, doc) {
|
|
179
158
|
return doc.positionAt(offset);
|
|
@@ -204,10 +183,11 @@ export function semanticTokens(tokens, doc, multilineSupport) {
|
|
|
204
183
|
builder.push(pos.line, pos.character, length, type, modifiers);
|
|
205
184
|
}
|
|
206
185
|
else {
|
|
207
|
-
const firstLineRemainingLength = doc.getText(ls.Range.create(pos.line, pos.character, pos.line, MaxCharacterNumber))
|
|
186
|
+
const firstLineRemainingLength = doc.getText(ls.Range.create(pos.line, pos.character, pos.line, MaxCharacterNumber))
|
|
187
|
+
.length;
|
|
208
188
|
const lastLineLeadingLength = doc.getText(ls.Range.create(endPos.line, 0, endPos.line, endPos.character)).length;
|
|
209
189
|
builder.push(pos.line, pos.character, firstLineRemainingLength, type, modifiers);
|
|
210
|
-
for (let i = pos.line + 1; i
|
|
190
|
+
for (let i = pos.line + 1; i <= endPos.line - 1; i++) {
|
|
211
191
|
const lineLength = doc.getText(ls.Range.create(i, 0, i, MaxCharacterNumber)).length;
|
|
212
192
|
builder.push(i, 0, lineLength, type, modifiers);
|
|
213
193
|
}
|
|
@@ -240,18 +220,14 @@ export function signatureInformation(info) {
|
|
|
240
220
|
return {
|
|
241
221
|
label: info.label,
|
|
242
222
|
activeParameter: info.activeParameter,
|
|
243
|
-
documentation: info.documentation
|
|
244
|
-
? markupContent(info.documentation)
|
|
245
|
-
: undefined,
|
|
223
|
+
documentation: info.documentation ? markupContent(info.documentation) : undefined,
|
|
246
224
|
parameters: info.parameters.map(parameterInformation),
|
|
247
225
|
};
|
|
248
226
|
}
|
|
249
227
|
export function parameterInformation(info) {
|
|
250
228
|
return {
|
|
251
229
|
label: info.label,
|
|
252
|
-
documentation: info.documentation
|
|
253
|
-
? markupContent(info.documentation)
|
|
254
|
-
: undefined,
|
|
230
|
+
documentation: info.documentation ? markupContent(info.documentation) : undefined,
|
|
255
231
|
};
|
|
256
232
|
}
|
|
257
233
|
export function symbolInformation(symbol, symLoc, supportedKinds = []) {
|
|
@@ -265,9 +241,7 @@ export function symbolInformation(symbol, symLoc, supportedKinds = []) {
|
|
|
265
241
|
};
|
|
266
242
|
}
|
|
267
243
|
export function symbolInformationArray(map = {}, query, supportedKinds = []) {
|
|
268
|
-
return Object.values(map)
|
|
269
|
-
.filter((s) => s.identifier.includes(query))
|
|
270
|
-
.map((s) => [
|
|
244
|
+
return Object.values(map).filter((s) => s.identifier.includes(query)).map((s) => [
|
|
271
245
|
s,
|
|
272
246
|
[
|
|
273
247
|
...(s.declaration ?? []),
|
|
@@ -275,14 +249,10 @@ export function symbolInformationArray(map = {}, query, supportedKinds = []) {
|
|
|
275
249
|
...(s.implementation ?? []),
|
|
276
250
|
...(s.typeDefinition ?? []),
|
|
277
251
|
][0],
|
|
278
|
-
])
|
|
279
|
-
.filter(([_s, l]) => !!l)
|
|
280
|
-
.map(([s, l]) => symbolInformation(s, l, supportedKinds));
|
|
252
|
+
]).filter(([_s, l]) => !!l).map(([s, l]) => symbolInformation(s, l, supportedKinds));
|
|
281
253
|
}
|
|
282
254
|
export function symbolInformationArrayFromTable(table, query, supportedKinds = []) {
|
|
283
|
-
return Object.values(table)
|
|
284
|
-
.map((m) => symbolInformationArray(m, query, supportedKinds))
|
|
285
|
-
.flat();
|
|
255
|
+
return Object.values(table).map((m) => symbolInformationArray(m, query, supportedKinds)).flat();
|
|
286
256
|
}
|
|
287
257
|
export function symbolKind(category, subcategory = '', supportedKinds = []) {
|
|
288
258
|
const UltimateFallback = ls.SymbolKind.Variable;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@spyglassmc/language-server",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.8",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"main": "lib/server.js",
|
|
6
6
|
"types": "lib/server.d.ts",
|
|
@@ -21,10 +21,10 @@
|
|
|
21
21
|
"env-paths": "^2.2.1",
|
|
22
22
|
"vscode-languageserver": "^9.0.1",
|
|
23
23
|
"vscode-languageserver-textdocument": "^1.0.11",
|
|
24
|
-
"@spyglassmc/core": "0.4.
|
|
25
|
-
"@spyglassmc/java-edition": "0.3.
|
|
26
|
-
"@spyglassmc/locales": "0.3.
|
|
27
|
-
"@spyglassmc/mcdoc": "0.3.
|
|
24
|
+
"@spyglassmc/core": "0.4.6",
|
|
25
|
+
"@spyglassmc/java-edition": "0.3.9",
|
|
26
|
+
"@spyglassmc/locales": "0.3.6",
|
|
27
|
+
"@spyglassmc/mcdoc": "0.3.9"
|
|
28
28
|
},
|
|
29
29
|
"publishConfig": {
|
|
30
30
|
"access": "public"
|