tjs-lang 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.
Files changed (91) hide show
  1. package/CONTEXT.md +594 -0
  2. package/LICENSE +190 -0
  3. package/README.md +220 -0
  4. package/bin/benchmarks.ts +351 -0
  5. package/bin/dev.ts +205 -0
  6. package/bin/docs.js +170 -0
  7. package/bin/install-cursor.sh +71 -0
  8. package/bin/install-vscode.sh +71 -0
  9. package/bin/select-local-models.d.ts +1 -0
  10. package/bin/select-local-models.js +28 -0
  11. package/bin/select-local-models.ts +31 -0
  12. package/demo/autocomplete.test.ts +232 -0
  13. package/demo/docs.json +186 -0
  14. package/demo/examples.test.ts +598 -0
  15. package/demo/index.html +91 -0
  16. package/demo/src/autocomplete.ts +482 -0
  17. package/demo/src/capabilities.ts +859 -0
  18. package/demo/src/demo-nav.ts +2097 -0
  19. package/demo/src/examples.test.ts +161 -0
  20. package/demo/src/examples.ts +476 -0
  21. package/demo/src/imports.test.ts +196 -0
  22. package/demo/src/imports.ts +421 -0
  23. package/demo/src/index.ts +639 -0
  24. package/demo/src/module-store.ts +635 -0
  25. package/demo/src/module-sw.ts +132 -0
  26. package/demo/src/playground.ts +949 -0
  27. package/demo/src/service-host.ts +389 -0
  28. package/demo/src/settings.ts +440 -0
  29. package/demo/src/style.ts +280 -0
  30. package/demo/src/tjs-playground.ts +1605 -0
  31. package/demo/src/ts-examples.ts +478 -0
  32. package/demo/src/ts-playground.ts +1092 -0
  33. package/demo/static/favicon.svg +30 -0
  34. package/demo/static/photo-1.jpg +0 -0
  35. package/demo/static/photo-2.jpg +0 -0
  36. package/demo/static/texts/ai-history.txt +9 -0
  37. package/demo/static/texts/coffee-origins.txt +9 -0
  38. package/demo/static/texts/renewable-energy.txt +9 -0
  39. package/dist/index.js +256 -0
  40. package/dist/index.js.map +37 -0
  41. package/dist/tjs-batteries.js +4 -0
  42. package/dist/tjs-batteries.js.map +15 -0
  43. package/dist/tjs-full.js +256 -0
  44. package/dist/tjs-full.js.map +37 -0
  45. package/dist/tjs-transpiler.js +220 -0
  46. package/dist/tjs-transpiler.js.map +21 -0
  47. package/dist/tjs-vm.js +4 -0
  48. package/dist/tjs-vm.js.map +14 -0
  49. package/docs/CNAME +1 -0
  50. package/docs/favicon.svg +30 -0
  51. package/docs/index.html +91 -0
  52. package/docs/index.js +10468 -0
  53. package/docs/index.js.map +92 -0
  54. package/docs/photo-1.jpg +0 -0
  55. package/docs/photo-1.webp +0 -0
  56. package/docs/photo-2.jpg +0 -0
  57. package/docs/photo-2.webp +0 -0
  58. package/docs/texts/ai-history.txt +9 -0
  59. package/docs/texts/coffee-origins.txt +9 -0
  60. package/docs/texts/renewable-energy.txt +9 -0
  61. package/docs/tjs-lang.svg +31 -0
  62. package/docs/tosijs-agent.svg +31 -0
  63. package/editors/README.md +325 -0
  64. package/editors/ace/ajs-mode.js +328 -0
  65. package/editors/ace/ajs-mode.ts +269 -0
  66. package/editors/ajs-syntax.ts +212 -0
  67. package/editors/build-grammars.ts +510 -0
  68. package/editors/codemirror/ajs-language.js +287 -0
  69. package/editors/codemirror/ajs-language.ts +1447 -0
  70. package/editors/codemirror/autocomplete.test.ts +531 -0
  71. package/editors/codemirror/component.ts +404 -0
  72. package/editors/monaco/ajs-monarch.js +243 -0
  73. package/editors/monaco/ajs-monarch.ts +225 -0
  74. package/editors/tjs-syntax.ts +115 -0
  75. package/editors/vscode/language-configuration.json +37 -0
  76. package/editors/vscode/package.json +65 -0
  77. package/editors/vscode/syntaxes/ajs-injection.tmLanguage.json +107 -0
  78. package/editors/vscode/syntaxes/ajs.tmLanguage.json +252 -0
  79. package/editors/vscode/syntaxes/tjs.tmLanguage.json +333 -0
  80. package/package.json +83 -0
  81. package/src/cli/commands/check.ts +41 -0
  82. package/src/cli/commands/convert.ts +133 -0
  83. package/src/cli/commands/emit.ts +260 -0
  84. package/src/cli/commands/run.ts +68 -0
  85. package/src/cli/commands/test.ts +194 -0
  86. package/src/cli/commands/types.ts +20 -0
  87. package/src/cli/create-app.ts +236 -0
  88. package/src/cli/playground.ts +250 -0
  89. package/src/cli/tjs.ts +166 -0
  90. package/src/cli/tjsx.ts +160 -0
  91. package/tjs-lang.svg +31 -0
@@ -0,0 +1,478 @@
1
+ /**
2
+ * TypeScript Examples
3
+ *
4
+ * These examples demonstrate the TS -> TJS -> JS pipeline.
5
+ * They are written in ACTUAL TypeScript syntax (not TJS).
6
+ * The playground shows:
7
+ * - TS input (editable)
8
+ * - TJS intermediate (read-only)
9
+ * - JS output with __tjs metadata
10
+ */
11
+
12
+ export interface TSExample {
13
+ name: string
14
+ description: string
15
+ code: string
16
+ group: 'intro' | 'validation' | 'patterns' | 'advanced'
17
+ }
18
+
19
+ export const tsExamples: TSExample[] = [
20
+ // ═══════════════════════════════════════════════════════════════
21
+ // INTRO: Basic TypeScript to TJS examples
22
+ // ═══════════════════════════════════════════════════════════════
23
+ {
24
+ name: 'Hello TypeScript',
25
+ description: 'See how TypeScript types become TJS example-based types',
26
+ group: 'intro',
27
+ code: `// TypeScript: Types are compile-time only
28
+ // TJS: Types become runtime validation!
29
+
30
+ function greet(name: string): string {
31
+ return \`Hello, \${name}!\`
32
+ }
33
+
34
+ // This works - correct type
35
+ console.log(greet('World'))
36
+
37
+ // In pure TS, this would crash at runtime
38
+ // In TJS, you get a clean error object
39
+ console.log('Bad call result:', greet(42 as any))
40
+ `,
41
+ },
42
+ {
43
+ name: 'Multiple Functions',
44
+ description: 'Multiple functions transpile correctly',
45
+ group: 'intro',
46
+ code: `// Multiple functions in one file
47
+
48
+ function add(a: number, b: number): number {
49
+ return a + b
50
+ }
51
+
52
+ function multiply(a: number, b: number): number {
53
+ return a * b
54
+ }
55
+
56
+ function greet(name: string, excited?: boolean): string {
57
+ return excited ? \`Hello, \${name}!\` : \`Hello, \${name}\`
58
+ }
59
+
60
+ // Test them all
61
+ console.log('add(2, 3) =', add(2, 3))
62
+ console.log('multiply(4, 5) =', multiply(4, 5))
63
+ console.log('greet("World") =', greet('World'))
64
+ console.log('greet("World", true) =', greet('World', true))
65
+ `,
66
+ },
67
+ {
68
+ name: 'Type Transformation',
69
+ description: 'See how TypeScript types become TJS examples',
70
+ group: 'intro',
71
+ code: `// TypeScript type syntax -> TJS example syntax
72
+ //
73
+ // TypeScript: TJS:
74
+ // name: string -> name: ''
75
+ // count: number -> count: 0
76
+ // flag: boolean -> flag: true
77
+ // items: string[] -> items: ['']
78
+ // ): string -> -> ''
79
+
80
+ function processData(
81
+ name: string,
82
+ count: number,
83
+ active: boolean,
84
+ tags: string[]
85
+ ): string {
86
+ return \`\${name}: \${count} items, active=\${active}, tags=[\${tags.join(', ')}]\`
87
+ }
88
+
89
+ console.log(processData('Test', 42, true, ['a', 'b', 'c']))
90
+ `,
91
+ },
92
+
93
+ // ═══════════════════════════════════════════════════════════════
94
+ // VALIDATION: Runtime type checking from TS types
95
+ // ═══════════════════════════════════════════════════════════════
96
+ {
97
+ name: 'Embedded Tests',
98
+ description: 'Write tests in comments that survive TypeScript compilation',
99
+ group: 'validation',
100
+ code: `// Embedded tests live inside /*test ... */ comments
101
+ // These survive TypeScript compilation and are extracted by TJS!
102
+
103
+ function add(a: number, b: number): number {
104
+ return a + b
105
+ }
106
+
107
+ /*test 'adds positive numbers' {
108
+ expect(add(2, 3)).toBe(5)
109
+ }*/
110
+
111
+ /*test 'adds negative numbers' {
112
+ expect(add(-1, -2)).toBe(-3)
113
+ }*/
114
+
115
+ /*test 'handles zero' {
116
+ expect(add(0, 5)).toBe(5)
117
+ expect(add(5, 0)).toBe(5)
118
+ }*/
119
+
120
+ function multiply(a: number, b: number): number {
121
+ return a * b
122
+ }
123
+
124
+ /*test 'multiplies numbers' {
125
+ expect(multiply(3, 4)).toBe(12)
126
+ expect(multiply(-2, 3)).toBe(-6)
127
+ }*/
128
+
129
+ // Try it: Check the "Tests" tab to see results!
130
+ // These tests run at transpile time, giving you immediate feedback.
131
+
132
+ console.log('add(10, 20) =', add(10, 20))
133
+ console.log('multiply(5, 6) =', multiply(5, 6))
134
+ `,
135
+ },
136
+ {
137
+ name: 'Runtime Validation',
138
+ description: 'TypeScript types work at RUNTIME, not just compile time',
139
+ group: 'validation',
140
+ code: `// The key insight: TS types become runtime checks
141
+
142
+ function divide(a: number, b: number): number {
143
+ if (b === 0) return NaN
144
+ return a / b
145
+ }
146
+
147
+ // Valid calls work normally
148
+ console.log('10 / 2 =', divide(10, 2))
149
+ console.log('10 / 0 =', divide(10, 0))
150
+
151
+ // Invalid calls return error objects (not crashes!)
152
+ const badResult = divide('ten' as any, 2)
153
+ console.log('divide("ten", 2) =', badResult)
154
+
155
+ if (badResult && badResult.$error) {
156
+ console.log(' ^ This is a validation error, not a crash!')
157
+ }
158
+ `,
159
+ },
160
+ {
161
+ name: 'Object Validation',
162
+ description: 'Object types are validated at runtime',
163
+ group: 'validation',
164
+ code: `// Object types become runtime checks
165
+
166
+ interface User {
167
+ name: string
168
+ age: number
169
+ }
170
+
171
+ function greetUser(user: User): string {
172
+ return \`Hello, \${user.name}! You are \${user.age} years old.\`
173
+ }
174
+
175
+ // Valid object works
176
+ const alice = { name: 'Alice', age: 30 }
177
+ console.log(greetUser(alice))
178
+
179
+ // Non-object fails validation
180
+ const badInput = greetUser('not an object' as any)
181
+ console.log('String input:', badInput)
182
+
183
+ // Note: Current validation checks type (object vs primitive)
184
+ // Deep property validation is a future enhancement
185
+ `,
186
+ },
187
+ {
188
+ name: 'Optional Parameters',
189
+ description: 'Optional params work in TS and TJS',
190
+ group: 'validation',
191
+ code: `// Optional parameters: TS ? syntax or default values
192
+
193
+ function createGreeting(
194
+ name: string,
195
+ greeting?: string,
196
+ punctuation: string = '!'
197
+ ): string {
198
+ const g = greeting ?? 'Hello'
199
+ return \`\${g}, \${name}\${punctuation}\`
200
+ }
201
+
202
+ // All these work
203
+ console.log(createGreeting('World'))
204
+ console.log(createGreeting('World', 'Hi'))
205
+ console.log(createGreeting('World', 'Hey', '...'))
206
+
207
+ // Check the metadata
208
+ console.log('\\nFunction metadata:')
209
+ console.log(' name: required')
210
+ console.log(' greeting: optional')
211
+ console.log(' punctuation: optional with default "!"')
212
+ `,
213
+ },
214
+
215
+ // ═══════════════════════════════════════════════════════════════
216
+ // PATTERNS: Common TypeScript patterns
217
+ // ═══════════════════════════════════════════════════════════════
218
+ {
219
+ name: 'Array Operations',
220
+ description: 'Array types flow through the pipeline',
221
+ group: 'patterns',
222
+ code: `// Array types are preserved
223
+
224
+ function sum(numbers: number[]): number {
225
+ return numbers.reduce((a, b) => a + b, 0)
226
+ }
227
+
228
+ function average(numbers: number[]): number {
229
+ if (numbers.length === 0) return 0
230
+ return sum(numbers) / numbers.length
231
+ }
232
+
233
+ function filterPositive(numbers: number[]): number[] {
234
+ return numbers.filter(n => n > 0)
235
+ }
236
+
237
+ const data = [-1, 2, -3, 4, 5, -6, 7]
238
+ console.log('Data:', data)
239
+ console.log('Sum:', sum(data))
240
+ console.log('Average:', average(data))
241
+ console.log('Positive only:', filterPositive(data))
242
+ `,
243
+ },
244
+ {
245
+ name: 'Nested Objects',
246
+ description: 'Nested object types work correctly',
247
+ group: 'patterns',
248
+ code: `// Nested object types
249
+
250
+ interface Address {
251
+ street: string
252
+ city: string
253
+ zip: string
254
+ }
255
+
256
+ interface Person {
257
+ name: string
258
+ address: Address
259
+ }
260
+
261
+ function formatAddress(person: Person): string {
262
+ const { name, address } = person
263
+ return \`\${name}\\n\${address.street}\\n\${address.city}, \${address.zip}\`
264
+ }
265
+
266
+ const john: Person = {
267
+ name: 'John Doe',
268
+ address: {
269
+ street: '123 Main St',
270
+ city: 'Springfield',
271
+ zip: '12345'
272
+ }
273
+ }
274
+
275
+ console.log(formatAddress(john))
276
+ `,
277
+ },
278
+ {
279
+ name: 'Union Types',
280
+ description: 'Union types and nullable values',
281
+ group: 'patterns',
282
+ code: `// Union types: T | null, T | undefined
283
+
284
+ function findUser(id: number): string | null {
285
+ // Simulated lookup
286
+ if (id === 1) return 'Alice'
287
+ if (id === 2) return 'Bob'
288
+ return null
289
+ }
290
+
291
+ function greetOrWarn(name: string | null): string {
292
+ if (name === null) {
293
+ return 'User not found!'
294
+ }
295
+ return \`Hello, \${name}!\`
296
+ }
297
+
298
+ console.log('Find user 1:', findUser(1))
299
+ console.log('Find user 2:', findUser(2))
300
+ console.log('Find user 99:', findUser(99))
301
+
302
+ console.log('\\nGreet user 1:', greetOrWarn(findUser(1)))
303
+ console.log('Greet user 99:', greetOrWarn(findUser(99)))
304
+ `,
305
+ },
306
+
307
+ // ═══════════════════════════════════════════════════════════════
308
+ // ADVANCED: More complex TypeScript patterns
309
+ // ═══════════════════════════════════════════════════════════════
310
+ {
311
+ name: 'Generic Functions',
312
+ description: 'Generics transpile with warnings (best-effort)',
313
+ group: 'advanced',
314
+ code: `// Generic functions: TJS handles them best-effort
315
+ // Generic type params become 'any' with a warning
316
+
317
+ function identity<T>(value: T): T {
318
+ return value
319
+ }
320
+
321
+ function first<T>(items: T[]): T | undefined {
322
+ return items[0]
323
+ }
324
+
325
+ function wrap<T>(value: T): { value: T } {
326
+ return { value }
327
+ }
328
+
329
+ // These work at runtime
330
+ console.log('identity(42):', identity(42))
331
+ console.log('identity("hello"):', identity('hello'))
332
+ console.log('first([1,2,3]):', first([1, 2, 3]))
333
+ console.log('wrap({ x: 1 }):', wrap({ x: 1 }))
334
+
335
+ // Check the TJS output - you'll see warnings about generic params
336
+ `,
337
+ },
338
+ {
339
+ name: 'Async Functions',
340
+ description: 'Async/await works naturally',
341
+ group: 'advanced',
342
+ code: `// Async functions work naturally
343
+ // Promise<T> is unwrapped to T in return type
344
+
345
+ async function fetchData(url: string): Promise<string> {
346
+ // Simulated fetch
347
+ await new Promise(r => setTimeout(r, 100))
348
+ return \`Data from \${url}\`
349
+ }
350
+
351
+ async function fetchMultiple(urls: string[]): Promise<string[]> {
352
+ return Promise.all(urls.map(fetchData))
353
+ }
354
+
355
+ // Run the async functions
356
+ async function main() {
357
+ console.log('Fetching single...')
358
+ const single = await fetchData('/api/users')
359
+ console.log('Result:', single)
360
+
361
+ console.log('\\nFetching multiple...')
362
+ const multiple = await fetchMultiple(['/api/a', '/api/b', '/api/c'])
363
+ console.log('Results:', multiple)
364
+ }
365
+
366
+ main()
367
+ `,
368
+ },
369
+ {
370
+ name: 'Classes',
371
+ description: 'Classes are supported with metadata',
372
+ group: 'advanced',
373
+ code: `// Classes with typed methods
374
+
375
+ class Calculator {
376
+ private value: number = 0
377
+
378
+ add(n: number): Calculator {
379
+ this.value += n
380
+ return this
381
+ }
382
+
383
+ multiply(n: number): Calculator {
384
+ this.value *= n
385
+ return this
386
+ }
387
+
388
+ getResult(): number {
389
+ return this.value
390
+ }
391
+
392
+ reset(): void {
393
+ this.value = 0
394
+ }
395
+ }
396
+
397
+ // Use the class
398
+ const calc = new Calculator()
399
+ const result = calc.add(5).multiply(3).add(10).getResult()
400
+ console.log('5 * 3 + 10 =', result)
401
+
402
+ // Chain of operations
403
+ calc.reset()
404
+ console.log('After reset:', calc.getResult())
405
+ console.log('(2 + 3) * 4 =', calc.add(2).add(3).multiply(4).getResult())
406
+ `,
407
+ },
408
+ {
409
+ name: 'The Full Picture',
410
+ description:
411
+ 'Complete example showing the TS -> TJS -> JS value proposition',
412
+ group: 'advanced',
413
+ code: `/**
414
+ * THE FULL PICTURE
415
+ *
416
+ * TypeScript promises type safety.
417
+ * TJS delivers it at RUNTIME.
418
+ *
419
+ * This is what "TS keeps its promise" means.
420
+ */
421
+
422
+ // Define your types with standard TypeScript syntax
423
+ interface Product {
424
+ id: number
425
+ name: string
426
+ price: number
427
+ }
428
+
429
+ interface Order {
430
+ products: Product[]
431
+ customer: string
432
+ }
433
+
434
+ // Write your business logic
435
+ function calculateTotal(order: Order): number {
436
+ return order.products.reduce((sum, p) => sum + p.price, 0)
437
+ }
438
+
439
+ function validateOrder(order: Order): string | null {
440
+ if (order.products.length === 0) {
441
+ return 'Order must have at least one product'
442
+ }
443
+ if (!order.customer) {
444
+ return 'Customer name is required'
445
+ }
446
+ return null
447
+ }
448
+
449
+ function processOrder(order: Order): { success: boolean; total?: number; error?: string } {
450
+ const error = validateOrder(order)
451
+ if (error) {
452
+ return { success: false, error }
453
+ }
454
+ return { success: true, total: calculateTotal(order) }
455
+ }
456
+
457
+ // Test with valid data
458
+ const validOrder: Order = {
459
+ customer: 'Alice',
460
+ products: [
461
+ { id: 1, name: 'Widget', price: 9.99 },
462
+ { id: 2, name: 'Gadget', price: 19.99 }
463
+ ]
464
+ }
465
+ console.log('Valid order:', processOrder(validOrder))
466
+
467
+ // Test with invalid data - TypeScript would let this through!
468
+ // But TJS catches it at runtime.
469
+ const badOrder = { customer: 'Bob' } as any // Missing products
470
+ console.log('Bad order:', processOrder(badOrder))
471
+
472
+ // The value proposition:
473
+ // 1. Write normal TypeScript
474
+ // 2. TJS transpiles it with runtime checks
475
+ // 3. Bad data gets caught, not crashed on
476
+ `,
477
+ },
478
+ ]