@ape-egg/vibe 2.3.0 → 3.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.
Files changed (57) hide show
  1. package/README.md +14 -4
  2. package/boot.js +4 -4
  3. package/component.js +27 -29
  4. package/hot-module-refresh.js +4 -4
  5. package/index.js +10 -15
  6. package/llms.txt +8 -6
  7. package/package.json +19 -14
  8. package/runtime/affected.js +159 -36
  9. package/runtime/cleanup.js +45 -1
  10. package/runtime/component.js +312 -99
  11. package/runtime/conditionals.js +111 -14
  12. package/runtime/debug.js +24 -0
  13. package/runtime/dispatch.js +172 -0
  14. package/runtime/hydrate.js +251 -111
  15. package/runtime/index.js +180 -71
  16. package/runtime/iterate.js +125 -50
  17. package/runtime/iteration-utils.js +59 -8
  18. package/runtime/manifest.js +77 -2
  19. package/runtime/parse.js +69 -5
  20. package/runtime/pre-compiled-iterations.js +19 -6
  21. package/runtime/pre-compiled-manifest.js +13 -4
  22. package/runtime/staging.js +153 -0
  23. package/runtime/state.js +31 -0
  24. package/runtime/tracking.js +173 -0
  25. package/runtime/utils.js +155 -78
  26. package/spa.js +77 -14
  27. package/vibe.css +8 -4
  28. package/CHANGELOG.md +0 -1196
  29. package/ROADMAP.md +0 -397
  30. package/compiler/bin/vibe-compile.js +0 -121
  31. package/compiler/native/.gitkeep +0 -0
  32. package/compiler/native/vibe-compiler-darwin-arm64 +0 -0
  33. package/compiler/native/vibe-compiler-linux-x64 +0 -0
  34. package/compiler/src/Cargo.lock +0 -2023
  35. package/compiler/src/Cargo.toml +0 -38
  36. package/compiler/src/compiler/PRE-RENDERING-IMPLEMENTATION.md +0 -241
  37. package/compiler/src/compiler/binding_case.rs +0 -88
  38. package/compiler/src/compiler/compile.rs +0 -2880
  39. package/compiler/src/compiler/component_tagger.rs +0 -469
  40. package/compiler/src/compiler/iteration_optimizer.rs +0 -455
  41. package/compiler/src/compiler/js_analyzer.rs +0 -715
  42. package/compiler/src/compiler/manifest_builder.rs +0 -693
  43. package/compiler/src/compiler/mod.rs +0 -16
  44. package/compiler/src/compiler/name_binding_protect.rs +0 -207
  45. package/compiler/src/compiler/reassignment_analyzer.rs +0 -456
  46. package/compiler/src/compiler/spa.rs +0 -477
  47. package/compiler/src/compiler/state_extractor.rs +0 -263
  48. package/compiler/src/compiler/value_stamper.rs +0 -921
  49. package/compiler/src/compiler/watcher.rs +0 -1278
  50. package/compiler/src/config.rs +0 -279
  51. package/compiler/src/main.rs +0 -358
  52. package/compiler/src/parser/element.rs +0 -96
  53. package/compiler/src/parser/html.rs +0 -1004
  54. package/compiler/src/parser/mod.rs +0 -8
  55. package/runtime/pre-compiled-manifest.test.mjs +0 -58
  56. package/runtime/scope.js +0 -50
  57. package/test-results/.last-run.json +0 -4
@@ -1,8 +0,0 @@
1
- pub mod html;
2
- mod element;
3
-
4
- pub use html::HtmlParser;
5
- #[allow(unused_imports)]
6
- pub use html::ParseError;
7
- #[allow(unused_imports)]
8
- pub use element::Element;
@@ -1,58 +0,0 @@
1
- import assert from 'node:assert';
2
-
3
- // The module runs a top-level `await detectHyperspeed()` that touches the DOM,
4
- // so stub the globals before importing it. querySelector returns truthy →
5
- // skipNetwork → no import() probing during module init.
6
- globalThis.window = { location: { pathname: '/' }, __ROUTE__: undefined };
7
- globalThis.document = { querySelector: () => ({}) };
8
-
9
- const { buildManifestCandidatePaths } = await import('./pre-compiled-manifest.js');
10
-
11
- let passed = 0;
12
- const test = (name, fn) => {
13
- fn();
14
- passed++;
15
- console.log(` ok - ${name}`);
16
- };
17
-
18
- // Dynamic route: window.__ROUTE__ tells us the trailing segment is a param, so
19
- // the very first candidate must be the tokenized `$` manifest — no literal
20
- // `0.html.manifest.js` probes that are guaranteed to 404.
21
- test('dynamic route resolves the $ manifest first (no literal probing)', () => {
22
- const paths = buildManifestCandidatePaths('/brawlers/0', '/brawlers/:index');
23
- assert.strictEqual(paths[0], '/vibe-hyperspeed/brawlers/$.html.manifest.js');
24
- assert.ok(
25
- !paths.includes('/vibe-hyperspeed/brawlers/0.html.manifest.js') ||
26
- paths.indexOf('/vibe-hyperspeed/brawlers/$.html.manifest.js') <
27
- paths.indexOf('/vibe-hyperspeed/brawlers/0.html.manifest.js'),
28
- 'tokenized path must come before any literal path',
29
- );
30
- });
31
-
32
- // Mid-path params tokenize by position, not just the filename.
33
- test('tokenizes only the param segments named by the route', () => {
34
- const paths = buildManifestCandidatePaths(
35
- '/_internal/characters/troll',
36
- '/_internal/characters/:key',
37
- );
38
- assert.strictEqual(
39
- paths[0],
40
- '/vibe-hyperspeed/_internal/characters/$.html.manifest.js',
41
- );
42
- });
43
-
44
- // Static page: no route hint, behaviour unchanged, no duplicate candidates.
45
- test('static top-level page resolves cleanly with no duplicates', () => {
46
- const paths = buildManifestCandidatePaths('/armory', null);
47
- assert.ok(paths.includes('/vibe-hyperspeed/armory.html.manifest.js'));
48
- assert.strictEqual(paths.length, new Set(paths).size, 'no duplicate candidates');
49
- });
50
-
51
- // Subdirectory static page: strategies 2 and 3 collapse to the same URL — it
52
- // must be probed once, not twice.
53
- test('subdirectory page dedupes identical candidates', () => {
54
- const paths = buildManifestCandidatePaths('/foo/bar', null);
55
- assert.strictEqual(paths.length, new Set(paths).size, 'no duplicate candidates');
56
- });
57
-
58
- console.log(`\n${passed} passed`);
package/runtime/scope.js DELETED
@@ -1,50 +0,0 @@
1
- // Scope resolution for component state
2
-
3
- /**
4
- * Find the component ID that owns this element
5
- * Finds nearest ancestor with data-vibe-component-id (set by component.js)
6
- * @param {Element} element - DOM element to find component for
7
- * @returns {string|null} - Component ID or null if not in component scope
8
- */
9
- export const findComponentId = (element) => {
10
- if (!element || !element.closest) return null;
11
-
12
- // Find nearest component wrapper (tagged by component.js)
13
- const wrapper = element.closest('[data-vibe-component-id]');
14
- return wrapper ? wrapper.getAttribute('data-vibe-component-id') : null;
15
- };
16
-
17
- /**
18
- * Resolve a property path with component scope fallback
19
- * Checks component state first, then global state
20
- * @param {string} path - Property path (e.g., "count" or "user.name")
21
- * @param {Element} element - DOM element for context
22
- * @param {object} globalState - Global $ object
23
- * @returns {*} - Resolved value
24
- */
25
- export const resolveWithScope = (path, element, globalState) => {
26
- const componentId = findComponentId(element);
27
-
28
- if (componentId && globalState[componentId]) {
29
- // Check component state first
30
- const componentState = globalState[componentId];
31
- const value = resolvePath(path, componentState);
32
-
33
- if (value !== undefined) {
34
- return value;
35
- }
36
- }
37
-
38
- // Fallback to global state
39
- return resolvePath(path, globalState);
40
- };
41
-
42
- /**
43
- * Resolve a dot-notation path in an object
44
- * @param {string} path - Property path
45
- * @param {object} obj - Object to resolve path in
46
- * @returns {*} - Resolved value or undefined
47
- */
48
- const resolvePath = (path, obj) => {
49
- return path.split('.').reduce((current, key) => current?.[key], obj);
50
- };
@@ -1,4 +0,0 @@
1
- {
2
- "status": "failed",
3
- "failedTests": []
4
- }