ripple 0.3.7 → 0.3.9

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 (119) hide show
  1. package/CHANGELOG.md +14 -0
  2. package/package.json +2 -2
  3. package/src/compiler/phases/1-parse/index.js +48 -349
  4. package/src/compiler/phases/2-analyze/index.js +343 -52
  5. package/src/compiler/phases/3-transform/client/index.js +28 -160
  6. package/src/compiler/phases/3-transform/segments.js +0 -7
  7. package/src/compiler/phases/3-transform/server/index.js +31 -154
  8. package/src/compiler/types/acorn.d.ts +1 -1
  9. package/src/compiler/types/estree.d.ts +1 -1
  10. package/src/compiler/types/import.d.ts +0 -2
  11. package/src/compiler/types/index.d.ts +5 -17
  12. package/src/compiler/types/parse.d.ts +1 -17
  13. package/src/compiler/utils.js +53 -20
  14. package/src/runtime/index-client.js +2 -13
  15. package/src/runtime/index-server.js +2 -2
  16. package/src/runtime/internal/client/bindings.js +3 -1
  17. package/src/runtime/internal/client/composite.js +3 -2
  18. package/src/runtime/internal/client/events.js +1 -1
  19. package/src/runtime/internal/client/head.js +3 -4
  20. package/src/runtime/internal/client/index.js +0 -1
  21. package/src/runtime/internal/client/runtime.js +0 -52
  22. package/src/runtime/internal/server/index.js +31 -55
  23. package/tests/client/array/array.copy-within.test.ripple +12 -12
  24. package/tests/client/array/array.derived.test.ripple +46 -46
  25. package/tests/client/array/array.iteration.test.ripple +10 -10
  26. package/tests/client/array/array.mutations.test.ripple +20 -20
  27. package/tests/client/array/array.to-methods.test.ripple +6 -6
  28. package/tests/client/async-suspend.test.ripple +5 -5
  29. package/tests/client/basic/basic.attributes.test.ripple +81 -81
  30. package/tests/client/basic/basic.collections.test.ripple +9 -9
  31. package/tests/client/basic/basic.components.test.ripple +28 -28
  32. package/tests/client/basic/basic.errors.test.ripple +46 -18
  33. package/tests/client/basic/basic.events.test.ripple +37 -37
  34. package/tests/client/basic/basic.get-set.test.ripple +6 -6
  35. package/tests/client/basic/basic.reactivity.test.ripple +58 -203
  36. package/tests/client/basic/basic.rendering.test.ripple +19 -19
  37. package/tests/client/basic/basic.utilities.test.ripple +3 -3
  38. package/tests/client/boundaries.test.ripple +12 -12
  39. package/tests/client/compiler/__snapshots__/compiler.assignments.test.ripple.snap +5 -5
  40. package/tests/client/compiler/compiler.assignments.test.ripple +19 -19
  41. package/tests/client/compiler/compiler.basic.test.ripple +46 -27
  42. package/tests/client/compiler/compiler.tracked-access.test.ripple +2 -2
  43. package/tests/client/composite/composite.dynamic-components.test.ripple +9 -9
  44. package/tests/client/composite/composite.props.test.ripple +14 -16
  45. package/tests/client/composite/composite.reactivity.test.ripple +69 -70
  46. package/tests/client/composite/composite.render.test.ripple +3 -3
  47. package/tests/client/computed-properties.test.ripple +4 -4
  48. package/tests/client/date.test.ripple +42 -42
  49. package/tests/client/dynamic-elements.test.ripple +44 -45
  50. package/tests/client/events.test.ripple +70 -70
  51. package/tests/client/for.test.ripple +25 -25
  52. package/tests/client/head.test.ripple +19 -19
  53. package/tests/client/html.test.ripple +3 -3
  54. package/tests/client/input-value.test.ripple +84 -84
  55. package/tests/client/lazy-destructuring.test.ripple +138 -26
  56. package/tests/client/map.test.ripple +16 -16
  57. package/tests/client/media-query.test.ripple +7 -7
  58. package/tests/client/portal.test.ripple +11 -11
  59. package/tests/client/ref.test.ripple +4 -4
  60. package/tests/client/return.test.ripple +52 -52
  61. package/tests/client/set.test.ripple +6 -6
  62. package/tests/client/svg.test.ripple +5 -5
  63. package/tests/client/switch.test.ripple +44 -44
  64. package/tests/client/try.test.ripple +5 -5
  65. package/tests/client/url/url.derived.test.ripple +6 -6
  66. package/tests/client/url-search-params/url-search-params.derived.test.ripple +8 -8
  67. package/tests/client/url-search-params/url-search-params.iteration.test.ripple +10 -10
  68. package/tests/client/url-search-params/url-search-params.mutation.test.ripple +10 -10
  69. package/tests/client/url-search-params/url-search-params.retrieval.test.ripple +18 -18
  70. package/tests/client/url-search-params/url-search-params.serialization.test.ripple +2 -2
  71. package/tests/hydration/compiled/client/events.js +25 -25
  72. package/tests/hydration/compiled/client/for.js +70 -66
  73. package/tests/hydration/compiled/client/head.js +25 -25
  74. package/tests/hydration/compiled/client/hmr.js +2 -2
  75. package/tests/hydration/compiled/client/html.js +3 -3
  76. package/tests/hydration/compiled/client/if-children.js +24 -24
  77. package/tests/hydration/compiled/client/if.js +18 -18
  78. package/tests/hydration/compiled/client/mixed-control-flow.js +9 -9
  79. package/tests/hydration/compiled/client/portal.js +3 -3
  80. package/tests/hydration/compiled/client/reactivity.js +16 -16
  81. package/tests/hydration/compiled/client/return.js +40 -40
  82. package/tests/hydration/compiled/client/switch.js +12 -12
  83. package/tests/hydration/compiled/server/events.js +19 -19
  84. package/tests/hydration/compiled/server/for.js +41 -41
  85. package/tests/hydration/compiled/server/head.js +26 -26
  86. package/tests/hydration/compiled/server/hmr.js +2 -2
  87. package/tests/hydration/compiled/server/html.js +2 -2
  88. package/tests/hydration/compiled/server/if-children.js +16 -16
  89. package/tests/hydration/compiled/server/if.js +11 -11
  90. package/tests/hydration/compiled/server/mixed-control-flow.js +6 -6
  91. package/tests/hydration/compiled/server/portal.js +2 -2
  92. package/tests/hydration/compiled/server/reactivity.js +16 -16
  93. package/tests/hydration/compiled/server/return.js +25 -25
  94. package/tests/hydration/compiled/server/switch.js +8 -8
  95. package/tests/hydration/components/events.ripple +25 -25
  96. package/tests/hydration/components/for.ripple +66 -66
  97. package/tests/hydration/components/head.ripple +16 -16
  98. package/tests/hydration/components/hmr.ripple +2 -2
  99. package/tests/hydration/components/html.ripple +3 -3
  100. package/tests/hydration/components/if-children.ripple +24 -24
  101. package/tests/hydration/components/if.ripple +18 -18
  102. package/tests/hydration/components/mixed-control-flow.ripple +9 -9
  103. package/tests/hydration/components/portal.ripple +3 -3
  104. package/tests/hydration/components/reactivity.ripple +16 -16
  105. package/tests/hydration/components/return.ripple +40 -40
  106. package/tests/hydration/components/switch.ripple +20 -20
  107. package/tests/server/await.test.ripple +3 -3
  108. package/tests/server/basic.attributes.test.ripple +34 -34
  109. package/tests/server/basic.components.test.ripple +10 -10
  110. package/tests/server/basic.test.ripple +38 -40
  111. package/tests/server/compiler.test.ripple +22 -0
  112. package/tests/server/composite.props.test.ripple +12 -14
  113. package/tests/server/dynamic-elements.test.ripple +15 -15
  114. package/tests/server/head.test.ripple +11 -11
  115. package/tests/server/lazy-destructuring.test.ripple +92 -13
  116. package/tsconfig.typecheck.json +4 -0
  117. package/types/index.d.ts +0 -19
  118. package/tests/client/__snapshots__/tracked-expression.test.ripple.snap +0 -34
  119. package/tests/client/tracked-expression.test.ripple +0 -26
@@ -64,16 +64,16 @@ describe('early return in client components', () => {
64
64
 
65
65
  it('reactive: condition changes from false to true hides rest', () => {
66
66
  component App() {
67
- let condition = track(false);
67
+ let &[condition] = track(false);
68
68
 
69
69
  <button
70
70
  onClick={() => {
71
- @condition = true;
71
+ condition = true;
72
72
  }}
73
73
  >
74
74
  {'toggle'}
75
75
  </button>
76
- if (@condition) {
76
+ if (condition) {
77
77
  <div class="guard">{'guard hit'}</div>
78
78
  return;
79
79
  }
@@ -93,16 +93,16 @@ describe('early return in client components', () => {
93
93
 
94
94
  it('reactive: condition changes from true to false shows rest', () => {
95
95
  component App() {
96
- let condition = track(true);
96
+ let &[condition] = track(true);
97
97
 
98
98
  <button
99
99
  onClick={() => {
100
- @condition = false;
100
+ condition = false;
101
101
  }}
102
102
  >
103
103
  {'toggle'}
104
104
  </button>
105
- if (@condition) {
105
+ if (condition) {
106
106
  <div class="guard">{'guard hit'}</div>
107
107
  return;
108
108
  }
@@ -905,19 +905,19 @@ describe('early return in client components', () => {
905
905
 
906
906
  it('reactive: nested return condition changes', () => {
907
907
  component App() {
908
- let a = track(true);
909
- let b = track(true);
908
+ let &[a] = track(true);
909
+ let &[b] = track(true);
910
910
 
911
911
  <button
912
912
  onClick={() => {
913
- @b = false;
913
+ b = false;
914
914
  }}
915
915
  >
916
916
  {'toggle b'}
917
917
  </button>
918
- if (@a) {
918
+ if (a) {
919
919
  <div class="a">{'a is true'}</div>
920
- if (@b) {
920
+ if (b) {
921
921
  <div class="b">{'b is true'}</div>
922
922
  return;
923
923
  }
@@ -940,18 +940,18 @@ describe('early return in client components', () => {
940
940
 
941
941
  it('reactive: return in nested element scope', () => {
942
942
  component App() {
943
- let show = track(true);
943
+ let &[show] = track(true);
944
944
 
945
945
  <button
946
946
  onClick={() => {
947
- @show = false;
947
+ show = false;
948
948
  }}
949
949
  >
950
950
  {'toggle'}
951
951
  </button>
952
952
  <div class="outer">
953
953
  <span class="label">{'outer'}</span>
954
- if (@show) {
954
+ if (show) {
955
955
  <p class="inner">{'inner'}</p>
956
956
  return;
957
957
  }
@@ -1214,17 +1214,17 @@ describe('early return in client components', () => {
1214
1214
 
1215
1215
  it('reactive: nested return - outer condition changes to false shows rest', () => {
1216
1216
  component App() {
1217
- let a = track(true);
1217
+ let &[a] = track(true);
1218
1218
  let b = true;
1219
1219
 
1220
1220
  <button
1221
1221
  onClick={() => {
1222
- @a = false;
1222
+ a = false;
1223
1223
  }}
1224
1224
  >
1225
1225
  {'toggle a'}
1226
1226
  </button>
1227
- if (@a) {
1227
+ if (a) {
1228
1228
  <div class="a">{'a'}</div>
1229
1229
  if (b) {
1230
1230
  <div class="b">{'b'}</div>
@@ -1251,11 +1251,11 @@ describe('early return in client components', () => {
1251
1251
  component App() {
1252
1252
  let a = true;
1253
1253
  let b = true;
1254
- let c = track(true);
1254
+ let &[c] = track(true);
1255
1255
 
1256
1256
  <button
1257
1257
  onClick={() => {
1258
- @c = false;
1258
+ c = false;
1259
1259
  }}
1260
1260
  >
1261
1261
  {'toggle c'}
@@ -1264,7 +1264,7 @@ describe('early return in client components', () => {
1264
1264
  <div class="a">{'a'}</div>
1265
1265
  if (b) {
1266
1266
  <div class="b">{'b'}</div>
1267
- if (@c) {
1267
+ if (c) {
1268
1268
  <div class="c">{'c'}</div>
1269
1269
  return;
1270
1270
  }
@@ -2208,15 +2208,15 @@ describe('early return in client components', () => {
2208
2208
 
2209
2209
  it('nested reactive: toggling conditions updates DOM', () => {
2210
2210
  component App() {
2211
- let a = track(false);
2212
- let b = track(false);
2213
- let c = track(false);
2214
- let d = track(false);
2211
+ let &[a] = track(false);
2212
+ let &[b] = track(false);
2213
+ let &[c] = track(false);
2214
+ let &[d] = track(false);
2215
2215
 
2216
2216
  <button
2217
2217
  class="toggle-c"
2218
2218
  onClick={() => {
2219
- @c = !@c;
2219
+ c = !c;
2220
2220
  }}
2221
2221
  >
2222
2222
  {'toggle c'}
@@ -2224,24 +2224,24 @@ describe('early return in client components', () => {
2224
2224
  <button
2225
2225
  class="toggle-d"
2226
2226
  onClick={() => {
2227
- @d = !@d;
2227
+ d = !d;
2228
2228
  }}
2229
2229
  >
2230
2230
  {'toggle d'}
2231
2231
  </button>
2232
2232
 
2233
2233
  <div class="outer">
2234
- if (@a) {
2234
+ if (a) {
2235
2235
  <span class="a">{'branch a'}</span>
2236
2236
  }
2237
2237
  <div class="inner">
2238
- if (@b) {
2238
+ if (b) {
2239
2239
  <span class="b">{'branch b'}</span>
2240
2240
  }
2241
- if (@c) {
2241
+ if (c) {
2242
2242
  return;
2243
2243
  }
2244
- if (@d) {
2244
+ if (d) {
2245
2245
  <span class="d">{'branch d'}</span>
2246
2246
  return;
2247
2247
  }
@@ -2279,19 +2279,19 @@ describe('early return in client components', () => {
2279
2279
  () => {
2280
2280
  component App() {
2281
2281
  let a = true;
2282
- let b = track(true);
2282
+ let &[b] = track(true);
2283
2283
 
2284
2284
  <button
2285
2285
  class="toggle"
2286
2286
  onClick={() => {
2287
- @b = !@b;
2287
+ b = !b;
2288
2288
  }}
2289
2289
  >
2290
2290
  {'Toggle'}
2291
2291
  </button>
2292
2292
  if (a) {
2293
2293
  <div class="a">{'a'}</div>
2294
- if (@b) {
2294
+ if (b) {
2295
2295
  <div class="b">{'b'}</div>
2296
2296
  return;
2297
2297
  }
@@ -2326,29 +2326,29 @@ describe('early return in client components', () => {
2326
2326
 
2327
2327
  it('reactive sibling returns cycle through first, second, and fallback branches', () => {
2328
2328
  component App() {
2329
- let mode = track('first');
2329
+ let &[mode] = track('first');
2330
2330
 
2331
2331
  <button
2332
2332
  class="toggle"
2333
2333
  onClick={() => {
2334
- if (@mode === 'first') {
2335
- @mode = 'second';
2336
- } else if (@mode === 'second') {
2337
- @mode = 'none';
2334
+ if (mode === 'first') {
2335
+ mode = 'second';
2336
+ } else if (mode === 'second') {
2337
+ mode = 'none';
2338
2338
  } else {
2339
- @mode = 'first';
2339
+ mode = 'first';
2340
2340
  }
2341
2341
  }}
2342
2342
  >
2343
2343
  {'toggle'}
2344
2344
  </button>
2345
2345
 
2346
- if (@mode === 'first') {
2346
+ if (mode === 'first') {
2347
2347
  <div class="first">{'first guard'}</div>
2348
2348
  return;
2349
2349
  }
2350
2350
 
2351
- if (@mode === 'second') {
2351
+ if (mode === 'second') {
2352
2352
  <div class="second">{'second guard'}</div>
2353
2353
  return;
2354
2354
  }
@@ -2382,13 +2382,13 @@ describe('early return in client components', () => {
2382
2382
 
2383
2383
  it('reactive nested returns with tracked outer and inner flags transition correctly', () => {
2384
2384
  component App() {
2385
- let a = track(true);
2386
- let b = track(true);
2385
+ let &[a] = track(true);
2386
+ let &[b] = track(true);
2387
2387
 
2388
2388
  <button
2389
2389
  class="toggle-a"
2390
2390
  onClick={() => {
2391
- @a = !@a;
2391
+ a = !a;
2392
2392
  }}
2393
2393
  >
2394
2394
  {'toggle a'}
@@ -2397,21 +2397,21 @@ describe('early return in client components', () => {
2397
2397
  <button
2398
2398
  class="toggle-b"
2399
2399
  onClick={() => {
2400
- @b = !@b;
2400
+ b = !b;
2401
2401
  }}
2402
2402
  >
2403
2403
  {'toggle b'}
2404
2404
  </button>
2405
2405
 
2406
- if (@a) {
2406
+ if (a) {
2407
2407
  <div class="a">{'a'}</div>
2408
- if (@b) {
2408
+ if (b) {
2409
2409
  <div class="b">{'b'}</div>
2410
2410
  return;
2411
2411
  }
2412
2412
  }
2413
2413
 
2414
- <div class="rest">{@a ? 'a-on rest' : 'a-off rest'}</div>
2414
+ <div class="rest">{a ? 'a-on rest' : 'a-off rest'}</div>
2415
2415
  }
2416
2416
 
2417
2417
  render(App);
@@ -2446,21 +2446,21 @@ describe('early return in client components', () => {
2446
2446
 
2447
2447
  it('reactive else-if return chain transitions between return and non-return states', () => {
2448
2448
  component App() {
2449
- let status = track(0);
2449
+ let &[status] = track(0);
2450
2450
 
2451
2451
  <button
2452
2452
  class="toggle"
2453
2453
  onClick={() => {
2454
- @status = (@status + 1) % 3;
2454
+ status = (status + 1) % 3;
2455
2455
  }}
2456
2456
  >
2457
2457
  {'toggle'}
2458
2458
  </button>
2459
2459
 
2460
- if (@status === 0) {
2460
+ if (status === 0) {
2461
2461
  <div class="zero">{'zero'}</div>
2462
2462
  return;
2463
- } else if (@status === 1) {
2463
+ } else if (status === 1) {
2464
2464
  <div class="one">{'one'}</div>
2465
2465
  return;
2466
2466
  }
@@ -60,10 +60,10 @@ describe('RippleSet', () => {
60
60
  it('handles has operation', () => {
61
61
  component SetTest() {
62
62
  let items = new RippleSet([1, 2, 3]);
63
- let hasValue = track(() => items.has(2));
63
+ let &[hasValue] = track(() => items.has(2));
64
64
 
65
65
  <button onClick={() => items.delete(2)}>{'delete'}</button>
66
- <pre>{@hasValue}</pre>
66
+ <pre>{hasValue}</pre>
67
67
  }
68
68
 
69
69
  render(SetTest);
@@ -100,11 +100,11 @@ describe('RippleSet', () => {
100
100
  it('creates RippleSet with initial values using RippleSet() shorthand syntax', () => {
101
101
  component SetTest() {
102
102
  let items = RippleSet([1, 2, 3, 4]);
103
- let hasValue = track(() => items.has(3));
103
+ let &[hasValue] = track(() => items.has(3));
104
104
 
105
105
  <button onClick={() => items.delete(3)}>{'delete'}</button>
106
106
  <pre>{items.size}</pre>
107
- <pre>{@hasValue}</pre>
107
+ <pre>{hasValue}</pre>
108
108
  }
109
109
 
110
110
  render(SetTest);
@@ -123,13 +123,13 @@ describe('RippleSet', () => {
123
123
  it('handles all operations with RippleSet() shorthand syntax', () => {
124
124
  component SetTest() {
125
125
  let items = RippleSet([10, 20, 30]);
126
- let values = track(() => Array.from(items.values()));
126
+ let &[values] = track(() => Array.from(items.values()));
127
127
 
128
128
  <button onClick={() => items.add(40)}>{'add'}</button>
129
129
  <button onClick={() => items.delete(20)}>{'delete'}</button>
130
130
  <button onClick={() => items.clear()}>{'clear'}</button>
131
131
 
132
- <pre>{JSON.stringify(@values)}</pre>
132
+ <pre>{JSON.stringify(values)}</pre>
133
133
  <pre>{items.size}</pre>
134
134
  }
135
135
 
@@ -290,7 +290,7 @@ describe('SVG namespace handling', () => {
290
290
  }
291
291
 
292
292
  component App() {
293
- let dynTag = track('polygon');
293
+ let &[dynTag] = track('polygon');
294
294
  <SVG>
295
295
  <@dynTag points="0,0 30,0 15,10" />
296
296
  </SVG>
@@ -317,7 +317,7 @@ describe('SVG namespace handling', () => {
317
317
  }
318
318
 
319
319
  component App() {
320
- let Component = track(() => Polygon);
320
+ let &[Component] = track(() => Polygon);
321
321
  <SVG>
322
322
  <@Component points="0,0 30,0 15,10" />
323
323
  </SVG>
@@ -334,19 +334,19 @@ describe('SVG namespace handling', () => {
334
334
 
335
335
  it('should render SVG as a dynamic top element with any dynamic children elements', () => {
336
336
  component SVG({ children }: PropsWithChildren<{}>) {
337
- const tag = track('svg');
337
+ let &[tag] = track('svg');
338
338
  <@tag width={100} height={50} fill="red" viewBox="0 0 30 10" preserveAspectRatio="none">
339
339
  <children />
340
340
  </@tag>
341
341
  }
342
342
 
343
343
  component Polygon({ points }: PropsWithExtras<{ points: string }>) {
344
- let dynTag = track('polygon');
344
+ let &[dynTag] = track('polygon');
345
345
  <@dynTag {points} />
346
346
  }
347
347
 
348
348
  component App() {
349
- let Component = track(() => Polygon);
349
+ let &[Component] = track(() => Polygon);
350
350
  <SVG>
351
351
  <@Component points="0,0 30,0 15,10" />
352
352
  </SVG>
@@ -3,12 +3,12 @@ import { flushSync, track } from 'ripple';
3
3
  describe('switch statements', () => {
4
4
  it('renders simple switch with literal cases', () => {
5
5
  component App() {
6
- let value = track('b');
6
+ let &[value] = track('b');
7
7
 
8
- <button onClick={() => (@value = 'c')}>{'Change to C'}</button>
9
- <button onClick={() => (@value = 'a')}>{'Change to A'}</button>
8
+ <button onClick={() => (value = 'c')}>{'Change to C'}</button>
9
+ <button onClick={() => (value = 'a')}>{'Change to A'}</button>
10
10
 
11
- switch (@value) {
11
+ switch (value) {
12
12
  case 'a':
13
13
  <div>{'Case A'}</div>
14
14
  break;
@@ -38,11 +38,11 @@ describe('switch statements', () => {
38
38
 
39
39
  it('renders switch with reactive discriminant', () => {
40
40
  component App() {
41
- let count = track(1);
41
+ let &[count] = track(1);
42
42
 
43
- <button onClick={() => @count++}>{'Increment'}</button>
43
+ <button onClick={() => count++}>{'Increment'}</button>
44
44
 
45
- switch (@count) {
45
+ switch (count) {
46
46
  case 1:
47
47
  <div>{'Count is 1'}</div>
48
48
  break;
@@ -70,13 +70,13 @@ describe('switch statements', () => {
70
70
 
71
71
  it('renders switch with default clause only', () => {
72
72
  component App() {
73
- let value = track('x');
73
+ let &[value] = track('x');
74
74
 
75
- <button onClick={() => (@value = 'y')}>{'Change Value'}</button>
75
+ <button onClick={() => (value = 'y')}>{'Change Value'}</button>
76
76
 
77
- switch (@value) {
77
+ switch (value) {
78
78
  default:
79
- <div>{'Default for ' + @value}</div>
79
+ <div>{'Default for ' + value}</div>
80
80
  }
81
81
  }
82
82
 
@@ -91,12 +91,12 @@ describe('switch statements', () => {
91
91
 
92
92
  it('renders switch using empty case fall-through', () => {
93
93
  component App() {
94
- let value = track('a');
94
+ let &[value] = track('a');
95
95
 
96
- <button onClick={() => (@value = 'b')}>{'Change to B'}</button>
97
- <button onClick={() => (@value = 'c')}>{'Change to C'}</button>
96
+ <button onClick={() => (value = 'b')}>{'Change to B'}</button>
97
+ <button onClick={() => (value = 'c')}>{'Change to C'}</button>
98
98
 
99
- switch (@value) {
99
+ switch (value) {
100
100
  case 'a':
101
101
  <div>{'Case A'}</div>
102
102
  break;
@@ -133,29 +133,29 @@ describe('switch statements', () => {
133
133
 
134
134
  it('renders switch with template content and reacts to tracked changes', () => {
135
135
  component App() {
136
- let status = track('active');
137
- let message = track('');
136
+ let &[status] = track('active');
137
+ let &[message] = track('');
138
138
 
139
- <button onClick={() => (@status = 'pending')}>{'Pending'}</button>
140
- <button onClick={() => (@status = 'completed')}>{'Completed'}</button>
141
- <button onClick={() => (@status = 'error')}>{'Error'}</button>
139
+ <button onClick={() => (status = 'pending')}>{'Pending'}</button>
140
+ <button onClick={() => (status = 'completed')}>{'Completed'}</button>
141
+ <button onClick={() => (status = 'error')}>{'Error'}</button>
142
142
 
143
- switch (@status) {
143
+ switch (status) {
144
144
  case 'active':
145
- @message = 'Currently active.';
146
- <div>{'Status: ' + @message}</div>
145
+ message = 'Currently active.';
146
+ <div>{'Status: ' + message}</div>
147
147
  break;
148
148
  case 'pending':
149
- @message = 'Waiting for completion.';
150
- <div>{'Status: ' + @message}</div>
149
+ message = 'Waiting for completion.';
150
+ <div>{'Status: ' + message}</div>
151
151
  break;
152
152
  case 'completed':
153
- @message = 'Task finished!';
154
- <div class="success">{'Status: ' + @message}</div>
153
+ message = 'Task finished!';
154
+ <div class="success">{'Status: ' + message}</div>
155
155
  break;
156
156
  default:
157
- @message = 'An error occurred.';
158
- <div class="error">{'Status: ' + @message}</div>
157
+ message = 'An error occurred.';
158
+ <div class="error">{'Status: ' + message}</div>
159
159
  }
160
160
  }
161
161
 
@@ -185,9 +185,9 @@ describe('switch statements', () => {
185
185
  'renders switch with multiple non-empty fall-through cases and reacts to tracked changes without recreating DOM unnecessarily',
186
186
  () => {
187
187
  component App() {
188
- let status = track(0);
188
+ let &[status] = track(0);
189
189
  <div>
190
- switch (@status) {
190
+ switch (status) {
191
191
  case -1:
192
192
  case 0:
193
193
  <p>{' Idle'}</p>
@@ -208,7 +208,7 @@ describe('switch statements', () => {
208
208
  </div>
209
209
  <button
210
210
  onClick={() => {
211
- @status = (@status + 1) % 5;
211
+ status = (status + 1) % 5;
212
212
  }}
213
213
  >
214
214
  {'Next Status'}
@@ -253,15 +253,15 @@ describe('switch statements', () => {
253
253
  'renders a fall-through default in the middle of switch cases and reacts to changes without recreating DOM unnecessarily',
254
254
  () => {
255
255
  component App() {
256
- let value = track('x');
256
+ let &[value] = track('x');
257
257
 
258
- <button onClick={() => (@value = 'a')}>{'Set A'}</button>
259
- <button onClick={() => (@value = 'b')}>{'Set B'}</button>
260
- <button onClick={() => (@value = 'c')}>{'Set C'}</button>
261
- <button onClick={() => (@value = 'x')}>{'Set X'}</button>
258
+ <button onClick={() => (value = 'a')}>{'Set A'}</button>
259
+ <button onClick={() => (value = 'b')}>{'Set B'}</button>
260
+ <button onClick={() => (value = 'c')}>{'Set C'}</button>
261
+ <button onClick={() => (value = 'x')}>{'Set X'}</button>
262
262
 
263
263
  <div>
264
- switch (@value) {
264
+ switch (value) {
265
265
  case 'a':
266
266
  <div>{' Case A'}</div>
267
267
  break;
@@ -271,7 +271,7 @@ describe('switch statements', () => {
271
271
  // The browser works correctly.
272
272
  // So, we're just using a defined case in the middle to simulate default.
273
273
  case 'x':
274
- <div>{' Default Case for ' + @value}</div>
274
+ <div>{' Default Case for ' + value}</div>
275
275
  case 'b':
276
276
  <div>{' Case B'}</div>
277
277
  break;
@@ -359,19 +359,19 @@ describe('switch statements', () => {
359
359
 
360
360
  it('renders switch with block-scoped cases and break inside blocks', () => {
361
361
  component App() {
362
- let level = track(1);
362
+ let &[level] = track(1);
363
363
 
364
364
  <button
365
365
  onClick={() => {
366
- if (@level === 1) @level = 2;
367
- else if (@level === 2) @level = 3;
368
- else @level = 1;
366
+ if (level === 1) level = 2;
367
+ else if (level === 2) level = 3;
368
+ else level = 1;
369
369
  }}
370
370
  >
371
371
  {'Toggle'}
372
372
  </button>
373
373
 
374
- switch (@level) {
374
+ switch (level) {
375
375
  case 1: {
376
376
  <div class="level">{'Level 1'}</div>
377
377
  break;
@@ -88,10 +88,10 @@ describe('try block', () => {
88
88
  }
89
89
 
90
90
  component Child() {
91
- let value = track(1);
92
- await Promise.resolve(@value + 1);
91
+ let &[value, valueTracked] = track(1);
92
+ await Promise.resolve(value + 1);
93
93
 
94
- <input type="number" {ref bindValue(value)} />
94
+ <input type="number" {ref bindValue(valueTracked)} />
95
95
  }
96
96
 
97
97
  render(App);
@@ -152,10 +152,10 @@ describe('try block', () => {
152
152
  component FilteredList({ query }: { query: any }) {
153
153
  let items = await Promise.resolve(['apple', 'banana', 'cherry']);
154
154
  let list = RippleArray.from(items);
155
- let filtered = track(() => list.filter((item: string) => item.includes(@query)));
155
+ let &[filtered] = track(() => list.filter((item: string) => item.includes(query.value)));
156
156
 
157
157
  <ul>
158
- for (let item of @filtered) {
158
+ for (let item of filtered) {
159
159
  <li>{item}</li>
160
160
  }
161
161
  </ul>
@@ -4,13 +4,13 @@ describe('RippleURL > derived', () => {
4
4
  it('handles reactive computed properties based on URL', () => {
5
5
  component URLTest() {
6
6
  const url = RippleURL('https://example.com/users/123?tab=profile');
7
- let userId = track(() => url.pathname.split('/').pop());
8
- let activeTab = track(() => url.searchParams.get('tab'));
7
+ let &[userId] = track(() => url.pathname.split('/').pop());
8
+ let &[activeTab] = track(() => url.searchParams.get('tab'));
9
9
 
10
10
  <button onClick={() => (url.pathname = '/users/456')}>{'Change User'}</button>
11
11
  <button onClick={() => url.searchParams.set('tab', 'settings')}>{'Change Tab'}</button>
12
- <pre>{`User ID: ${@userId}`}</pre>
13
- <pre>{`Active Tab: ${@activeTab}`}</pre>
12
+ <pre>{`User ID: ${userId}`}</pre>
13
+ <pre>{`Active Tab: ${activeTab}`}</pre>
14
14
  }
15
15
 
16
16
  render(URLTest);
@@ -57,10 +57,10 @@ describe('RippleURL > derived', () => {
57
57
  }
58
58
 
59
59
  component ChildB({ url }: { url: RippleURL }) {
60
- let count = track(() => url.searchParams.get('count'));
60
+ let &[count] = track(() => url.searchParams.get('count'));
61
61
 
62
62
  <pre>{url.href}</pre>
63
- <pre>{@count}</pre>
63
+ <pre>{count}</pre>
64
64
  }
65
65
 
66
66
  render(ParentTest);
@@ -4,15 +4,15 @@ describe('RippleURLSearchParams > derived', () => {
4
4
  it('handles reactive computed properties based on search params', () => {
5
5
  component URLTest() {
6
6
  const params = RippleURLSearchParams('page=1&limit=10');
7
- let page = track(() => parseInt(params.get('page') || '1', 10));
8
- let limit = track(() => parseInt(params.get('limit') || '10', 10));
9
- let offset = track(() => (@page - 1) * @limit);
7
+ let &[page] = track(() => parseInt(params.get('page') || '1', 10));
8
+ let &[limit] = track(() => parseInt(params.get('limit') || '10', 10));
9
+ let &[offset] = track(() => (page - 1) * limit);
10
10
 
11
11
  <button onClick={() => params.set('page', '2')}>{'next page'}</button>
12
12
  <button onClick={() => params.set('page', '1')}>{'first page'}</button>
13
- <pre>{`Page: ${@page}`}</pre>
14
- <pre>{`Limit: ${@limit}`}</pre>
15
- <pre>{`Offset: ${@offset}`}</pre>
13
+ <pre>{`Page: ${page}`}</pre>
14
+ <pre>{`Limit: ${limit}`}</pre>
15
+ <pre>{`Offset: ${offset}`}</pre>
16
16
  }
17
17
 
18
18
  render(URLTest);
@@ -62,9 +62,9 @@ describe('RippleURLSearchParams > derived', () => {
62
62
  }
63
63
 
64
64
  component ChildB({ params }: { params: RippleURLSearchParams }) {
65
- let count = track(() => params.get('count'));
65
+ let &[count] = track(() => params.get('count'));
66
66
 
67
- <pre>{@count}</pre>
67
+ <pre>{count}</pre>
68
68
  }
69
69
 
70
70
  render(ParentTest);