tree-sitter-ucode 0.4.0 → 0.6.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.
@@ -400,9 +400,7 @@ static bool scan_automatic_semicolon(TSLexer *lexer) {
400
400
  }
401
401
 
402
402
  static bool scan_ternary_qmark(TSLexer *lexer) {
403
- while (lexer->lookahead != '\r' && lexer->lookahead != '\n' &&
404
- lexer->lookahead != 0x2028 && lexer->lookahead != 0x2029 &&
405
- iswspace(lexer->lookahead))
403
+ while (iswspace(lexer->lookahead))
406
404
  skip(lexer);
407
405
 
408
406
  if (lexer->lookahead != '?') return false;
Binary file
Binary file
package/tree-sitter.json CHANGED
@@ -14,9 +14,21 @@
14
14
  "locals": [
15
15
  "queries/locals.scm"
16
16
  ],
17
+ "injections": [
18
+ "queries/injections.scm"
19
+ ],
17
20
  "tags": [
18
21
  "queries/tags.scm"
19
22
  ],
23
+ "folds": [
24
+ "queries/folds.scm"
25
+ ],
26
+ "indents": [
27
+ "queries/indents.scm"
28
+ ],
29
+ "textobjects": [
30
+ "queries/textobjects.scm"
31
+ ],
20
32
  "injection-regex": "^ucode$"
21
33
  },
22
34
  {
@@ -50,10 +62,23 @@
50
62
  "markup/queries/textobjects.scm"
51
63
  ],
52
64
  "injection-regex": "^ucode_markup$"
65
+ },
66
+ {
67
+ "name": "ucdocs",
68
+ "camelcase": "Ucdocs",
69
+ "path": "./ucdocs",
70
+ "file-types": null,
71
+ "highlights": [
72
+ "ucdocs/queries/highlights.scm"
73
+ ],
74
+ "tags": [
75
+ "ucdocs/queries/tags.scm"
76
+ ],
77
+ "injection-regex": "^ucdocs$"
53
78
  }
54
79
  ],
55
80
  "metadata": {
56
- "version": "0.4.0",
81
+ "version": "0.5.0",
57
82
  "license": "MIT",
58
83
  "description": "Ucode grammar for tree-sitter",
59
84
  "links": {
@@ -0,0 +1,313 @@
1
+ /**
2
+ * @file Ucdocs grammar for tree-sitter
3
+ * @license MIT
4
+ */
5
+
6
+ /// <reference types="tree-sitter-cli/dsl" />
7
+ // @ts-check
8
+
9
+ module.exports = grammar({
10
+ name: 'ucdocs',
11
+
12
+ extras: _ => [
13
+ token(choice(
14
+ // Skip leading stars at the start of each line (e.g. " * " in block comments)
15
+ seq(/\n/, /[ \t]*/, repeat(seq('*', /[ \t]*/))),
16
+ /\s/,
17
+ )),
18
+ ],
19
+
20
+ rules: {
21
+ document: $ => seq(
22
+ $._begin,
23
+ optional(alias($._free_description, $.description)),
24
+ repeat(choice(
25
+ $.param_tag,
26
+ $.returns_tag,
27
+ $.template_tag,
28
+ $.typedef_tag,
29
+ $.type_tag,
30
+ $.throws_tag,
31
+ $.deprecated_tag,
32
+ $.since_tag,
33
+ $.see_tag,
34
+ $.example_tag,
35
+ $.default_tag,
36
+ $.function_tag,
37
+ $.module_tag,
38
+ $.unknown_tag,
39
+ )),
40
+ $._end,
41
+ ),
42
+
43
+ _begin: _ => token(seq('/', /\*+/)),
44
+ _end: _ => token(seq(/\**/, '/')),
45
+
46
+ // Used after a type_expression/rest_type_expression has already claimed `{` at
47
+ // this position (param_tag, returns_tag, throws_tag) — excludes _brace_text so
48
+ // it never competes with a legitimate {type} for the leading `{`.
49
+ _typed_description: $ => repeat1(choice($._text, $.inline_tag)),
50
+
51
+ // Used wherever no type_expression can appear at the same position, so a bare
52
+ // `{` can only be an inline tag or arbitrary brace-text (e.g. @example code).
53
+ _free_description: $ => repeat1(choice($._text, $.inline_tag, $._brace_text)),
54
+
55
+ // {@link target text} and similar inline JSDoc tags embedded in description text.
56
+ inline_tag: $ => seq(
57
+ '{',
58
+ $.tag_name,
59
+ optional(alias($._free_description, $.description)),
60
+ '}',
61
+ ),
62
+
63
+ // A `{` not immediately followed by `@tagname` is not an inline tag — e.g. an
64
+ // object literal or arrow-function block in an @example code block. Recursive
65
+ // so nested braces (object literals inside arrow functions, etc.) stay balanced
66
+ // instead of erroring out on the first inner `}`.
67
+ _brace_text: $ => seq(
68
+ '{',
69
+ optional(seq(
70
+ /[^{}@]/,
71
+ repeat(choice(
72
+ /[^{}]+/,
73
+ $._brace_text,
74
+ )),
75
+ )),
76
+ '}',
77
+ ),
78
+
79
+ param_tag: $ => seq(
80
+ '@param',
81
+ optional(field('type', choice($.type_expression, $.rest_type_expression))),
82
+ optional(field('name', choice($.identifier, $.optional_param))),
83
+ optional(field('description', alias($._typed_description, $.description))),
84
+ ),
85
+
86
+ // [name] or [name=default] — marks the parameter as optional, JSDoc-style.
87
+ optional_param: $ => seq(
88
+ '[',
89
+ field('name', $.param_path),
90
+ optional(seq('=', field('default', $.default_value))),
91
+ ']',
92
+ ),
93
+
94
+ // Dotted parameter paths, e.g. opts.precision for nested option fields.
95
+ param_path: $ => seq(
96
+ $.identifier,
97
+ repeat(seq('.', $.identifier)),
98
+ ),
99
+
100
+ default_value: _ => token(choice(
101
+ /-?\d+(\.\d+)?/,
102
+ /[a-zA-Z_$][a-zA-Z0-9_$]*/,
103
+ )),
104
+
105
+ returns_tag: $ => seq(
106
+ choice('@returns', '@return'),
107
+ optional(field('type', $.type_expression)),
108
+ optional(field('description', alias($._typed_description, $.description))),
109
+ ),
110
+
111
+ template_tag: $ => seq(
112
+ '@template',
113
+ commaSep1(alias($.type_identifier, $.type_param)),
114
+ ),
115
+
116
+ typedef_tag: $ => seq(
117
+ '@typedef',
118
+ optional(field('type', $.type_expression)),
119
+ field('name', $.type_identifier),
120
+ ),
121
+
122
+ type_tag: $ => seq(
123
+ '@type',
124
+ field('type', $.type_expression),
125
+ ),
126
+
127
+ throws_tag: $ => seq(
128
+ choice('@throws', '@throw'),
129
+ optional(field('type', $.type_expression)),
130
+ optional(field('description', alias($._typed_description, $.description))),
131
+ ),
132
+
133
+ deprecated_tag: $ => seq(
134
+ '@deprecated',
135
+ optional(field('description', alias($._free_description, $.description))),
136
+ ),
137
+
138
+ since_tag: $ => seq(
139
+ '@since',
140
+ optional(field('description', alias($._free_description, $.description))),
141
+ ),
142
+
143
+ see_tag: $ => seq(
144
+ '@see',
145
+ optional(field('description', alias($._free_description, $.description))),
146
+ ),
147
+
148
+ example_tag: $ => seq(
149
+ '@example',
150
+ optional(field('description', alias($._free_description, $.description))),
151
+ ),
152
+
153
+ default_tag: $ => seq(
154
+ '@default',
155
+ optional(field('description', alias($._free_description, $.description))),
156
+ ),
157
+
158
+ // @function module:X.Y#Z — identifies the qualified name of the documented function.
159
+ function_tag: $ => seq(
160
+ '@function',
161
+ optional(field('namepath', $.namepath)),
162
+ ),
163
+
164
+ // @module name — identifies the module this file documents.
165
+ module_tag: $ => seq(
166
+ '@module',
167
+ field('name', $.member_name),
168
+ ),
169
+
170
+ // module:X.Y#Z — a namepath referencing a specific member within a module.
171
+ // The #member suffix distinguishes instance methods from the module path itself.
172
+ namepath: $ => seq(
173
+ 'module:',
174
+ field('path', $.module_path),
175
+ optional(seq('#', field('member', $.member_name))),
176
+ ),
177
+
178
+ // Member names cover lowercase (error), uppercase (ERR), and underscored (ulog_open).
179
+ member_name: _ => /[a-zA-Z_$][a-zA-Z0-9_$]*/,
180
+
181
+ unknown_tag: $ => seq(
182
+ $.tag_name,
183
+ optional(field('description', alias($._free_description, $.description))),
184
+ ),
185
+
186
+ tag_name: _ => /@[a-zA-Z_]+/,
187
+
188
+ // ── Type expressions ────────────────────────────────────────────────────
189
+
190
+ type_expression: $ => seq('{', $._type, '}'),
191
+
192
+ // {..Type} — only valid on @param, signals a rest/variadic parameter.
193
+ rest_type_expression: $ => seq('{', '...', $._type, '}'),
194
+
195
+ _type: $ => choice(
196
+ $.primitive_type,
197
+ $.list_type,
198
+ $.dict_type,
199
+ $.record_type,
200
+ $.named_type,
201
+ $.module_type,
202
+ $.function_type,
203
+ $.anon_function_type,
204
+ $.union_type,
205
+ $.nullable_type,
206
+ $.any_type,
207
+ $.parenthesized_type,
208
+ $.array_type,
209
+ ),
210
+
211
+ primitive_type: _ => choice('int', 'float', 'string', 'boolean', 'null', 'void', 'function'),
212
+
213
+ any_type: _ => choice('*', 'any'),
214
+
215
+ list_type: $ => seq(
216
+ 'list',
217
+ '<',
218
+ field('element', $._type),
219
+ '>',
220
+ ),
221
+
222
+ dict_type: $ => seq(
223
+ 'dict',
224
+ '<',
225
+ field('value', $._type),
226
+ '>',
227
+ ),
228
+
229
+ record_type: $ => seq(
230
+ '{',
231
+ commaSep($.record_field),
232
+ '}',
233
+ ),
234
+
235
+ record_field: $ => seq(
236
+ field('name', $.identifier),
237
+ ':',
238
+ field('type', $._type),
239
+ ),
240
+
241
+ // module:core.ParseConfig — cross-module type reference used by stdlib docs.
242
+ module_type: $ => seq(
243
+ 'module:',
244
+ field('path', $.module_path),
245
+ ),
246
+
247
+ module_path: _ => /[a-zA-Z_$][a-zA-Z0-9_$]*(\.[a-zA-Z_$][a-zA-Z0-9_$]*)*/,
248
+
249
+ // Covers bare TypeName and generic TypeName<T>, TypeName<T, U>, etc.
250
+ named_type: $ => seq(
251
+ field('name', $.type_identifier),
252
+ optional(seq(
253
+ '<',
254
+ field('params', commaSep1($._type)),
255
+ '>',
256
+ )),
257
+ ),
258
+
259
+ function_type: $ => seq(
260
+ '(',
261
+ field('params', commaSep($.function_param)),
262
+ ')',
263
+ '=>',
264
+ field('return', $._type),
265
+ ),
266
+
267
+ function_param: $ => seq(
268
+ field('name', $.identifier),
269
+ ':',
270
+ field('type', $._type),
271
+ ),
272
+
273
+ // JSDoc anonymous function syntax: function(T, U): V (no parameter names).
274
+ // Return type is optional to allow bare function(T) declarations.
275
+ anon_function_type: $ => seq(
276
+ 'function',
277
+ '(',
278
+ field('params', commaSep($._type)),
279
+ ')',
280
+ optional(seq(':', field('return', $._type))),
281
+ ),
282
+
283
+ // Explicit grouping: (T|U) to override default union associativity or
284
+ // for clarity in complex expressions like ?(T|U).
285
+ parenthesized_type: $ => seq('(', $._type, ')'),
286
+
287
+ // T[] postfix array notation. Precedence 3 > nullable (2) > union (1)
288
+ // so ?T[] == ?(T[]) and T[]|U[] == (T[])|(U[]).
289
+ array_type: $ => prec(3, seq($._type, '[]')),
290
+
291
+ // Left-associative so T | U | V parses as (T | U) | V.
292
+ union_type: $ => prec.left(1, seq($._type, '|', $._type)),
293
+
294
+ // ?T is sugar for T | null; higher precedence than union so ?T | U == (?T) | U.
295
+ nullable_type: $ => prec(2, seq('?', $._type)),
296
+
297
+ // PascalCase names: typedef references and type parameters.
298
+ type_identifier: _ => /[A-Z][a-zA-Z0-9]*/,
299
+
300
+ // Lowercase-starting names: parameter names and function param names.
301
+ identifier: _ => /[a-z_$][a-zA-Z_$0-9]*/,
302
+
303
+ _text: _ => token(prec(-1, /[^*{}@\s][^*{}@\n\r]*/)),
304
+ },
305
+ });
306
+
307
+ function commaSep(rule) {
308
+ return optional(commaSep1(rule));
309
+ }
310
+
311
+ function commaSep1(rule) {
312
+ return seq(rule, repeat(seq(',', rule)));
313
+ }
@@ -0,0 +1,84 @@
1
+ ; ── Tag keywords ──────────────────────────────────────────────────────────────
2
+
3
+ (tag_name) @keyword
4
+
5
+ (param_tag "@param" @keyword)
6
+ (returns_tag ["@returns" "@return"] @keyword)
7
+ (template_tag "@template" @keyword)
8
+ (typedef_tag "@typedef" @keyword)
9
+ (type_tag "@type" @keyword)
10
+ (throws_tag ["@throws" "@throw"] @keyword)
11
+ (deprecated_tag "@deprecated" @keyword)
12
+ (since_tag "@since" @keyword)
13
+ (see_tag "@see" @keyword)
14
+ (example_tag "@example" @keyword)
15
+ (default_tag "@default" @keyword)
16
+ (function_tag "@function" @keyword)
17
+ (module_tag "@module" @keyword)
18
+
19
+ ; ── Names ──────────────────────────────────────────────────────────────────
20
+
21
+ (type_param) @type.parameter
22
+ (type_identifier) @type
23
+ (primitive_type) @type.builtin
24
+ (any_type) @type.builtin
25
+
26
+ (identifier) @variable.parameter
27
+ (record_field name: (identifier) @variable.member)
28
+ (member_name) @variable.member
29
+
30
+ (default_value) @constant
31
+
32
+ ; ── Module paths ────────────────────────────────────────────────────────────
33
+
34
+ (module_type "module:" @module)
35
+ (module_type path: (module_path) @module)
36
+ (namepath "module:" @module)
37
+ (namepath path: (module_path) @module)
38
+
39
+ ; ── Operators ───────────────────────────────────────────────────────────────
40
+
41
+ (union_type "|" @operator)
42
+ (nullable_type "?" @operator)
43
+ (function_type "=>" @operator)
44
+ (optional_param "=" @operator)
45
+
46
+ ; ── Punctuation: brackets ────────────────────────────────────────────────────
47
+
48
+ (type_expression "{" @punctuation.bracket "}" @punctuation.bracket)
49
+ (rest_type_expression "{" @punctuation.bracket "}" @punctuation.bracket)
50
+ (record_type "{" @punctuation.bracket "}" @punctuation.bracket)
51
+ (parenthesized_type "(" @punctuation.bracket ")" @punctuation.bracket)
52
+ (function_type "(" @punctuation.bracket ")" @punctuation.bracket)
53
+ (anon_function_type "(" @punctuation.bracket ")" @punctuation.bracket)
54
+ (named_type "<" @punctuation.bracket ">" @punctuation.bracket)
55
+ (list_type "<" @punctuation.bracket ">" @punctuation.bracket)
56
+ (dict_type "<" @punctuation.bracket ">" @punctuation.bracket)
57
+ (optional_param "[" @punctuation.bracket "]" @punctuation.bracket)
58
+ (array_type "[]" @punctuation.bracket)
59
+ (inline_tag "{" @punctuation.bracket "}" @punctuation.bracket)
60
+
61
+ ; ── Punctuation: delimiters ──────────────────────────────────────────────────
62
+
63
+ (record_type "," @punctuation.delimiter)
64
+ (record_field ":" @punctuation.delimiter)
65
+ (function_param ":" @punctuation.delimiter)
66
+ (anon_function_type ":" @punctuation.delimiter)
67
+ (namepath "#" @punctuation.delimiter)
68
+
69
+ ; ── Punctuation: special ─────────────────────────────────────────────────────
70
+
71
+ (rest_type_expression "..." @punctuation.special)
72
+
73
+ ; ── Descriptions ─────────────────────────────────────────────────────────────
74
+
75
+ (description) @comment
76
+
77
+ ; @spell only on prose-bearing tags; @example descriptions contain code.
78
+ (document (description) @spell)
79
+ (param_tag description: (description) @spell)
80
+ (returns_tag description: (description) @spell)
81
+ (throws_tag description: (description) @spell)
82
+ (deprecated_tag description: (description) @spell)
83
+ (since_tag description: (description) @spell)
84
+ (see_tag description: (description) @spell)
@@ -0,0 +1,22 @@
1
+ (template_tag
2
+ (type_param) @template.param)
3
+
4
+ (param_tag
5
+ type: (_)? @param.type
6
+ name: (_)? @param.name
7
+ description: (description)? @param.description)
8
+
9
+ (returns_tag
10
+ type: (type_expression) @returns.type
11
+ description: (description)? @returns.description)
12
+
13
+ (throws_tag
14
+ type: (type_expression)? @throws.type
15
+ description: (description)? @throws.description)
16
+
17
+ (typedef_tag
18
+ type: (type_expression)? @typedef.type
19
+ name: (type_identifier) @typedef.name)
20
+
21
+ (type_tag
22
+ type: (type_expression) @type.type)