@spyglassmc/mcdoc 0.1.1 → 0.2.0
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/binder/index.d.ts +2 -2
- package/lib/binder/index.js +2 -18
- package/lib/binder/uriBinder.js +5 -9
- package/lib/binder/util.js +2 -7
- package/lib/checker/CheckerContext.d.ts +1 -1
- package/lib/checker/CheckerContext.js +1 -2
- package/lib/checker/entry.d.ts +1 -1
- package/lib/checker/entry.js +4 -8
- package/lib/checker/index.d.ts +1 -1
- package/lib/checker/index.js +1 -17
- package/lib/colorizer/index.d.ts +1 -1
- package/lib/colorizer/index.js +8 -14
- package/lib/index.d.ts +5 -5
- package/lib/index.js +10 -40
- package/lib/node/index.d.ts +5 -2
- package/lib/node/index.js +84 -82
- package/lib/parser/index.d.ts +1 -1
- package/lib/parser/index.js +184 -214
- package/lib/type/index.d.ts +1 -1
- package/lib/type/index.js +24 -35
- package/package.json +4 -3
package/lib/parser/index.js
CHANGED
|
@@ -1,40 +1,14 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
-
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
-
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
-
}
|
|
8
|
-
Object.defineProperty(o, k2, desc);
|
|
9
|
-
}) : (function(o, m, k, k2) {
|
|
10
|
-
if (k2 === undefined) k2 = k;
|
|
11
|
-
o[k2] = m[k];
|
|
12
|
-
}));
|
|
13
|
-
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
-
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
-
}) : function(o, v) {
|
|
16
|
-
o["default"] = v;
|
|
17
|
-
});
|
|
18
|
-
var __importStar = (this && this.__importStar) || function (mod) {
|
|
19
|
-
if (mod && mod.__esModule) return mod;
|
|
20
|
-
var result = {};
|
|
21
|
-
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
22
|
-
__setModuleDefault(result, mod);
|
|
23
|
-
return result;
|
|
24
|
-
};
|
|
25
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
26
|
-
exports.type = exports.pathType = exports.unionType = exports.dispatcherType = exports.tupleType = exports.listType = exports.primitiveArrayType = exports.numericType = exports.literalType = exports.stringType = exports.integer = exports.booleanType = exports.anyType = exports.module_ = exports.useStatement = exports.typeAlias = exports.injection = exports.struct = exports.enum_ = exports.typedNumber = exports.float = exports.docComments = exports.docComment = exports.dispatchStatement = exports.attribute = exports.path = exports.identifier = exports.string = exports.resLoc = exports.literal = exports.comment = void 0;
|
|
27
|
-
const core = __importStar(require("@spyglassmc/core"));
|
|
28
|
-
const core_1 = require("@spyglassmc/core");
|
|
29
|
-
const locales_1 = require("@spyglassmc/locales");
|
|
1
|
+
import * as core from '@spyglassmc/core';
|
|
2
|
+
import { any, Arrayable, failOnEmpty, failOnError, Failure, map, optional, Range, repeat, ResourceLocation, select, sequence, setType, stopBefore, validate } from '@spyglassmc/core';
|
|
3
|
+
import { arrayToMessage, localeQuote, localize } from '@spyglassmc/locales';
|
|
30
4
|
/**
|
|
31
5
|
* @returns A comment parser that accepts normal comments (`//`) and reports an error if it's a doc comment (`///`).
|
|
32
6
|
*
|
|
33
7
|
* `Failure` when there isn't a comment.
|
|
34
8
|
*/
|
|
35
|
-
|
|
9
|
+
export const comment = validate(core.comment({
|
|
36
10
|
singleLinePrefixes: new Set(['//']),
|
|
37
|
-
}), (res, src) => !src.slice(res).startsWith('///'),
|
|
11
|
+
}), (res, src) => !src.slice(res).startsWith('///'), localize('mcdoc.parser.syntax.doc-comment-unexpected'));
|
|
38
12
|
/**
|
|
39
13
|
* @returns A parser that parses the gap between **SYNTAX** rules, which may contains whitespace and regular comments.
|
|
40
14
|
*/
|
|
@@ -45,7 +19,7 @@ delegatesDocComments = false) {
|
|
|
45
19
|
const ans = [];
|
|
46
20
|
src.skipWhitespace();
|
|
47
21
|
while (src.canRead() && src.peek(2) === '//' && (!delegatesDocComments || src.peek(3) !== '///')) {
|
|
48
|
-
const result =
|
|
22
|
+
const result = comment(src, ctx);
|
|
49
23
|
ans.push(result);
|
|
50
24
|
src.skipWhitespace();
|
|
51
25
|
}
|
|
@@ -55,36 +29,35 @@ delegatesDocComments = false) {
|
|
|
55
29
|
function syntax(parsers, delegatesDocComments = false) {
|
|
56
30
|
return (src, ctx) => {
|
|
57
31
|
src.skipWhitespace();
|
|
58
|
-
const ans =
|
|
32
|
+
const ans = sequence(parsers, syntaxGap(delegatesDocComments))(src, ctx);
|
|
59
33
|
src.skipWhitespace();
|
|
60
34
|
return ans;
|
|
61
35
|
};
|
|
62
36
|
}
|
|
63
37
|
function syntaxRepeat(parser, delegatesDocComments = false) {
|
|
64
|
-
return
|
|
38
|
+
return repeat(parser, syntaxGap(delegatesDocComments));
|
|
65
39
|
}
|
|
66
|
-
function literal(literal, options) {
|
|
40
|
+
export function literal(literal, options) {
|
|
67
41
|
return (src, ctx) => {
|
|
68
42
|
const ans = {
|
|
69
43
|
type: 'mcdoc:literal',
|
|
70
|
-
range:
|
|
44
|
+
range: Range.create(src),
|
|
71
45
|
value: '',
|
|
72
46
|
colorTokenType: options?.colorTokenType,
|
|
73
47
|
};
|
|
74
48
|
ans.value = src.readIf(c => options?.allowedChars?.has(c) ?? (options?.specialChars?.has(c) || /[a-z]/i.test(c)));
|
|
75
49
|
ans.range.end = src.cursor;
|
|
76
|
-
if (
|
|
77
|
-
ctx.err.report(
|
|
50
|
+
if (Arrayable.toArray(literal).every(l => l !== ans.value)) {
|
|
51
|
+
ctx.err.report(localize('expected-got', arrayToMessage(literal), localeQuote(ans.value)), ans);
|
|
78
52
|
}
|
|
79
53
|
return ans;
|
|
80
54
|
};
|
|
81
55
|
}
|
|
82
|
-
exports.literal = literal;
|
|
83
56
|
function keyword(keyword, options = { colorTokenType: 'keyword' }) {
|
|
84
57
|
return (src, ctx) => {
|
|
85
58
|
const result = literal(keyword, options)(src, ctx);
|
|
86
|
-
if (!
|
|
87
|
-
return
|
|
59
|
+
if (!Arrayable.toArray(keyword).includes(result.value)) {
|
|
60
|
+
return Failure;
|
|
88
61
|
}
|
|
89
62
|
return result;
|
|
90
63
|
};
|
|
@@ -93,7 +66,7 @@ function punctuation(punctuation) {
|
|
|
93
66
|
return (src, ctx) => {
|
|
94
67
|
src.skipWhitespace();
|
|
95
68
|
if (!src.trySkip(punctuation)) {
|
|
96
|
-
ctx.err.report(
|
|
69
|
+
ctx.err.report(localize('expected-got', localeQuote(punctuation), localeQuote(src.peek())), src);
|
|
97
70
|
}
|
|
98
71
|
return undefined;
|
|
99
72
|
};
|
|
@@ -102,32 +75,31 @@ function marker(punctuation) {
|
|
|
102
75
|
return (src, _ctx) => {
|
|
103
76
|
src.skipWhitespace();
|
|
104
77
|
if (!src.trySkip(punctuation)) {
|
|
105
|
-
return
|
|
78
|
+
return Failure;
|
|
106
79
|
}
|
|
107
80
|
return undefined;
|
|
108
81
|
};
|
|
109
82
|
}
|
|
110
|
-
function resLoc(options) {
|
|
111
|
-
return
|
|
83
|
+
export function resLoc(options) {
|
|
84
|
+
return validate(core.resourceLocation(options), res => res.namespace !== undefined, localize('mcdoc.parser.resource-location.colon-expected', localeQuote(ResourceLocation.NamespacePathSep)));
|
|
112
85
|
}
|
|
113
|
-
exports.resLoc = resLoc;
|
|
114
86
|
const UnicodeControlCharacters = Object.freeze([
|
|
115
87
|
'\x00', '\x01', '\x02', '\x03', '\x04', '\x05', '\x06',
|
|
116
88
|
'\x07', '\x08', '\x09', '\x0A', '\x0B', '\x0C', '\x0D',
|
|
117
89
|
'\x0E', '\x0F', '\x7F',
|
|
118
90
|
]);
|
|
119
|
-
|
|
91
|
+
export const string = stopBefore(core.string({
|
|
120
92
|
escapable: { characters: ['b', 'f', 'n', 'r', 't', '\\', '"'], unicode: true },
|
|
121
93
|
quotes: ['"'],
|
|
122
94
|
}), ...UnicodeControlCharacters);
|
|
123
|
-
const identifier = (src, ctx) => {
|
|
95
|
+
export const identifier = (src, ctx) => {
|
|
124
96
|
// https://spyglassmc.com/user/mcdoc/#identifier
|
|
125
97
|
const IdentifierStart = /^[\p{L}\p{Nl}]$/u;
|
|
126
98
|
const IdentifierContinue = /^[\p{L}\p{Nl}\u200C\u200D\p{Mn}\p{Mc}\p{Nd}\p{Pc}]$/u;
|
|
127
99
|
const ReservedWords = new Set(['any', 'boolean', 'byte', 'double', 'enum', 'false', 'float', 'int', 'long', 'short', 'string', 'struct', 'super', 'true']);
|
|
128
100
|
const ans = {
|
|
129
101
|
type: 'mcdoc:identifier',
|
|
130
|
-
range:
|
|
102
|
+
range: Range.create(src),
|
|
131
103
|
options: { category: 'mcdoc' },
|
|
132
104
|
value: '',
|
|
133
105
|
};
|
|
@@ -139,73 +111,72 @@ const identifier = (src, ctx) => {
|
|
|
139
111
|
}
|
|
140
112
|
}
|
|
141
113
|
else {
|
|
142
|
-
ctx.err.report(
|
|
114
|
+
ctx.err.report(localize('expected', localize('mcdoc.node.identifier')), src);
|
|
143
115
|
}
|
|
144
116
|
ans.value = src.string.slice(start, src.innerCursor);
|
|
145
117
|
ans.range.end = src.cursor;
|
|
146
118
|
if (ReservedWords.has(ans.value)) {
|
|
147
|
-
ctx.err.report(
|
|
119
|
+
ctx.err.report(localize('mcdoc.parser.identifier.reserved-word', localeQuote(ans.value)), ans);
|
|
148
120
|
}
|
|
149
121
|
return ans;
|
|
150
122
|
};
|
|
151
|
-
exports.identifier = identifier;
|
|
152
123
|
function indexBody(options) {
|
|
153
|
-
const accessorKey =
|
|
124
|
+
const accessorKey = select([
|
|
154
125
|
{
|
|
155
126
|
prefix: '%',
|
|
156
127
|
parser: literal(['%key', '%parent'], { specialChars: new Set(['%']) }),
|
|
157
128
|
},
|
|
158
129
|
{
|
|
159
130
|
prefix: '"',
|
|
160
|
-
parser:
|
|
131
|
+
parser: string,
|
|
161
132
|
},
|
|
162
133
|
{
|
|
163
|
-
parser:
|
|
134
|
+
parser: identifier,
|
|
164
135
|
},
|
|
165
136
|
]);
|
|
166
|
-
const dynamicIndex =
|
|
137
|
+
const dynamicIndex = setType('mcdoc:dynamic_index', syntax([
|
|
167
138
|
punctuation('['),
|
|
168
139
|
accessorKey,
|
|
169
|
-
|
|
140
|
+
repeat(sequence([marker('.'), accessorKey])),
|
|
170
141
|
punctuation(']'),
|
|
171
142
|
]));
|
|
172
|
-
const index =
|
|
143
|
+
const index = select([
|
|
173
144
|
{
|
|
174
145
|
prefix: '%',
|
|
175
146
|
parser: literal(['%fallback', '%none', '%unknown'], { specialChars: new Set(['%']) }),
|
|
176
147
|
},
|
|
177
148
|
{
|
|
178
149
|
prefix: '"',
|
|
179
|
-
parser:
|
|
150
|
+
parser: string,
|
|
180
151
|
},
|
|
181
152
|
{
|
|
182
153
|
prefix: '[',
|
|
183
154
|
parser: dynamicIndex,
|
|
184
155
|
},
|
|
185
156
|
{
|
|
186
|
-
parser:
|
|
157
|
+
parser: any([resLoc({ category: 'mcdoc/dispatcher', accessType: options?.accessType }), identifier]),
|
|
187
158
|
},
|
|
188
159
|
]);
|
|
189
|
-
return
|
|
160
|
+
return setType('mcdoc:index_body', syntax([
|
|
190
161
|
punctuation('['),
|
|
191
162
|
index,
|
|
192
|
-
syntaxRepeat(syntax([marker(','),
|
|
193
|
-
|
|
163
|
+
syntaxRepeat(syntax([marker(','), failOnEmpty(index)])),
|
|
164
|
+
optional(marker(',')),
|
|
194
165
|
punctuation(']'),
|
|
195
166
|
]));
|
|
196
167
|
}
|
|
197
|
-
const pathSegment =
|
|
168
|
+
const pathSegment = select([
|
|
198
169
|
{ prefix: 'super', parser: literal('super') },
|
|
199
|
-
{ parser:
|
|
170
|
+
{ parser: identifier },
|
|
200
171
|
]);
|
|
201
|
-
const path = (src, ctx) => {
|
|
172
|
+
export const path = (src, ctx) => {
|
|
202
173
|
let isAbsolute;
|
|
203
174
|
if (src.trySkip('::')) {
|
|
204
175
|
isAbsolute = true;
|
|
205
176
|
}
|
|
206
|
-
return
|
|
177
|
+
return map(sequence([
|
|
207
178
|
pathSegment,
|
|
208
|
-
|
|
179
|
+
repeat(sequence([marker('::'), pathSegment])),
|
|
209
180
|
]), res => {
|
|
210
181
|
const ans = {
|
|
211
182
|
type: 'mcdoc:path',
|
|
@@ -216,29 +187,28 @@ const path = (src, ctx) => {
|
|
|
216
187
|
return ans;
|
|
217
188
|
})(src, ctx);
|
|
218
189
|
};
|
|
219
|
-
|
|
220
|
-
const attributeTreePosValues = (0, core_1.setType)('mcdoc:attribute/tree/pos', syntax([
|
|
190
|
+
const attributeTreePosValues = setType('mcdoc:attribute/tree/pos', syntax([
|
|
221
191
|
{ get: () => attributeValue },
|
|
222
|
-
syntaxRepeat(syntax([marker(','), { get: () =>
|
|
192
|
+
syntaxRepeat(syntax([marker(','), { get: () => failOnEmpty(attributeValue) }], true), true),
|
|
223
193
|
], true));
|
|
224
194
|
const attributeNamedValue = syntax([
|
|
225
|
-
|
|
226
|
-
{ prefix: '"', parser:
|
|
227
|
-
{ parser:
|
|
195
|
+
select([
|
|
196
|
+
{ prefix: '"', parser: string },
|
|
197
|
+
{ parser: identifier },
|
|
228
198
|
]),
|
|
229
|
-
|
|
199
|
+
select([
|
|
230
200
|
{ prefix: '=', parser: syntax([punctuation('='), { get: () => attributeValue }], true) },
|
|
231
201
|
{ parser: { get: () => attributeTree } },
|
|
232
202
|
]),
|
|
233
203
|
], true);
|
|
234
|
-
const attributeTreeNamedValues =
|
|
204
|
+
const attributeTreeNamedValues = setType('mcdoc:attribute/tree/named', syntax([
|
|
235
205
|
attributeNamedValue,
|
|
236
|
-
syntaxRepeat(syntax([marker(','),
|
|
206
|
+
syntaxRepeat(syntax([marker(','), failOnEmpty(attributeNamedValue)], true), true),
|
|
237
207
|
], true));
|
|
238
|
-
const treeBody =
|
|
239
|
-
syntax([attributeTreeNamedValues,
|
|
240
|
-
syntax([attributeTreePosValues, punctuation(','), attributeTreeNamedValues,
|
|
241
|
-
syntax([attributeTreePosValues,
|
|
208
|
+
const treeBody = any([
|
|
209
|
+
syntax([attributeTreeNamedValues, optional(marker(','))]),
|
|
210
|
+
syntax([attributeTreePosValues, punctuation(','), attributeTreeNamedValues, optional(marker(','))]),
|
|
211
|
+
syntax([attributeTreePosValues, optional(marker(','))]),
|
|
242
212
|
]);
|
|
243
213
|
const AttributeTreeClosure = Object.freeze({
|
|
244
214
|
'(': ')',
|
|
@@ -248,7 +218,7 @@ const AttributeTreeClosure = Object.freeze({
|
|
|
248
218
|
const attributeTree = (src, ctx) => {
|
|
249
219
|
const delim = src.trySkip('(') ? '(' : (src.trySkip('[') ? '[' : (src.trySkip('{') ? '{' : undefined));
|
|
250
220
|
if (!delim) {
|
|
251
|
-
return
|
|
221
|
+
return Failure;
|
|
252
222
|
}
|
|
253
223
|
const res = treeBody(src, ctx);
|
|
254
224
|
const ans = {
|
|
@@ -260,38 +230,38 @@ const attributeTree = (src, ctx) => {
|
|
|
260
230
|
src.trySkip(AttributeTreeClosure[delim]);
|
|
261
231
|
return ans;
|
|
262
232
|
};
|
|
263
|
-
const attributeValue =
|
|
233
|
+
const attributeValue = select([
|
|
264
234
|
{ predicate: src => ['(', '[', '{'].includes(src.peek()), parser: attributeTree },
|
|
265
|
-
{ parser: { get: () =>
|
|
235
|
+
{ parser: { get: () => type } },
|
|
266
236
|
]);
|
|
267
|
-
|
|
237
|
+
export const attribute = setType('mcdoc:attribute', syntax([
|
|
268
238
|
marker('#['),
|
|
269
|
-
|
|
270
|
-
|
|
239
|
+
identifier,
|
|
240
|
+
select([
|
|
271
241
|
{ prefix: '=', parser: syntax([punctuation('='), attributeValue, punctuation(']')], true) },
|
|
272
242
|
{ predicate: src => ['(', '[', '{'].includes(src.peek()), parser: syntax([attributeTree, punctuation(']')], true) },
|
|
273
243
|
{ parser: punctuation(']') },
|
|
274
244
|
]),
|
|
275
245
|
], true));
|
|
276
|
-
const attributes =
|
|
277
|
-
|
|
246
|
+
const attributes = repeat(attribute);
|
|
247
|
+
export const dispatchStatement = setType('mcdoc:dispatch_statement', syntax([
|
|
278
248
|
attributes,
|
|
279
249
|
keyword('dispatch'),
|
|
280
250
|
resLoc({ category: 'mcdoc/dispatcher', accessType: 1 /* SymbolAccessType.Write */ }),
|
|
281
251
|
indexBody({ noDynamic: true }),
|
|
282
252
|
literal('to'),
|
|
283
|
-
{ get: () =>
|
|
253
|
+
{ get: () => type },
|
|
284
254
|
], true));
|
|
285
|
-
|
|
255
|
+
export const docComment = core.comment({
|
|
286
256
|
singleLinePrefixes: new Set(['///']),
|
|
287
257
|
includesEol: true,
|
|
288
258
|
});
|
|
289
|
-
|
|
259
|
+
export const docComments = setType('mcdoc:doc_comments', repeat(docComment, src => {
|
|
290
260
|
src.skipWhitespace();
|
|
291
261
|
return [];
|
|
292
262
|
}));
|
|
293
263
|
const prelim = syntax([
|
|
294
|
-
|
|
264
|
+
optional(failOnEmpty(docComments)),
|
|
295
265
|
attributes,
|
|
296
266
|
]);
|
|
297
267
|
const enumType = literal([
|
|
@@ -303,78 +273,78 @@ const enumType = literal([
|
|
|
303
273
|
'float',
|
|
304
274
|
'double',
|
|
305
275
|
], { colorTokenType: 'type' });
|
|
306
|
-
|
|
276
|
+
export const float = core.float({
|
|
307
277
|
pattern: /^[-+]?(?:[0-9]+(?:[eE][-+]?[0-9]+)?|[0-9]*\.[0-9]+(?:[eE][-+]?[0-9]+)?)$/,
|
|
308
278
|
});
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
279
|
+
export const typedNumber = setType('mcdoc:typed_number', sequence([
|
|
280
|
+
float,
|
|
281
|
+
optional(keyword(['b', 'B', 'd', 'D', 'f', 'F', 'l', 'L', 's', 'S'], { colorTokenType: 'keyword' })),
|
|
312
282
|
]));
|
|
313
|
-
const enumValue =
|
|
314
|
-
{ prefix: '"', parser:
|
|
315
|
-
{ parser:
|
|
283
|
+
const enumValue = select([
|
|
284
|
+
{ prefix: '"', parser: string },
|
|
285
|
+
{ parser: typedNumber },
|
|
316
286
|
]);
|
|
317
|
-
const enumField =
|
|
287
|
+
const enumField = setType('mcdoc:enum/field', syntax([
|
|
318
288
|
prelim,
|
|
319
|
-
|
|
289
|
+
identifier,
|
|
320
290
|
punctuation('='),
|
|
321
291
|
enumValue,
|
|
322
292
|
], true));
|
|
323
|
-
const enumBlock =
|
|
293
|
+
const enumBlock = setType('mcdoc:enum/block', syntax([
|
|
324
294
|
punctuation('{'),
|
|
325
|
-
|
|
295
|
+
select([
|
|
326
296
|
{ prefix: '}', parser: punctuation('}') },
|
|
327
297
|
{
|
|
328
298
|
parser: syntax([
|
|
329
299
|
enumField,
|
|
330
|
-
syntaxRepeat(syntax([marker(','),
|
|
331
|
-
|
|
300
|
+
syntaxRepeat(syntax([marker(','), failOnEmpty(enumField)], true), true),
|
|
301
|
+
optional(marker(',')),
|
|
332
302
|
punctuation('}'),
|
|
333
303
|
], true),
|
|
334
304
|
},
|
|
335
305
|
]),
|
|
336
306
|
], true));
|
|
337
|
-
|
|
307
|
+
export const enum_ = setType('mcdoc:enum', syntax([
|
|
338
308
|
prelim,
|
|
339
309
|
keyword('enum'),
|
|
340
310
|
punctuation('('),
|
|
341
311
|
enumType,
|
|
342
312
|
punctuation(')'),
|
|
343
|
-
|
|
313
|
+
optional(failOnError(identifier)),
|
|
344
314
|
enumBlock,
|
|
345
315
|
], true));
|
|
346
|
-
const typeParam =
|
|
347
|
-
|
|
348
|
-
|
|
316
|
+
const typeParam = setType('mcdoc:type_param', syntax([
|
|
317
|
+
identifier,
|
|
318
|
+
optional(syntax([failOnError(literal('extends')), path])),
|
|
349
319
|
]));
|
|
350
|
-
const typeParamBlock =
|
|
320
|
+
const typeParamBlock = setType('mcdoc:type_param_block', syntax([
|
|
351
321
|
punctuation('<'),
|
|
352
|
-
|
|
322
|
+
select([
|
|
353
323
|
{ prefix: '>', parser: punctuation('>') },
|
|
354
324
|
{
|
|
355
325
|
parser: syntax([
|
|
356
326
|
typeParam,
|
|
357
|
-
syntaxRepeat(syntax([marker(','),
|
|
358
|
-
|
|
327
|
+
syntaxRepeat(syntax([marker(','), failOnEmpty(typeParam)])),
|
|
328
|
+
optional(marker(',')),
|
|
359
329
|
punctuation('>'),
|
|
360
330
|
]),
|
|
361
331
|
},
|
|
362
332
|
]),
|
|
363
333
|
]));
|
|
364
334
|
const noop = () => undefined;
|
|
365
|
-
const optionalTypeParamBlock =
|
|
335
|
+
const optionalTypeParamBlock = select([
|
|
366
336
|
{ prefix: '<', parser: typeParamBlock },
|
|
367
337
|
{ parser: noop },
|
|
368
338
|
]);
|
|
369
|
-
const structMapKey =
|
|
339
|
+
const structMapKey = setType('mcdoc:struct/map_key', syntax([
|
|
370
340
|
punctuation('['),
|
|
371
|
-
{ get: () =>
|
|
341
|
+
{ get: () => type },
|
|
372
342
|
punctuation(']'),
|
|
373
343
|
], true));
|
|
374
|
-
const structKey =
|
|
375
|
-
{ prefix: '"', parser:
|
|
344
|
+
const structKey = select([
|
|
345
|
+
{ prefix: '"', parser: string },
|
|
376
346
|
{ prefix: '[', parser: structMapKey },
|
|
377
|
-
{ parser:
|
|
347
|
+
{ parser: identifier },
|
|
378
348
|
]);
|
|
379
349
|
const structPairField = (src, ctx) => {
|
|
380
350
|
let isOptional;
|
|
@@ -387,124 +357,124 @@ const structPairField = (src, ctx) => {
|
|
|
387
357
|
}
|
|
388
358
|
const result1 = syntax([
|
|
389
359
|
punctuation(':'),
|
|
390
|
-
{ get: () =>
|
|
360
|
+
{ get: () => type },
|
|
391
361
|
], true)(src, ctx);
|
|
392
362
|
const ans = {
|
|
393
363
|
type: 'mcdoc:struct/field/pair',
|
|
394
364
|
children: [...result0.children, ...result1.children],
|
|
395
|
-
range:
|
|
365
|
+
range: Range.span(result0, result1),
|
|
396
366
|
isOptional,
|
|
397
367
|
};
|
|
398
368
|
return ans;
|
|
399
369
|
};
|
|
400
|
-
const structSpreadField =
|
|
370
|
+
const structSpreadField = setType('mcdoc:struct/field/spread', syntax([
|
|
401
371
|
attributes,
|
|
402
372
|
marker('...'),
|
|
403
|
-
{ get: () =>
|
|
373
|
+
{ get: () => type },
|
|
404
374
|
], true));
|
|
405
|
-
const structField =
|
|
375
|
+
const structField = any([
|
|
406
376
|
structSpreadField,
|
|
407
377
|
structPairField,
|
|
408
378
|
]);
|
|
409
|
-
const structBlock =
|
|
379
|
+
const structBlock = setType('mcdoc:struct/block', syntax([
|
|
410
380
|
punctuation('{'),
|
|
411
|
-
|
|
381
|
+
select([
|
|
412
382
|
{ prefix: '}', parser: punctuation('}') },
|
|
413
383
|
{
|
|
414
384
|
parser: syntax([
|
|
415
385
|
structField,
|
|
416
|
-
syntaxRepeat(syntax([marker(','),
|
|
417
|
-
|
|
386
|
+
syntaxRepeat(syntax([marker(','), failOnEmpty(structField)], true), true),
|
|
387
|
+
optional(marker(',')),
|
|
418
388
|
punctuation('}'),
|
|
419
389
|
], true),
|
|
420
390
|
},
|
|
421
391
|
]),
|
|
422
392
|
], true));
|
|
423
|
-
|
|
393
|
+
export const struct = setType('mcdoc:struct', syntax([
|
|
424
394
|
prelim,
|
|
425
395
|
keyword('struct'),
|
|
426
|
-
|
|
396
|
+
optional(failOnEmpty(identifier)),
|
|
427
397
|
optionalTypeParamBlock,
|
|
428
398
|
structBlock,
|
|
429
399
|
], true));
|
|
430
|
-
const enumInjection =
|
|
400
|
+
const enumInjection = setType('mcdoc:injection/enum', syntax([
|
|
431
401
|
literal('enum'),
|
|
432
402
|
punctuation('('),
|
|
433
403
|
enumType,
|
|
434
404
|
punctuation(')'),
|
|
435
|
-
|
|
405
|
+
path,
|
|
436
406
|
enumBlock,
|
|
437
407
|
]));
|
|
438
|
-
const structInjection =
|
|
408
|
+
const structInjection = setType('mcdoc:injection/struct', syntax([
|
|
439
409
|
literal('struct'),
|
|
440
|
-
|
|
410
|
+
path,
|
|
441
411
|
optionalTypeParamBlock,
|
|
442
412
|
structBlock,
|
|
443
413
|
]));
|
|
444
|
-
|
|
414
|
+
export const injection = setType('mcdoc:injection', syntax([
|
|
445
415
|
keyword('inject'),
|
|
446
|
-
|
|
416
|
+
select([
|
|
447
417
|
{ prefix: 'enum', parser: enumInjection },
|
|
448
418
|
{ parser: structInjection },
|
|
449
419
|
]),
|
|
450
420
|
]));
|
|
451
|
-
|
|
421
|
+
export const typeAlias = setType('mcdoc:type_alias', syntax([
|
|
452
422
|
prelim,
|
|
453
423
|
keyword('type'),
|
|
454
|
-
|
|
424
|
+
identifier,
|
|
455
425
|
optionalTypeParamBlock,
|
|
456
426
|
punctuation('='),
|
|
457
|
-
{ get: () =>
|
|
427
|
+
{ get: () => type },
|
|
458
428
|
], true));
|
|
459
|
-
|
|
429
|
+
export const useStatement = setType('mcdoc:use_statement', syntax([
|
|
460
430
|
keyword('use'),
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
{ prefix: 'as', parser: syntax([literal('as'),
|
|
431
|
+
path,
|
|
432
|
+
select([
|
|
433
|
+
{ prefix: 'as', parser: syntax([literal('as'), identifier]) },
|
|
464
434
|
{ parser: noop },
|
|
465
435
|
]),
|
|
466
436
|
], true));
|
|
467
|
-
const topLevel =
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
437
|
+
const topLevel = any([
|
|
438
|
+
comment,
|
|
439
|
+
dispatchStatement,
|
|
440
|
+
enum_,
|
|
441
|
+
injection,
|
|
442
|
+
struct,
|
|
443
|
+
typeAlias,
|
|
444
|
+
useStatement,
|
|
475
445
|
]);
|
|
476
|
-
|
|
446
|
+
export const module_ = setType('mcdoc:module', syntaxRepeat(topLevel, true));
|
|
477
447
|
/* eslint-enable @typescript-eslint/indent */
|
|
478
448
|
function typeBase(type, parser) {
|
|
479
|
-
return
|
|
449
|
+
return setType(type, syntax([
|
|
480
450
|
attributes,
|
|
481
451
|
parser,
|
|
482
|
-
syntaxRepeat(
|
|
452
|
+
syntaxRepeat(failOnError(indexBody())),
|
|
483
453
|
], true));
|
|
484
454
|
}
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
455
|
+
export const anyType = typeBase('mcdoc:type/any', keyword('any', { colorTokenType: 'type' }));
|
|
456
|
+
export const booleanType = typeBase('mcdoc:type/boolean', keyword('boolean', { colorTokenType: 'type' }));
|
|
457
|
+
export const integer = core.integer({
|
|
488
458
|
pattern: /^(?:0|[-+]?[1-9][0-9]*)$/,
|
|
489
459
|
});
|
|
490
460
|
function range(type, number) {
|
|
491
|
-
return
|
|
461
|
+
return setType(type, select([
|
|
492
462
|
{
|
|
493
463
|
prefix: '..',
|
|
494
|
-
parser:
|
|
464
|
+
parser: sequence([
|
|
495
465
|
literal('..', { allowedChars: new Set('.') }),
|
|
496
466
|
number,
|
|
497
467
|
]),
|
|
498
468
|
},
|
|
499
469
|
{
|
|
500
|
-
parser:
|
|
501
|
-
|
|
502
|
-
|
|
470
|
+
parser: sequence([
|
|
471
|
+
stopBefore(number, '..'),
|
|
472
|
+
select([
|
|
503
473
|
{
|
|
504
474
|
prefix: '..',
|
|
505
|
-
parser:
|
|
475
|
+
parser: sequence([
|
|
506
476
|
literal('..', { allowedChars: new Set('.') }),
|
|
507
|
-
|
|
477
|
+
optional(failOnEmpty(number)),
|
|
508
478
|
]),
|
|
509
479
|
},
|
|
510
480
|
{ parser: noop },
|
|
@@ -513,32 +483,32 @@ function range(type, number) {
|
|
|
513
483
|
},
|
|
514
484
|
]));
|
|
515
485
|
}
|
|
516
|
-
const intRange = range('mcdoc:int_range',
|
|
517
|
-
const atIntRange =
|
|
486
|
+
const intRange = range('mcdoc:int_range', integer);
|
|
487
|
+
const atIntRange = optional((src, ctx) => {
|
|
518
488
|
if (!src.trySkip('@')) {
|
|
519
|
-
return
|
|
489
|
+
return Failure;
|
|
520
490
|
}
|
|
521
491
|
src.skipWhitespace();
|
|
522
492
|
return intRange(src, ctx);
|
|
523
493
|
});
|
|
524
|
-
|
|
494
|
+
export const stringType = typeBase('mcdoc:type/string', syntax([
|
|
525
495
|
keyword('string', { colorTokenType: 'type' }),
|
|
526
496
|
atIntRange,
|
|
527
497
|
]));
|
|
528
|
-
|
|
498
|
+
export const literalType = typeBase('mcdoc:type/literal', select([
|
|
529
499
|
{ predicate: src => src.tryPeek('false') || src.tryPeek('true'), parser: keyword(['false', 'true'], { colorTokenType: 'type' }) },
|
|
530
|
-
{ prefix: '"', parser:
|
|
531
|
-
{ parser:
|
|
500
|
+
{ prefix: '"', parser: failOnEmpty(string) },
|
|
501
|
+
{ parser: failOnError(typedNumber) },
|
|
532
502
|
]));
|
|
533
|
-
const floatRange = range('mcdoc:float_range',
|
|
534
|
-
const atFloatRange =
|
|
503
|
+
const floatRange = range('mcdoc:float_range', float);
|
|
504
|
+
const atFloatRange = optional((src, ctx) => {
|
|
535
505
|
if (!src.trySkip('@')) {
|
|
536
|
-
return
|
|
506
|
+
return Failure;
|
|
537
507
|
}
|
|
538
508
|
src.skipWhitespace();
|
|
539
509
|
return floatRange(src, ctx);
|
|
540
510
|
});
|
|
541
|
-
|
|
511
|
+
export const numericType = typeBase('mcdoc:type/numeric_type', select([
|
|
542
512
|
{
|
|
543
513
|
predicate: src => src.tryPeek('float') || src.tryPeek('double'),
|
|
544
514
|
parser: syntax([
|
|
@@ -553,82 +523,82 @@ exports.numericType = typeBase('mcdoc:type/numeric_type', (0, core_1.select)([
|
|
|
553
523
|
]),
|
|
554
524
|
},
|
|
555
525
|
]));
|
|
556
|
-
|
|
526
|
+
export const primitiveArrayType = typeBase('mcdoc:type/primitive_array', syntax([
|
|
557
527
|
literal(['byte', 'int', 'long']),
|
|
558
528
|
atIntRange,
|
|
559
529
|
keyword('[]', { allowedChars: new Set(['[', ']']), colorTokenType: 'type' }),
|
|
560
530
|
atIntRange,
|
|
561
531
|
]));
|
|
562
|
-
|
|
532
|
+
export const listType = typeBase('mcdoc:type/list', syntax([
|
|
563
533
|
marker('['),
|
|
564
|
-
{ get: () =>
|
|
534
|
+
{ get: () => type },
|
|
565
535
|
punctuation(']'),
|
|
566
536
|
atIntRange,
|
|
567
537
|
], true));
|
|
568
|
-
|
|
538
|
+
export const tupleType = typeBase('mcdoc:type/tuple', syntax([
|
|
569
539
|
marker('['),
|
|
570
|
-
{ get: () =>
|
|
540
|
+
{ get: () => type },
|
|
571
541
|
marker(','),
|
|
572
|
-
|
|
542
|
+
select([
|
|
573
543
|
{ prefix: ']', parser: punctuation(']') },
|
|
574
544
|
{
|
|
575
545
|
parser: syntax([
|
|
576
|
-
{ get: () =>
|
|
577
|
-
syntaxRepeat(syntax([marker(','), { get: () =>
|
|
578
|
-
|
|
546
|
+
{ get: () => type },
|
|
547
|
+
syntaxRepeat(syntax([marker(','), { get: () => failOnEmpty(type) }], true), true),
|
|
548
|
+
optional(marker(',')),
|
|
579
549
|
punctuation(']'),
|
|
580
550
|
], true),
|
|
581
551
|
},
|
|
582
552
|
]),
|
|
583
553
|
], true));
|
|
584
|
-
|
|
585
|
-
|
|
554
|
+
export const dispatcherType = typeBase('mcdoc:type/dispatcher', syntax([
|
|
555
|
+
failOnError(resLoc({ category: 'mcdoc/dispatcher' })),
|
|
586
556
|
indexBody(),
|
|
587
557
|
]));
|
|
588
|
-
|
|
558
|
+
export const unionType = typeBase('mcdoc:type/union', syntax([
|
|
589
559
|
marker('('),
|
|
590
|
-
|
|
560
|
+
select([
|
|
591
561
|
{ prefix: ')', parser: punctuation(')') },
|
|
592
562
|
{
|
|
593
563
|
parser: syntax([
|
|
594
|
-
{ get: () =>
|
|
595
|
-
syntaxRepeat(syntax([marker('|'), { get: () =>
|
|
596
|
-
|
|
564
|
+
{ get: () => type },
|
|
565
|
+
syntaxRepeat(syntax([marker('|'), { get: () => failOnEmpty(type) }], true), true),
|
|
566
|
+
optional(marker('|')),
|
|
597
567
|
punctuation(')'),
|
|
598
568
|
], true),
|
|
599
569
|
},
|
|
600
570
|
]),
|
|
601
571
|
]));
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
572
|
+
export const pathType = typeBase('mcdoc:type/path', syntax([
|
|
573
|
+
path,
|
|
574
|
+
optional(syntax([
|
|
605
575
|
marker('<'),
|
|
606
|
-
|
|
576
|
+
select([
|
|
607
577
|
{ prefix: '>', parser: punctuation('>') },
|
|
608
578
|
{
|
|
609
579
|
parser: syntax([
|
|
610
|
-
{ get: () =>
|
|
611
|
-
syntaxRepeat(syntax([marker(','), { get: () =>
|
|
612
|
-
|
|
580
|
+
{ get: () => type },
|
|
581
|
+
syntaxRepeat(syntax([marker(','), { get: () => failOnEmpty(type) }], true), true),
|
|
582
|
+
optional(marker(',')),
|
|
613
583
|
punctuation('>'),
|
|
614
584
|
], true),
|
|
615
585
|
},
|
|
616
586
|
]),
|
|
617
587
|
])),
|
|
618
588
|
]));
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
589
|
+
export const type = any([
|
|
590
|
+
anyType,
|
|
591
|
+
booleanType,
|
|
592
|
+
dispatcherType,
|
|
593
|
+
enum_,
|
|
594
|
+
listType,
|
|
595
|
+
literalType,
|
|
596
|
+
numericType,
|
|
597
|
+
primitiveArrayType,
|
|
598
|
+
stringType,
|
|
599
|
+
struct,
|
|
600
|
+
tupleType,
|
|
601
|
+
unionType,
|
|
602
|
+
pathType,
|
|
633
603
|
]);
|
|
634
604
|
//# sourceMappingURL=index.js.map
|