@hyperfixi/vite-plugin 2.0.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.
@@ -0,0 +1,404 @@
1
+ import { Plugin } from 'vite';
2
+ import { ASTNode } from '@hyperfixi/core/parser/hybrid/ast-types';
3
+
4
+ /**
5
+ * Vite Plugin Types
6
+ *
7
+ * Type definitions for the HyperFixi Vite plugin.
8
+ */
9
+ /**
10
+ * Options for the HyperFixi Vite plugin
11
+ */
12
+ interface HyperfixiPluginOptions {
13
+ /**
14
+ * Bundle generation mode:
15
+ * - 'interpret': Generate minimal bundle with parser (default, ~8KB gzip)
16
+ * - 'compile': Pre-compile hyperscript to JS at build time (~500 bytes gzip)
17
+ *
18
+ * Compile mode limitations:
19
+ * - No dynamic hyperscript (runtime execute() won't work)
20
+ * - No block commands (if, for, repeat, while, fetch)
21
+ * - HTML must be transformed to use data-h attributes
22
+ *
23
+ * Use compile mode when:
24
+ * - Bundle size is critical (<1KB target)
25
+ * - All hyperscript is static (no dynamic generation)
26
+ * - Only simple commands are used (toggle, add, remove, set, etc.)
27
+ */
28
+ mode?: 'interpret' | 'compile';
29
+ /**
30
+ * File patterns to scan for hyperscript usage.
31
+ * Defaults to common web file extensions.
32
+ */
33
+ include?: RegExp | string[];
34
+ /**
35
+ * File patterns to exclude from scanning.
36
+ * Defaults to node_modules.
37
+ */
38
+ exclude?: RegExp | string[];
39
+ /**
40
+ * Extra commands to always include in the bundle.
41
+ * Use this for dynamically generated hyperscript that can't be detected.
42
+ */
43
+ extraCommands?: string[];
44
+ /**
45
+ * Extra blocks to always include in the bundle.
46
+ */
47
+ extraBlocks?: string[];
48
+ /**
49
+ * Always include positional expressions (first, last, next, closest, parent).
50
+ * Set to true if your dynamic code uses these.
51
+ */
52
+ positional?: boolean;
53
+ /**
54
+ * Enable HTMX integration (auto-process after htmx:afterSettle).
55
+ */
56
+ htmx?: boolean;
57
+ /**
58
+ * Development mode fallback strategy.
59
+ * - 'hybrid-complete': Use pre-built hybrid-complete bundle for faster dev (default)
60
+ * - 'full': Use full bundle for complete compatibility
61
+ * - 'auto': Generate minimal bundle even in dev
62
+ */
63
+ devFallback?: 'hybrid-complete' | 'full' | 'auto';
64
+ /**
65
+ * Global variable name for the hyperfixi API.
66
+ * Defaults to 'hyperfixi'.
67
+ */
68
+ globalName?: string;
69
+ /**
70
+ * Bundle name for generated code comments.
71
+ * Defaults to 'ViteAutoGenerated'.
72
+ */
73
+ bundleName?: string;
74
+ /**
75
+ * Enable verbose logging during development.
76
+ */
77
+ debug?: boolean;
78
+ /**
79
+ * Enable semantic parsing for multilingual support.
80
+ * - false: No semantic parsing (default, current behavior)
81
+ * - true: Auto-detect languages from templates
82
+ * - 'en': English semantic only (synonyms, flexible syntax)
83
+ * - 'auto': Same as true
84
+ */
85
+ semantic?: boolean | 'en' | 'auto';
86
+ /**
87
+ * Explicit language list (overrides auto-detection).
88
+ * Use ISO 639-1 codes: 'en', 'es', 'ja', 'ko', 'zh', 'ar', etc.
89
+ */
90
+ languages?: string[];
91
+ /**
92
+ * Regional bundle shorthand (alternative to explicit languages).
93
+ * - 'western': en, es, pt, fr, de, it
94
+ * - 'east-asian': ja, zh, ko
95
+ * - 'slavic': pl, ru, uk
96
+ * - 'south-asian': hi, bn
97
+ * - 'priority': 13 most common languages
98
+ * - 'all': All 21 supported languages
99
+ */
100
+ region?: 'western' | 'east-asian' | 'slavic' | 'south-asian' | 'priority' | 'all';
101
+ /**
102
+ * Enable grammar transformation for native word order.
103
+ * When true, semantic is automatically enabled.
104
+ * Adds support for SOV (Japanese, Korean) and VSO (Arabic) word orders.
105
+ */
106
+ grammar?: boolean;
107
+ /**
108
+ * Always include these languages in addition to detected ones.
109
+ * Useful for dynamic content not detectable at build time.
110
+ */
111
+ extraLanguages?: string[];
112
+ /**
113
+ * Custom language keyword definitions.
114
+ * Use this to add new languages or extend/override existing keyword detection.
115
+ *
116
+ * @example
117
+ * ```typescript
118
+ * hyperfixi({
119
+ * customKeywords: {
120
+ * // Add a new language
121
+ * 'my-lang': {
122
+ * keywords: new Set(['mytoggle', 'myadd', 'myremove']),
123
+ * isNonLatin: false,
124
+ * },
125
+ * // Extend an existing language with additional keywords
126
+ * 'es': {
127
+ * keywords: new Set(['conmutar', 'intercambiar']), // Additional Spanish keywords
128
+ * extend: true, // Merge with existing keywords
129
+ * },
130
+ * },
131
+ * })
132
+ * ```
133
+ */
134
+ customKeywords?: Record<string, CustomLanguageKeywords>;
135
+ }
136
+ /**
137
+ * Custom language keyword configuration.
138
+ */
139
+ interface CustomLanguageKeywords {
140
+ /**
141
+ * Set of keywords for this language.
142
+ */
143
+ keywords: Set<string>;
144
+ /**
145
+ * Whether this language uses non-Latin script.
146
+ * Non-Latin scripts use simple substring matching (no word boundaries).
147
+ * Latin scripts use word boundary matching to avoid false positives.
148
+ */
149
+ isNonLatin?: boolean;
150
+ /**
151
+ * If true, merge these keywords with existing ones for this language.
152
+ * If false (default), replace existing keywords entirely.
153
+ */
154
+ extend?: boolean;
155
+ }
156
+ /**
157
+ * HTMX/Fixi attribute usage information
158
+ */
159
+ interface HtmxUsage {
160
+ /** Whether any htmx attributes were found */
161
+ hasHtmxAttributes: boolean;
162
+ /** Whether any fixi-specific attributes were found (fx-action, etc.) */
163
+ hasFixiAttributes: boolean;
164
+ /** HTTP methods used (GET, POST, PUT, PATCH, DELETE) */
165
+ httpMethods: Set<string>;
166
+ /** Swap strategies used (innerHTML, morph, delete, beforeend, etc.) */
167
+ swapStrategies: Set<string>;
168
+ /** hx-on:* handler values (raw hyperscript) */
169
+ onHandlers: string[];
170
+ /** Trigger modifiers detected (debounce, throttle, once) */
171
+ triggerModifiers: Set<string>;
172
+ /** URL management strategies (push-url, replace-url) */
173
+ urlManagement: Set<string>;
174
+ /** Whether hx-confirm is used */
175
+ usesConfirm: boolean;
176
+ }
177
+ /**
178
+ * Usage information detected from a single file
179
+ */
180
+ interface FileUsage {
181
+ /** Commands used in this file */
182
+ commands: Set<string>;
183
+ /** Block types used (if, repeat, for, while, fetch) */
184
+ blocks: Set<string>;
185
+ /** Whether positional expressions are used */
186
+ positional: boolean;
187
+ /** Non-English languages detected in hyperscript (ISO 639-1 codes) */
188
+ detectedLanguages: Set<string>;
189
+ /** HTMX/Fixi attribute usage (if detected) */
190
+ htmx?: HtmxUsage;
191
+ }
192
+ /**
193
+ * Aggregated usage information across all files
194
+ */
195
+ interface AggregatedUsage {
196
+ /** All commands detected across all files */
197
+ commands: Set<string>;
198
+ /** All blocks detected across all files */
199
+ blocks: Set<string>;
200
+ /** Whether any file uses positional expressions */
201
+ positional: boolean;
202
+ /** All non-English languages detected across all files */
203
+ detectedLanguages: Set<string>;
204
+ /** Aggregated HTMX/Fixi usage across all files */
205
+ htmx: HtmxUsage;
206
+ /** Map of file paths to their usage */
207
+ fileUsage: Map<string, FileUsage>;
208
+ }
209
+
210
+ /**
211
+ * Compiler
212
+ *
213
+ * Compiles hyperscript AST to JavaScript at build time.
214
+ * Eliminates the need for runtime parsing.
215
+ *
216
+ * Multilingual support:
217
+ * - For English: Uses HybridParser directly
218
+ * - For other languages: Uses semantic parser to translate → AST → JavaScript
219
+ * - Semantic parsing happens at BUILD time (zero runtime overhead)
220
+ */
221
+
222
+ /**
223
+ * Semantic analyzer interface for multilingual support.
224
+ * This matches the interface from @lokascript/semantic.
225
+ */
226
+ interface SemanticAnalysisResult {
227
+ confidence: number;
228
+ node?: unknown;
229
+ errors?: string[];
230
+ }
231
+ interface SemanticAnalyzer {
232
+ analyze(input: string, language: string): SemanticAnalysisResult;
233
+ supportsLanguage(language: string): boolean;
234
+ }
235
+ type BuildASTFn = (node: unknown) => {
236
+ ast: ASTNode;
237
+ warnings: string[];
238
+ };
239
+ /**
240
+ * Configure the semantic parser for multilingual compilation.
241
+ * Call this with the semantic analyzer from @lokascript/semantic.
242
+ *
243
+ * @example
244
+ * ```typescript
245
+ * import { createSemanticAnalyzer, buildAST } from '@lokascript/semantic';
246
+ * import { setSemanticParser } from '@hyperfixi/vite-plugin';
247
+ *
248
+ * setSemanticParser(createSemanticAnalyzer(), buildAST);
249
+ * ```
250
+ */
251
+ declare function setSemanticParser(analyzer: SemanticAnalyzer, buildAST: BuildASTFn): void;
252
+ /**
253
+ * Clear the semantic parser (for testing).
254
+ */
255
+ declare function clearSemanticParser(): void;
256
+ /**
257
+ * Check if semantic parser is available.
258
+ */
259
+ declare function hasSemanticParser(): boolean;
260
+ interface CompiledHandler {
261
+ /** Unique handler ID (h0, h1, etc.) */
262
+ id: string;
263
+ /** Event name (click, input, etc.) */
264
+ event: string;
265
+ /** Event modifiers */
266
+ modifiers: {
267
+ prevent?: boolean;
268
+ stop?: boolean;
269
+ once?: boolean;
270
+ debounce?: number;
271
+ throttle?: number;
272
+ };
273
+ /** Compiled JavaScript code */
274
+ code: string;
275
+ /** Whether handler needs the mini-evaluator for dynamic expressions */
276
+ needsEvaluator: boolean;
277
+ /** Original hyperscript for debugging */
278
+ original: string;
279
+ }
280
+ /**
281
+ * Compile options for multilingual support.
282
+ */
283
+ interface CompileOptions {
284
+ /** Language code (ISO 639-1). Defaults to 'en'. */
285
+ language?: string;
286
+ /** Enable debug logging. */
287
+ debug?: boolean;
288
+ }
289
+
290
+ /**
291
+ * Language Keywords for Detection
292
+ *
293
+ * Maps of keywords for each of the 21 supported languages.
294
+ * Used by the scanner to detect which languages are used in hyperscript templates.
295
+ *
296
+ * Note: These are a representative subset of keywords - enough to reliably
297
+ * detect language usage without including every possible keyword variant.
298
+ */
299
+
300
+ /**
301
+ * All supported language codes.
302
+ */
303
+ declare const SUPPORTED_LANGUAGES: readonly ["en", "es", "pt", "fr", "de", "it", "vi", "pl", "ru", "uk", "ja", "zh", "ko", "ar", "hi", "bn", "th", "tr", "id", "sw", "qu", "tl"];
304
+ type SupportedLanguage = (typeof SUPPORTED_LANGUAGES)[number];
305
+ /**
306
+ * Regional bundle mappings.
307
+ */
308
+ declare const REGIONS: {
309
+ western: SupportedLanguage[];
310
+ 'east-asian': SupportedLanguage[];
311
+ slavic: SupportedLanguage[];
312
+ 'south-asian': SupportedLanguage[];
313
+ priority: SupportedLanguage[];
314
+ all: SupportedLanguage[];
315
+ };
316
+ /**
317
+ * Detect all languages used in a hyperscript string.
318
+ * Returns a Set of language codes found.
319
+ *
320
+ * Note: English is never detected (it's the default).
321
+ * Only non-English languages are detected.
322
+ */
323
+ declare function detectLanguages(script: string): Set<SupportedLanguage>;
324
+ /**
325
+ * Register custom keywords for a language.
326
+ * Call this before scanning to add or extend language detection.
327
+ *
328
+ * @param code - Language code (e.g., 'es', 'my-lang')
329
+ * @param config - Keyword configuration
330
+ */
331
+ declare function registerCustomKeywords(code: string, config: CustomLanguageKeywords): void;
332
+ /**
333
+ * Get keywords for a language, including custom registrations.
334
+ */
335
+ declare function getKeywordsForLanguage(code: string): Set<string> | undefined;
336
+ /**
337
+ * Check if a language uses non-Latin script.
338
+ */
339
+ declare function isNonLatinLanguage(code: string): boolean;
340
+ /**
341
+ * Get all registered language codes (built-in + custom).
342
+ */
343
+ declare function getAllLanguageCodes(): string[];
344
+ /**
345
+ * Clear all custom keyword registrations.
346
+ */
347
+ declare function clearCustomKeywords(): void;
348
+ /**
349
+ * Get the optimal regional bundle for a set of detected languages.
350
+ * Returns the smallest bundle that covers all detected languages.
351
+ */
352
+ declare function getOptimalRegion(languages: Set<SupportedLanguage>): 'western' | 'east-asian' | 'slavic' | 'south-asian' | 'priority' | 'all' | null;
353
+
354
+ /**
355
+ * @hyperfixi/vite-plugin
356
+ *
357
+ * Zero-config Vite plugin that automatically generates minimal HyperFixi bundles
358
+ * based on detected hyperscript usage in your source files.
359
+ *
360
+ * @example
361
+ * ```javascript
362
+ * // vite.config.js
363
+ * import { hyperfixi } from '@hyperfixi/vite-plugin';
364
+ *
365
+ * export default {
366
+ * plugins: [hyperfixi()]
367
+ * };
368
+ * ```
369
+ *
370
+ * The plugin automatically:
371
+ * - Scans HTML, Vue, Svelte, JSX/TSX files for `_="..."` attributes
372
+ * - Detects which commands, blocks, and expressions are used
373
+ * - Generates a minimal bundle with only needed features
374
+ * - Re-generates on file changes (HMR)
375
+ *
376
+ * @example
377
+ * ```javascript
378
+ * // With options
379
+ * hyperfixi({
380
+ * extraCommands: ['fetch', 'put'], // Always include these commands
381
+ * htmx: true, // Enable htmx integration
382
+ * debug: true, // Enable verbose logging
383
+ * })
384
+ * ```
385
+ *
386
+ * @example
387
+ * ```javascript
388
+ * // Compile mode for smallest bundles (~500 bytes)
389
+ * hyperfixi({
390
+ * mode: 'compile', // Pre-compile hyperscript to JS
391
+ * debug: true,
392
+ * })
393
+ * ```
394
+ */
395
+
396
+ /**
397
+ * Create the HyperFixi Vite plugin
398
+ *
399
+ * @param options Plugin options
400
+ * @returns Vite plugin
401
+ */
402
+ declare function hyperfixi(options?: HyperfixiPluginOptions): Plugin;
403
+
404
+ export { type AggregatedUsage, type CompileOptions, type CompiledHandler, type CustomLanguageKeywords, type FileUsage, type HyperfixiPluginOptions, REGIONS, SUPPORTED_LANGUAGES, type SupportedLanguage, clearCustomKeywords, clearSemanticParser, hyperfixi as default, detectLanguages, getAllLanguageCodes, getKeywordsForLanguage, getOptimalRegion, hasSemanticParser, hyperfixi, isNonLatinLanguage, registerCustomKeywords, setSemanticParser };