@fuzdev/fuz_ui 0.204.0 → 0.205.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.
Files changed (95) hide show
  1. package/dist/ApiModule.svelte +14 -1
  2. package/dist/ApiModule.svelte.d.ts.map +1 -1
  3. package/dist/DeclarationDetail.svelte +15 -4
  4. package/dist/DeclarationDetail.svelte.d.ts.map +1 -1
  5. package/package.json +12 -36
  6. package/dist/Mdz.svelte +0 -34
  7. package/dist/Mdz.svelte.d.ts +0 -11
  8. package/dist/Mdz.svelte.d.ts.map +0 -1
  9. package/dist/MdzNodeView.svelte +0 -107
  10. package/dist/MdzNodeView.svelte.d.ts +0 -9
  11. package/dist/MdzNodeView.svelte.d.ts.map +0 -1
  12. package/dist/MdzPrecompiled.svelte +0 -30
  13. package/dist/MdzPrecompiled.svelte.d.ts +0 -11
  14. package/dist/MdzPrecompiled.svelte.d.ts.map +0 -1
  15. package/dist/MdzRoot.svelte +0 -30
  16. package/dist/MdzRoot.svelte.d.ts +0 -12
  17. package/dist/MdzRoot.svelte.d.ts.map +0 -1
  18. package/dist/MdzStream.svelte +0 -32
  19. package/dist/MdzStream.svelte.d.ts +0 -12
  20. package/dist/MdzStream.svelte.d.ts.map +0 -1
  21. package/dist/MdzStreamNodeView.svelte +0 -106
  22. package/dist/MdzStreamNodeView.svelte.d.ts +0 -9
  23. package/dist/MdzStreamNodeView.svelte.d.ts.map +0 -1
  24. package/dist/mdz.d.ts +0 -112
  25. package/dist/mdz.d.ts.map +0 -1
  26. package/dist/mdz.js +0 -1186
  27. package/dist/mdz_components.d.ts +0 -63
  28. package/dist/mdz_components.d.ts.map +0 -1
  29. package/dist/mdz_components.js +0 -32
  30. package/dist/mdz_helpers.d.ts +0 -164
  31. package/dist/mdz_helpers.d.ts.map +0 -1
  32. package/dist/mdz_helpers.js +0 -424
  33. package/dist/mdz_lexer.d.ts +0 -93
  34. package/dist/mdz_lexer.d.ts.map +0 -1
  35. package/dist/mdz_lexer.js +0 -732
  36. package/dist/mdz_opcodes.d.ts +0 -174
  37. package/dist/mdz_opcodes.d.ts.map +0 -1
  38. package/dist/mdz_opcodes.js +0 -14
  39. package/dist/mdz_opcodes_to_nodes.d.ts +0 -20
  40. package/dist/mdz_opcodes_to_nodes.d.ts.map +0 -1
  41. package/dist/mdz_opcodes_to_nodes.js +0 -332
  42. package/dist/mdz_stream_parser.d.ts +0 -80
  43. package/dist/mdz_stream_parser.d.ts.map +0 -1
  44. package/dist/mdz_stream_parser.js +0 -354
  45. package/dist/mdz_stream_parser_block.d.ts +0 -76
  46. package/dist/mdz_stream_parser_block.d.ts.map +0 -1
  47. package/dist/mdz_stream_parser_block.js +0 -458
  48. package/dist/mdz_stream_parser_inline.d.ts +0 -52
  49. package/dist/mdz_stream_parser_inline.d.ts.map +0 -1
  50. package/dist/mdz_stream_parser_inline.js +0 -378
  51. package/dist/mdz_stream_parser_link.d.ts +0 -22
  52. package/dist/mdz_stream_parser_link.d.ts.map +0 -1
  53. package/dist/mdz_stream_parser_link.js +0 -215
  54. package/dist/mdz_stream_parser_state.d.ts +0 -187
  55. package/dist/mdz_stream_parser_state.d.ts.map +0 -1
  56. package/dist/mdz_stream_parser_state.js +0 -398
  57. package/dist/mdz_stream_parser_text.d.ts +0 -14
  58. package/dist/mdz_stream_parser_text.d.ts.map +0 -1
  59. package/dist/mdz_stream_parser_text.js +0 -50
  60. package/dist/mdz_stream_parser_url.d.ts +0 -60
  61. package/dist/mdz_stream_parser_url.d.ts.map +0 -1
  62. package/dist/mdz_stream_parser_url.js +0 -307
  63. package/dist/mdz_stream_state.svelte.d.ts +0 -44
  64. package/dist/mdz_stream_state.svelte.d.ts.map +0 -1
  65. package/dist/mdz_stream_state.svelte.js +0 -357
  66. package/dist/mdz_to_svelte.d.ts +0 -41
  67. package/dist/mdz_to_svelte.d.ts.map +0 -1
  68. package/dist/mdz_to_svelte.js +0 -100
  69. package/dist/mdz_token_parser.d.ts +0 -14
  70. package/dist/mdz_token_parser.d.ts.map +0 -1
  71. package/dist/mdz_token_parser.js +0 -344
  72. package/dist/svelte_preprocess_mdz.d.ts +0 -65
  73. package/dist/svelte_preprocess_mdz.d.ts.map +0 -1
  74. package/dist/svelte_preprocess_mdz.js +0 -529
  75. package/dist/tsdoc_mdz.d.ts +0 -45
  76. package/dist/tsdoc_mdz.d.ts.map +0 -1
  77. package/dist/tsdoc_mdz.js +0 -88
  78. package/src/lib/mdz.ts +0 -1532
  79. package/src/lib/mdz_components.ts +0 -64
  80. package/src/lib/mdz_helpers.ts +0 -449
  81. package/src/lib/mdz_lexer.ts +0 -1012
  82. package/src/lib/mdz_opcodes.ts +0 -205
  83. package/src/lib/mdz_opcodes_to_nodes.ts +0 -375
  84. package/src/lib/mdz_stream_parser.ts +0 -415
  85. package/src/lib/mdz_stream_parser_block.ts +0 -532
  86. package/src/lib/mdz_stream_parser_inline.ts +0 -414
  87. package/src/lib/mdz_stream_parser_link.ts +0 -271
  88. package/src/lib/mdz_stream_parser_state.ts +0 -539
  89. package/src/lib/mdz_stream_parser_text.ts +0 -77
  90. package/src/lib/mdz_stream_parser_url.ts +0 -365
  91. package/src/lib/mdz_stream_state.svelte.ts +0 -387
  92. package/src/lib/mdz_to_svelte.ts +0 -141
  93. package/src/lib/mdz_token_parser.ts +0 -434
  94. package/src/lib/svelte_preprocess_mdz.ts +0 -742
  95. package/src/lib/tsdoc_mdz.ts +0 -97
@@ -1,365 +0,0 @@
1
- /**
2
- * Auto-URL and auto-path handlers (text-first scanning) for the streaming
3
- * mdz parser. Operates in two phases:
4
- *
5
- * 1. Speculative prefix matching: chars stream as visible text while we
6
- * verify a `https://` / `http://` prefix.
7
- * 2. Confirmed mode: chars stream as text and on terminator a `wrap`
8
- * opcode retroactively wraps the text node in a Link.
9
- *
10
- * Paths (`/...`, `./...`, `../...`) skip phase 1 — their prefix is validated
11
- * by hold (require enough lookahead).
12
- *
13
- * @module
14
- */
15
-
16
- import {
17
- NEWLINE,
18
- SPACE,
19
- TAB,
20
- PERIOD,
21
- SLASH,
22
- ascii_to_lower,
23
- is_valid_path_char,
24
- is_word_char,
25
- match_url_prefix_case_insensitive,
26
- trim_trailing_punctuation,
27
- } from './mdz_helpers.js';
28
- import {
29
- type MdzStreamParserState,
30
- type TryResult,
31
- accumulate_text,
32
- alloc_id,
33
- emit,
34
- ensure_paragraph,
35
- flush_text,
36
- offset,
37
- } from './mdz_stream_parser_state.js';
38
-
39
- const HTTPS_PREFIX = 'https://';
40
- const HTTP_PREFIX = 'http://';
41
-
42
- /**
43
- * Forced-mode URL detection: the full prefix must be in the buffer.
44
- * Used at EOF when speculative prefix matching isn't needed.
45
- * Scheme match is case-insensitive (RFC 3986).
46
- */
47
- export const try_auto_url_forced = (state: MdzStreamParserState): TryResult => {
48
- if (state.prev_char !== -1 && is_word_char(state.prev_char)) return 'not_match';
49
-
50
- const prefix_len = match_url_prefix_case_insensitive(state.buffer, state.pos);
51
- if (prefix_len === 0) return 'not_match';
52
-
53
- // must have content after protocol
54
- if (state.pos + prefix_len >= state.buffer.length) return 'not_match';
55
- const after = state.buffer.charCodeAt(state.pos + prefix_len);
56
- if (after === SPACE || after === NEWLINE) return 'not_match';
57
-
58
- return scan_auto_link_forced(state, 'external');
59
- };
60
-
61
- export const try_auto_path_absolute = (state: MdzStreamParserState, forced = false): TryResult => {
62
- // must be at word boundary (preceded by space/newline/start)
63
- if (
64
- state.prev_char !== -1 &&
65
- state.prev_char !== SPACE &&
66
- state.prev_char !== NEWLINE &&
67
- state.prev_char !== TAB
68
- ) {
69
- return 'not_match';
70
- }
71
-
72
- // reject // and /space
73
- if (state.pos + 1 >= state.buffer.length) return forced ? 'not_match' : 'need_more';
74
- const next = state.buffer.charCodeAt(state.pos + 1);
75
- if (next === SLASH || next === SPACE || next === NEWLINE || next === TAB) {
76
- return 'not_match';
77
- }
78
-
79
- if (forced) return scan_auto_link_forced(state, 'internal');
80
- start_pending_url(state, 'internal');
81
- return 'consumed';
82
- };
83
-
84
- export const try_auto_path_relative = (state: MdzStreamParserState, forced = false): TryResult => {
85
- if (
86
- state.prev_char !== -1 &&
87
- state.prev_char !== SPACE &&
88
- state.prev_char !== NEWLINE &&
89
- state.prev_char !== TAB
90
- ) {
91
- return 'not_match';
92
- }
93
-
94
- // check for ./ or ../
95
- const remaining = state.buffer.length - state.pos;
96
- if (remaining < 3) return forced ? 'not_match' : 'need_more';
97
-
98
- if (
99
- state.buffer.charCodeAt(state.pos + 1) === PERIOD &&
100
- state.buffer.charCodeAt(state.pos + 2) === SLASH
101
- ) {
102
- // ../
103
- if (remaining < 4) return forced ? 'not_match' : 'need_more';
104
- const after = state.buffer.charCodeAt(state.pos + 3);
105
- if (after === SPACE || after === NEWLINE || after === TAB || after === SLASH) {
106
- return 'not_match';
107
- }
108
- if (forced) return scan_auto_link_forced(state, 'internal');
109
- start_pending_url(state, 'internal');
110
- return 'consumed';
111
- }
112
-
113
- if (state.buffer.charCodeAt(state.pos + 1) === SLASH) {
114
- // ./
115
- const after = state.buffer.charCodeAt(state.pos + 2);
116
- if (after === SPACE || after === NEWLINE || after === TAB || after === SLASH) {
117
- return 'not_match';
118
- }
119
- if (forced) return scan_auto_link_forced(state, 'internal');
120
- start_pending_url(state, 'internal');
121
- return 'consumed';
122
- }
123
-
124
- return 'not_match';
125
- };
126
-
127
- /**
128
- * Start confirmed text-first mode for paths. Prefix already validated by hold.
129
- * Flushes prior text, resets active_text_id, sets pending_url with confirmed=true.
130
- */
131
- export const start_pending_url = (
132
- state: MdzStreamParserState,
133
- link_type: 'external' | 'internal',
134
- ): void => {
135
- flush_text(state);
136
- ensure_paragraph(state);
137
- state.active_text_id = null;
138
- state.pending_url = {
139
- url_text: '',
140
- start: offset(state),
141
- link_type,
142
- confirmed: true,
143
- viable_https: false,
144
- viable_http: false,
145
- };
146
- // don't advance pos — URL chars start at current position, handled by process_url_content
147
- };
148
-
149
- /**
150
- * Start speculative text-first mode for URL prefixes.
151
- * Chars stream as visible text while we verify `https://` or `http://`.
152
- * Cancels if prefix doesn't match (text stays as plain text).
153
- */
154
- export const start_speculative_url = (state: MdzStreamParserState): void => {
155
- flush_text(state);
156
- ensure_paragraph(state);
157
- state.active_text_id = null;
158
- state.pending_url = {
159
- url_text: '',
160
- start: offset(state),
161
- link_type: 'external',
162
- confirmed: false,
163
- viable_https: true,
164
- viable_http: true,
165
- };
166
- };
167
-
168
- /**
169
- * Speculative URL prefix matching. Checks each char against viable prefixes,
170
- * streaming as text. Confirms on full match, cancels on mismatch.
171
- *
172
- * Scheme letters (`h`, `t`, `p`, `s`) are matched case-insensitively (RFC 3986);
173
- * the `:` and `//` portion remains literal. Original casing is preserved in
174
- * the emitted reference.
175
- */
176
- export const process_url_prefix = (state: MdzStreamParserState): void => {
177
- const pu = state.pending_url!;
178
- const char_code = state.buffer.charCodeAt(state.pos);
179
- const pos = pu.url_text.length;
180
-
181
- // scheme letters (positions 0-4) match case-insensitively;
182
- // `:` and `/` (positions 5-7 for https, 4-6 for http) are literal.
183
- const cmp_code = pos < 5 ? ascii_to_lower(char_code) : char_code;
184
-
185
- // narrow viable prefixes
186
- if (
187
- pu.viable_https &&
188
- (pos >= HTTPS_PREFIX.length || cmp_code !== HTTPS_PREFIX.charCodeAt(pos))
189
- ) {
190
- pu.viable_https = false;
191
- }
192
- if (pu.viable_http && (pos >= HTTP_PREFIX.length || cmp_code !== HTTP_PREFIX.charCodeAt(pos))) {
193
- pu.viable_http = false;
194
- }
195
-
196
- if (!pu.viable_https && !pu.viable_http) {
197
- // no viable prefix — cancel speculation, don't consume char
198
- state.pending_url = null;
199
- return;
200
- }
201
-
202
- // char matches — accumulate as text
203
- accumulate_text(state, state.buffer[state.pos]!, offset(state));
204
- pu.url_text += state.buffer[state.pos];
205
- state.pos++;
206
- state.column++;
207
- state.prev_char = char_code;
208
-
209
- // check if a prefix is fully confirmed
210
- if (
211
- (pu.viable_https && pos + 1 === HTTPS_PREFIX.length) ||
212
- (pu.viable_http && pos + 1 === HTTP_PREFIX.length)
213
- ) {
214
- pu.confirmed = true;
215
- }
216
- };
217
-
218
- /**
219
- * Process URL/path chars in text-first mode. Scans path chars,
220
- * accumulates as visible text. Terminates on space/newline/non-path-char
221
- * and emits a `wrap` opcode.
222
- */
223
- export const process_url_content = (state: MdzStreamParserState, forced: boolean): void => {
224
- // speculative prefix matching phase
225
- if (!state.pending_url!.confirmed) {
226
- process_url_prefix(state);
227
- return;
228
- }
229
-
230
- const char_code = state.buffer.charCodeAt(state.pos);
231
-
232
- // URL terminator
233
- if (char_code === SPACE || char_code === NEWLINE || !is_valid_path_char(char_code)) {
234
- flush_text(state);
235
- complete_pending_url(state);
236
- // don't consume terminator — outer loop handles it
237
- return;
238
- }
239
-
240
- // scan URL chars
241
- const start = state.pos;
242
- state.pos++;
243
- while (state.pos < state.buffer.length) {
244
- const c = state.buffer.charCodeAt(state.pos);
245
- if (c === SPACE || c === NEWLINE || !is_valid_path_char(c)) break;
246
- state.pos++;
247
- }
248
- const text = state.buffer.slice(start, state.pos);
249
- accumulate_text(state, text, offset(state, start));
250
- state.pending_url!.url_text += text;
251
- state.prev_char = state.buffer.charCodeAt(state.pos - 1);
252
- state.column += state.pos - start;
253
-
254
- // at EOF in forced mode, finalize the URL
255
- if (state.pos >= state.buffer.length && forced) {
256
- flush_text(state);
257
- complete_pending_url(state);
258
- }
259
- };
260
-
261
- /**
262
- * Complete a pending URL: compute reference with trimmed punctuation,
263
- * emit a `wrap` opcode to retroactively wrap the text node in a Link.
264
- */
265
- export const complete_pending_url = (state: MdzStreamParserState): void => {
266
- const pu = state.pending_url!;
267
- state.pending_url = null;
268
-
269
- const reference = trim_trailing_punctuation(pu.url_text);
270
- if (reference.length === 0) return; // empty after trimming — text stays as plain text
271
-
272
- // for external URLs, must have content after protocol prefix
273
- if (pu.link_type === 'external') {
274
- const prefix_len = match_url_prefix_case_insensitive(reference, 0);
275
- if (reference.length < prefix_len + 1) return; // just protocol, no content
276
- }
277
-
278
- const text_id = state.active_text_id;
279
- if (text_id === null) return; // no text node to wrap (shouldn't happen)
280
-
281
- const trim_end = pu.url_text.length - reference.length;
282
- const wrap_id = alloc_id(state);
283
- const url_end = pu.start + reference.length;
284
-
285
- if (trim_end > 0) {
286
- const trim_id = alloc_id(state);
287
- emit(state, {
288
- type: 'wrap',
289
- id: wrap_id,
290
- node_type: 'Link',
291
- target_id: text_id,
292
- reference,
293
- link_type: pu.link_type,
294
- start: pu.start,
295
- end: url_end,
296
- trim_end,
297
- trim_id,
298
- });
299
- state.active_text_id = trim_id;
300
- } else {
301
- emit(state, {
302
- type: 'wrap',
303
- id: wrap_id,
304
- node_type: 'Link',
305
- target_id: text_id,
306
- reference,
307
- link_type: pu.link_type,
308
- start: pu.start,
309
- end: url_end,
310
- });
311
- state.active_text_id = null;
312
- }
313
- };
314
-
315
- /**
316
- * Forced-mode auto-link: scan the full URL/path inline (no streaming needed
317
- * at EOF). Used when forced=true — the entire URL must be in the buffer.
318
- */
319
- export const scan_auto_link_forced = (
320
- state: MdzStreamParserState,
321
- link_type: 'external' | 'internal',
322
- ): TryResult => {
323
- let i = state.pos;
324
- while (i < state.buffer.length) {
325
- const c = state.buffer.charCodeAt(i);
326
- if (c === SPACE || c === NEWLINE || !is_valid_path_char(c)) break;
327
- i++;
328
- }
329
-
330
- let reference = state.buffer.slice(state.pos, i);
331
- reference = trim_trailing_punctuation(reference);
332
- if (reference.length === 0) return 'not_match';
333
-
334
- // for external URLs, must have content after protocol prefix
335
- if (link_type === 'external') {
336
- const prefix_len = match_url_prefix_case_insensitive(reference, 0);
337
- if (reference.length < prefix_len + 1) return 'not_match';
338
- }
339
-
340
- const end_pos = state.pos + reference.length;
341
- const link_start = offset(state);
342
- const link_end = offset(state, end_pos);
343
-
344
- flush_text(state);
345
- ensure_paragraph(state);
346
-
347
- const link_id = alloc_id(state);
348
- emit(state, {type: 'open', id: link_id, node_type: 'Link', start: link_start});
349
- const text_id = alloc_id(state);
350
- emit(state, {
351
- type: 'text',
352
- id: text_id,
353
- content: reference,
354
- text_type: 'Text',
355
- start: link_start,
356
- end: link_end,
357
- });
358
- emit(state, {type: 'close', id: link_id, end: link_end, reference, link_type});
359
-
360
- state.active_text_id = null;
361
- state.column += end_pos - state.pos;
362
- state.prev_char = reference.charCodeAt(reference.length - 1);
363
- state.pos = end_pos;
364
- return 'consumed';
365
- };