miniread 1.90.0 → 1.91.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.
@@ -84,8 +84,8 @@ const manifestData = {
84
84
  },
85
85
  "rename-charcode-variables-v2": {
86
86
  recommended: true,
87
- notes: "Derives names from charCodeAt argument for better stability (e.g., $charCodeAtIndex, $charCodeAtIndexPlus1).",
88
- evaluations: { "claude-code-2.1.10:claude-code-2.1.11": { "diffSizePercent": 100, "evaluatedAt": "2026-01-25T23:09:28.154Z", "changedLines": 238, "durationSeconds": 65.10692229200001, "stableNames": 1367 } },
87
+ notes: "Derives names from charCodeAt arguments for stability, normalizing leading `$` in argument identifiers and including update-expression operator/prefix suffixes (e.g., $charCodeAtIndexInc for index++, $charCodeAtIndexPreInc for ++index).",
88
+ evaluations: { "claude-code-2.1.10:claude-code-2.1.11": { "diffSizePercent": 100, "evaluatedAt": "2026-02-06T21:25:32.362Z", "changedLines": 254, "durationSeconds": 188.446434444, "stableNames": 1368 } },
89
89
  },
90
90
  "rename-client-aliases": {
91
91
  recommended: true,
@@ -3,11 +3,11 @@
3
3
  "evaluations": {
4
4
  "claude-code-2.1.10:claude-code-2.1.11": {
5
5
  "diffSizePercent": 100,
6
- "evaluatedAt": "2026-01-25T23:09:28.154Z",
7
- "changedLines": 238,
8
- "durationSeconds": 65.10692229200001,
9
- "stableNames": 1367
6
+ "evaluatedAt": "2026-02-06T21:25:32.362Z",
7
+ "changedLines": 254,
8
+ "durationSeconds": 188.446434444,
9
+ "stableNames": 1368
10
10
  }
11
11
  },
12
- "notes": "Derives names from charCodeAt argument for better stability (e.g., $charCodeAtIndex, $charCodeAtIndexPlus1)."
12
+ "notes": "Derives names from charCodeAt arguments for stability, normalizing leading `$` in argument identifiers and including update-expression operator/prefix suffixes (e.g., $charCodeAtIndexInc for index++, $charCodeAtIndexPreInc for ++index)."
13
13
  }
@@ -9,6 +9,26 @@ const traverse = require("@babel/traverse").default;
9
9
  */
10
10
  const capitalize = (s) => s.charAt(0).toUpperCase() + s.slice(1);
11
11
  const MAX_RECURSION_DEPTH = 5;
12
+ const getNormalizedIdentifierSuffix = (name) => {
13
+ const normalizedName = name.replace(/^\$+/u, "");
14
+ if (normalizedName.length === 0)
15
+ return undefined;
16
+ return capitalize(normalizedName);
17
+ };
18
+ const getUpdateExpressionSuffix = (expression) => {
19
+ if (expression.type !== "UpdateExpression")
20
+ return undefined;
21
+ if (expression.argument.type !== "Identifier")
22
+ return undefined;
23
+ const operatorSuffix = expression.operator === "++" ? "Inc" : "Dec";
24
+ const positionSuffix = expression.prefix
25
+ ? `Pre${operatorSuffix}`
26
+ : operatorSuffix;
27
+ const identifierSuffix = getNormalizedIdentifierSuffix(expression.argument.name);
28
+ if (identifierSuffix === undefined)
29
+ return undefined;
30
+ return `${identifierSuffix}${positionSuffix}`;
31
+ };
12
32
  /**
13
33
  * Converts a charCodeAt argument expression to a suffix for the variable name.
14
34
  * Returns undefined if the expression is too complex to represent.
@@ -19,11 +39,19 @@ const MAX_RECURSION_DEPTH = 5;
19
39
  * - `index + 1` → "IndexPlus1"
20
40
  * - `i` → "I"
21
41
  * - `pos` → "Pos"
42
+ * - `index++` → "IndexInc"
43
+ * - `index--` → "IndexDec"
44
+ * - `++index` → "IndexPreInc"
45
+ * - `--index` → "IndexPreDec"
46
+ * - `$index` → "Index"
22
47
  */
23
48
  const getArgumentSuffix = (expression, depth = 0) => {
24
49
  // Prevent stack overflow from deeply nested expressions
25
50
  if (depth > MAX_RECURSION_DEPTH)
26
51
  return undefined;
52
+ const updateSuffix = getUpdateExpressionSuffix(expression);
53
+ if (updateSuffix !== undefined)
54
+ return updateSuffix;
27
55
  // Numeric literal: charCodeAt(0) → "0"
28
56
  if (expression.type === "NumericLiteral") {
29
57
  if (Number.isInteger(expression.value) && expression.value >= 0) {
@@ -33,7 +61,7 @@ const getArgumentSuffix = (expression, depth = 0) => {
33
61
  }
34
62
  // Identifier: charCodeAt(index) → "Index"
35
63
  if (expression.type === "Identifier") {
36
- return capitalize(expression.name);
64
+ return getNormalizedIdentifierSuffix(expression.name);
37
65
  }
38
66
  // Binary expression with +: charCodeAt(index + 1) → "IndexPlus1"
39
67
  if (expression.type === "BinaryExpression") {
@@ -1,4 +1,4 @@
1
- import { unwrapParentheses } from "./unwrap-parentheses.js";
1
+ import { unwrapParentheses } from "../shared/unwrap-parentheses.js";
2
2
  export const isMemberAccess = (value, objectName, keyName) => {
3
3
  if (value.type !== "MemberExpression")
4
4
  return false;
@@ -1,4 +1,4 @@
1
- import { unwrapParentheses } from "./unwrap-parentheses.js";
1
+ import { unwrapParentheses } from "../shared/unwrap-parentheses.js";
2
2
  const hasLocalBinding = (path, name) => path.scope.hasBinding(name, { noGlobals: true, noUids: true });
3
3
  export const isUndefinedExpression = (expression, path) => {
4
4
  const unwrapped = unwrapParentheses(expression);
@@ -2,7 +2,7 @@ import { getReturnExpression } from "./get-return-expression.js";
2
2
  import { getReturnedFunction } from "./get-returned-function.js";
3
3
  import { isMemberAccess } from "./is-member-access.js";
4
4
  import { isNullishCheck, isUndefinedExpression } from "./is-nullish-check.js";
5
- import { unwrapParentheses } from "./unwrap-parentheses.js";
5
+ import { unwrapParentheses } from "../shared/unwrap-parentheses.js";
6
6
  const matchSafePropertyAccessorFactory = (outerPath) => {
7
7
  const parameters = outerPath.node.params;
8
8
  if (parameters.length !== 1)
@@ -1,6 +1,6 @@
1
1
  import { isBinaryExpression, isIdentifier, isLogicalExpression, isNullLiteral, isPrivateName, } from "@babel/types";
2
2
  import { isUndefinedExpression } from "./is-undefined-expression.js";
3
- import { unwrapParentheses } from "./unwrap-parentheses.js";
3
+ import { unwrapParentheses } from "../shared/unwrap-parentheses.js";
4
4
  const noCoverage = {
5
5
  coversNull: false,
6
6
  coversUndefined: false,
@@ -1,5 +1,5 @@
1
1
  import { isIdentifier, isNumericLiteral, isUnaryExpression, } from "@babel/types";
2
- import { unwrapParentheses } from "./unwrap-parentheses.js";
2
+ import { unwrapParentheses } from "../shared/unwrap-parentheses.js";
3
3
  export const isUndefinedExpression = (expression) => {
4
4
  const unwrapped = unwrapParentheses(expression);
5
5
  if (isIdentifier(unwrapped) && unwrapped.name === "undefined")
package/package.json CHANGED
@@ -2,7 +2,7 @@
2
2
  "name": "miniread",
3
3
  "author": "Łukasz Jerciński",
4
4
  "license": "MIT",
5
- "version": "1.90.0",
5
+ "version": "1.91.0",
6
6
  "description": "Transform minified JavaScript/TypeScript into a more readable form using deterministic AST-based transforms.",
7
7
  "repository": {
8
8
  "type": "git",
@@ -1,7 +0,0 @@
1
- export const unwrapParentheses = (expression) => {
2
- let unwrapped = expression;
3
- while (unwrapped.type === "ParenthesizedExpression") {
4
- unwrapped = unwrapped.expression;
5
- }
6
- return unwrapped;
7
- };
@@ -1,2 +0,0 @@
1
- import type { Expression } from "@babel/types";
2
- export declare const unwrapParentheses: (expression: Expression) => Expression;