yuku-analyzer 0.5.38 → 0.5.41

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 (3) hide show
  1. package/README.md +22 -0
  2. package/decode.js +13 -12
  3. package/package.json +12 -12
package/README.md CHANGED
@@ -66,6 +66,28 @@ module.resolve("name") // scope-chain lookup, like the engine does at runtime
66
66
 
67
67
  Node identity is exact: the node you reach by walking `module.ast` and the node a semantic query returns are the same JavaScript object, so `===` always works.
68
68
 
69
+ ## Editing the AST
70
+
71
+ That identity is the payoff. Because the `node` on a symbol or reference _is_ the AST node, a refactor is a plain assignment, and [`yuku-codegen`](https://www.npmjs.com/package/yuku-codegen) prints the mutated tree back to source. No visitor to register, no separate model to translate back.
72
+
73
+ ```js
74
+ import { print } from "yuku-codegen";
75
+
76
+ const m = analyzer.addFile("util.ts", `const tmp = load();\nexport const data = tmp.value + tmp.size;`);
77
+ const tmp = m.rootScope.find("tmp");
78
+ tmp.declarations[0] === m.ast.body[0].declarations[0].id; // true, literally the same node
79
+
80
+ tmp.declarations[0].name = "raw"; // rename the binding
81
+ for (const ref of tmp.references) ref.node.name = "raw"; // and every resolved use
82
+
83
+ // across files, analyzer.referencesOf(symbol) hands back these same live nodes for every use
84
+ print(m.ast).code;
85
+ // const raw = load();
86
+ // export const data = raw.value + raw.size;
87
+ ```
88
+
89
+ The uses come from resolved references, not a name search, so a shadowing inner `tmp` is left untouched: the rename only reaches the identifiers that actually bind to this symbol.
90
+
69
91
  ## Walking with semantic context
70
92
 
71
93
  `module.walk` is a typed visitor walk where every handler also receives the current scope, symbol, and reference. No manual scope tracking, ever:
package/decode.js CHANGED
@@ -670,19 +670,20 @@ function decode(buffer, source) {
670
670
  if (s === e) return "";
671
671
  if (s >= _srcLen) return _poolDecode(s, e);
672
672
  if (e <= _firstNa) return _src.slice(s, e);
673
- const ss = s < _firstNa ? s : pm[s - _firstNa];
674
- return _src.slice(ss, pm[e - _firstNa]);
673
+ return _src.slice(s < _firstNa ? s : pm[s - _firstNa], pm[e - _firstNa]);
675
674
  };
676
675
  function nodeArr(s, len) {
677
- const r = Array.from({ length: len });
678
- for (let j = 0; j < len; j++) r[j] = node(_u32[_extraBase + s + j]);
676
+ const r = [];
677
+ const base = _extraBase + s;
678
+ for (let j = 0; j < len; j++) r.push(node(_u32[base + j]));
679
679
  return r;
680
680
  }
681
681
  function nodeArrHoles(s, len) {
682
- const r = Array.from({ length: len });
682
+ const r = [];
683
+ const base = _extraBase + s;
683
684
  for (let j = 0; j < len; j++) {
684
- const x = _u32[_extraBase + s + j];
685
- r[j] = x !== NULL ? node(x) : null;
685
+ const x = _u32[base + j];
686
+ r.push(x !== NULL ? node(x) : null);
686
687
  }
687
688
  return r;
688
689
  }
@@ -722,11 +723,11 @@ function decode(buffer, source) {
722
723
  return r;
723
724
  }
724
725
  function _decode(i) {
725
- const o = _nodesOff + i * 48;
726
- const tag = _u8[o];
727
- const flags = _u8[o + 2] | (_u8[o + 3] << 8);
728
- const f0 = _u8[o + 4] | (_u8[o + 5] << 8);
729
- const b = o >> 2;
726
+ const b = (_nodesOff + i * 48) >> 2;
727
+ const h0 = _u32[b];
728
+ const tag = h0 & 255;
729
+ const flags = h0 >>> 16;
730
+ const f0 = _u32[b + 1] & 65535;
730
731
  const f1 = _u32[b + 2], f2 = _u32[b + 3],
731
732
  f3 = _u32[b + 4], f4 = _u32[b + 5],
732
733
  f5 = _u32[b + 6], f6 = _u32[b + 7],
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "yuku-analyzer",
3
- "version": "0.5.38",
3
+ "version": "0.5.41",
4
4
  "description": "Full JavaScript and TypeScript semantic analysis: scopes, symbols, resolved references, closures, and cross-file module linking, computed natively in Zig and queried as plain JavaScript objects",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -21,17 +21,17 @@
21
21
  "decode.js"
22
22
  ],
23
23
  "optionalDependencies": {
24
- "@yuku-analyzer/binding-linux-x64-gnu": "0.5.38",
25
- "@yuku-analyzer/binding-linux-arm64-gnu": "0.5.38",
26
- "@yuku-analyzer/binding-linux-arm-gnu": "0.5.38",
27
- "@yuku-analyzer/binding-linux-x64-musl": "0.5.38",
28
- "@yuku-analyzer/binding-linux-arm64-musl": "0.5.38",
29
- "@yuku-analyzer/binding-linux-arm-musl": "0.5.38",
30
- "@yuku-analyzer/binding-darwin-x64": "0.5.38",
31
- "@yuku-analyzer/binding-darwin-arm64": "0.5.38",
32
- "@yuku-analyzer/binding-win32-x64": "0.5.38",
33
- "@yuku-analyzer/binding-win32-arm64": "0.5.38",
34
- "@yuku-analyzer/binding-freebsd-x64": "0.5.38"
24
+ "@yuku-analyzer/binding-linux-x64-gnu": "0.5.41",
25
+ "@yuku-analyzer/binding-linux-arm64-gnu": "0.5.41",
26
+ "@yuku-analyzer/binding-linux-arm-gnu": "0.5.41",
27
+ "@yuku-analyzer/binding-linux-x64-musl": "0.5.41",
28
+ "@yuku-analyzer/binding-linux-arm64-musl": "0.5.41",
29
+ "@yuku-analyzer/binding-linux-arm-musl": "0.5.41",
30
+ "@yuku-analyzer/binding-darwin-x64": "0.5.41",
31
+ "@yuku-analyzer/binding-darwin-arm64": "0.5.41",
32
+ "@yuku-analyzer/binding-win32-x64": "0.5.41",
33
+ "@yuku-analyzer/binding-win32-arm64": "0.5.41",
34
+ "@yuku-analyzer/binding-freebsd-x64": "0.5.41"
35
35
  },
36
36
  "keywords": [
37
37
  "analyzer",