@clayroach/unplugin 0.1.0-source-trace.3 → 0.1.0-source-trace.4

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.
package/dist/cjs/index.js CHANGED
@@ -8,6 +8,7 @@ var _generator = _interopRequireDefault(require("@babel/generator"));
8
8
  var _parser = require("@babel/parser");
9
9
  var _traverse2 = _interopRequireDefault(require("@babel/traverse"));
10
10
  var _unplugin = require("unplugin");
11
+ var _annotateEffects = require("./transformers/annotateEffects.js");
11
12
  var _sourceTrace = require("./transformers/sourceTrace.js");
12
13
  var _withSpanTrace = require("./transformers/withSpanTrace.js");
13
14
  function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
@@ -49,7 +50,7 @@ function shouldTransform(id, include, exclude) {
49
50
  */
50
51
  const unpluginFactory = (options = {}) => {
51
52
  const {
52
- annotateEffects: _annotateEffects = false,
53
+ annotateEffects = false,
53
54
  exclude = DEFAULT_EXCLUDE,
54
55
  include = DEFAULT_INCLUDE,
55
56
  sourceTrace = true,
@@ -74,8 +75,15 @@ const unpluginFactory = (options = {}) => {
74
75
  if (spanTrace) {
75
76
  visitors.push((0, _withSpanTrace.createWithSpanTraceVisitor)(id));
76
77
  }
78
+ // Run annotateEffects separately (it has a simpler state)
79
+ if (annotateEffects) {
80
+ const annotateState = {
81
+ filename: id
82
+ };
83
+ traverse(ast, (0, _annotateEffects.createAnnotateEffectsVisitor)(id), undefined, annotateState);
84
+ }
77
85
  // Combine visitors
78
- if (visitors.length === 0) {
86
+ if (visitors.length === 0 && !annotateEffects) {
79
87
  return null;
80
88
  }
81
89
  // Initialize state for each visitor
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["_generator","_interopRequireDefault","require","_parser","_traverse2","_unplugin","_sourceTrace","_withSpanTrace","e","__esModule","default","traverse","_traverse","generate","_generate","DEFAULT_INCLUDE","DEFAULT_EXCLUDE","shouldTransform","id","include","exclude","pattern","includes","test","unpluginFactory","options","annotateEffects","_annotateEffects","sourceTrace","spanTrace","name","transformInclude","transform","code","ast","parse","sourceType","plugins","visitors","push","createSourceTraceVisitor","createWithSpanTraceVisitor","length","states","map","filename","hoisting","hoistedTraces","Map","counter","statements","i","undefined","output","sourceMaps","sourceFileName","unplugin","exports","createUnplugin","_default"],"sources":["../../src/index.ts"],"sourcesContent":[null],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"file":"index.js","names":["_generator","_interopRequireDefault","require","_parser","_traverse2","_unplugin","_annotateEffects","_sourceTrace","_withSpanTrace","e","__esModule","default","traverse","_traverse","generate","_generate","DEFAULT_INCLUDE","DEFAULT_EXCLUDE","shouldTransform","id","include","exclude","pattern","includes","test","unpluginFactory","options","annotateEffects","sourceTrace","spanTrace","name","transformInclude","transform","code","ast","parse","sourceType","plugins","visitors","push","createSourceTraceVisitor","createWithSpanTraceVisitor","annotateState","filename","createAnnotateEffectsVisitor","undefined","length","states","map","hoisting","hoistedTraces","Map","counter","statements","i","output","sourceMaps","sourceFileName","unplugin","exports","createUnplugin","_default"],"sources":["../../src/index.ts"],"sourcesContent":[null],"mappings":"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","ignoreList":[]}
@@ -0,0 +1,141 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.annotateEffectsTransformer = annotateEffectsTransformer;
7
+ exports.createAnnotateEffectsVisitor = createAnnotateEffectsVisitor;
8
+ const PURE_ANNOTATION = "#__PURE__";
9
+ /**
10
+ * Checks if a node already has a PURE annotation.
11
+ */
12
+ function isPureAnnotated(node) {
13
+ const leadingComments = node.leadingComments;
14
+ if (!leadingComments) {
15
+ return false;
16
+ }
17
+ return leadingComments.some(comment => /[@#]__PURE__/.test(comment.value));
18
+ }
19
+ /**
20
+ * Adds a PURE annotation comment to a node.
21
+ */
22
+ function annotateAsPure(path) {
23
+ if (isPureAnnotated(path.node)) {
24
+ return;
25
+ }
26
+ path.addComment("leading", PURE_ANNOTATION);
27
+ }
28
+ /**
29
+ * Checks if the parent is a CallExpression or NewExpression.
30
+ */
31
+ function hasCallableParent(path) {
32
+ const parentPath = path.parentPath;
33
+ if (!parentPath) return false;
34
+ return parentPath.isCallExpression() || parentPath.isNewExpression();
35
+ }
36
+ /**
37
+ * Checks if this node is used as a callee (e.g., `foo()` where foo is the callee).
38
+ */
39
+ function isUsedAsCallee(path) {
40
+ if (!hasCallableParent(path)) {
41
+ return false;
42
+ }
43
+ const parentPath = path.parentPath;
44
+ return parentPath.get("callee") === path;
45
+ }
46
+ /**
47
+ * Checks if this node is inside a callee chain (e.g., `foo()()` or `foo.bar()`).
48
+ */
49
+ function isInCallee(path) {
50
+ let current = path;
51
+ do {
52
+ current = current.parentPath;
53
+ if (!current) return false;
54
+ if (isUsedAsCallee(current)) {
55
+ return true;
56
+ }
57
+ } while (!current.isStatement() && !current.isFunction());
58
+ return false;
59
+ }
60
+ /**
61
+ * Checks if this expression is executed during module initialization
62
+ * (not inside a function that isn't immediately invoked).
63
+ */
64
+ function isExecutedDuringInitialization(path) {
65
+ let functionParent = path.getFunctionParent();
66
+ while (functionParent) {
67
+ if (!isUsedAsCallee(functionParent)) {
68
+ return false;
69
+ }
70
+ functionParent = functionParent.getFunctionParent();
71
+ }
72
+ return true;
73
+ }
74
+ /**
75
+ * Checks if this expression is in an assignment context
76
+ * (variable declaration, assignment expression, or class).
77
+ */
78
+ function isInAssignmentContext(path) {
79
+ const statement = path.getStatementParent();
80
+ if (!statement) return false;
81
+ let currentPath = path;
82
+ do {
83
+ currentPath = currentPath.parentPath;
84
+ if (!currentPath) return false;
85
+ if (currentPath.isVariableDeclaration() || currentPath.isAssignmentExpression() || currentPath.isClass()) {
86
+ return true;
87
+ }
88
+ } while (currentPath !== statement);
89
+ return false;
90
+ }
91
+ /**
92
+ * Visitor function for CallExpression and NewExpression nodes.
93
+ */
94
+ function callableExpressionVisitor(path, _state) {
95
+ // Skip if this is used as a callee (e.g., foo()())
96
+ if (isUsedAsCallee(path)) {
97
+ return;
98
+ }
99
+ // Skip if this is inside a callee chain
100
+ if (isInCallee(path)) {
101
+ return;
102
+ }
103
+ // Skip if not executed during initialization
104
+ if (!isExecutedDuringInitialization(path)) {
105
+ return;
106
+ }
107
+ // Must be in assignment context or export default
108
+ const statement = path.getStatementParent();
109
+ if (!isInAssignmentContext(path) && !statement?.isExportDefaultDeclaration()) {
110
+ return;
111
+ }
112
+ annotateAsPure(path);
113
+ }
114
+ /**
115
+ * Creates a Babel visitor that adds PURE annotations to call expressions.
116
+ */
117
+ function createAnnotateEffectsVisitor(filename, _options) {
118
+ return {
119
+ Program: {
120
+ enter(_path, state) {
121
+ state.filename = filename;
122
+ }
123
+ },
124
+ CallExpression(path, state) {
125
+ callableExpressionVisitor(path, state);
126
+ },
127
+ NewExpression(path, state) {
128
+ callableExpressionVisitor(path, state);
129
+ }
130
+ };
131
+ }
132
+ /**
133
+ * Creates the annotate effects transformer plugin.
134
+ */
135
+ function annotateEffectsTransformer(options) {
136
+ return {
137
+ name: "effect-annotate-pure-calls",
138
+ visitor: createAnnotateEffectsVisitor("", options)
139
+ };
140
+ }
141
+ //# sourceMappingURL=annotateEffects.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"annotateEffects.js","names":["PURE_ANNOTATION","isPureAnnotated","node","leadingComments","some","comment","test","value","annotateAsPure","path","addComment","hasCallableParent","parentPath","isCallExpression","isNewExpression","isUsedAsCallee","get","isInCallee","current","isStatement","isFunction","isExecutedDuringInitialization","functionParent","getFunctionParent","isInAssignmentContext","statement","getStatementParent","currentPath","isVariableDeclaration","isAssignmentExpression","isClass","callableExpressionVisitor","_state","isExportDefaultDeclaration","createAnnotateEffectsVisitor","filename","_options","Program","enter","_path","state","CallExpression","NewExpression","annotateEffectsTransformer","options","name","visitor"],"sources":["../../../src/transformers/annotateEffects.ts"],"sourcesContent":[null],"mappings":";;;;;;;AAgCA,MAAMA,eAAe,GAAG,WAAW;AAEnC;;;AAGA,SAASC,eAAeA,CAACC,IAAY;EACnC,MAAMC,eAAe,GAAGD,IAAI,CAACC,eAAe;EAC5C,IAAI,CAACA,eAAe,EAAE;IACpB,OAAO,KAAK;EACd;EACA,OAAOA,eAAe,CAACC,IAAI,CAAEC,OAAO,IAAK,cAAc,CAACC,IAAI,CAACD,OAAO,CAACE,KAAK,CAAC,CAAC;AAC9E;AAEA;;;AAGA,SAASC,cAAcA,CAACC,IAAkD;EACxE,IAAIR,eAAe,CAACQ,IAAI,CAACP,IAAI,CAAC,EAAE;IAC9B;EACF;EACAO,IAAI,CAACC,UAAU,CAAC,SAAS,EAAEV,eAAe,CAAC;AAC7C;AAEA;;;AAGA,SAASW,iBAAiBA,CAACF,IAAc;EACvC,MAAMG,UAAU,GAAGH,IAAI,CAACG,UAAU;EAClC,IAAI,CAACA,UAAU,EAAE,OAAO,KAAK;EAC7B,OAAOA,UAAU,CAACC,gBAAgB,EAAE,IAAID,UAAU,CAACE,eAAe,EAAE;AACtE;AAEA;;;AAGA,SAASC,cAAcA,CAACN,IAAc;EACpC,IAAI,CAACE,iBAAiB,CAACF,IAAI,CAAC,EAAE;IAC5B,OAAO,KAAK;EACd;EACA,MAAMG,UAAU,GAAGH,IAAI,CAACG,UAA0D;EAClF,OAAOA,UAAU,CAACI,GAAG,CAAC,QAAQ,CAAC,KAAKP,IAAI;AAC1C;AAEA;;;AAGA,SAASQ,UAAUA,CAACR,IAAc;EAChC,IAAIS,OAAO,GAAoBT,IAAI;EACnC,GAAG;IACDS,OAAO,GAAGA,OAAO,CAACN,UAAU;IAC5B,IAAI,CAACM,OAAO,EAAE,OAAO,KAAK;IAC1B,IAAIH,cAAc,CAACG,OAAO,CAAC,EAAE;MAC3B,OAAO,IAAI;IACb;EACF,CAAC,QAAQ,CAACA,OAAO,CAACC,WAAW,EAAE,IAAI,CAACD,OAAO,CAACE,UAAU,EAAE;EACxD,OAAO,KAAK;AACd;AAEA;;;;AAIA,SAASC,8BAA8BA,CAACZ,IAAc;EACpD,IAAIa,cAAc,GAAGb,IAAI,CAACc,iBAAiB,EAAE;EAC7C,OAAOD,cAAc,EAAE;IACrB,IAAI,CAACP,cAAc,CAACO,cAAc,CAAC,EAAE;MACnC,OAAO,KAAK;IACd;IACAA,cAAc,GAAGA,cAAc,CAACC,iBAAiB,EAAE;EACrD;EACA,OAAO,IAAI;AACb;AAEA;;;;AAIA,SAASC,qBAAqBA,CAACf,IAAc;EAC3C,MAAMgB,SAAS,GAAGhB,IAAI,CAACiB,kBAAkB,EAAE;EAC3C,IAAI,CAACD,SAAS,EAAE,OAAO,KAAK;EAE5B,IAAIE,WAAW,GAAoBlB,IAAI;EACvC,GAAG;IACDkB,WAAW,GAAGA,WAAW,CAACf,UAAU;IACpC,IAAI,CAACe,WAAW,EAAE,OAAO,KAAK;IAE9B,IACEA,WAAW,CAACC,qBAAqB,EAAE,IACnCD,WAAW,CAACE,sBAAsB,EAAE,IACpCF,WAAW,CAACG,OAAO,EAAE,EACrB;MACA,OAAO,IAAI;IACb;EACF,CAAC,QAAQH,WAAW,KAAKF,SAAS;EAElC,OAAO,KAAK;AACd;AAEA;;;AAGA,SAASM,yBAAyBA,CAChCtB,IAAkD,EAClDuB,MAAsB;EAEtB;EACA,IAAIjB,cAAc,CAACN,IAAI,CAAC,EAAE;IACxB;EACF;EAEA;EACA,IAAIQ,UAAU,CAACR,IAAI,CAAC,EAAE;IACpB;EACF;EAEA;EACA,IAAI,CAACY,8BAA8B,CAACZ,IAAI,CAAC,EAAE;IACzC;EACF;EAEA;EACA,MAAMgB,SAAS,GAAGhB,IAAI,CAACiB,kBAAkB,EAAE;EAC3C,IAAI,CAACF,qBAAqB,CAACf,IAAI,CAAC,IAAI,CAACgB,SAAS,EAAEQ,0BAA0B,EAAE,EAAE;IAC5E;EACF;EAEAzB,cAAc,CAACC,IAAI,CAAC;AACtB;AAEA;;;AAGM,SAAUyB,4BAA4BA,CAC1CC,QAAgB,EAChBC,QAAiC;EAEjC,OAAO;IACLC,OAAO,EAAE;MACPC,KAAKA,CAACC,KAAK,EAAEC,KAAK;QAChBA,KAAK,CAACL,QAAQ,GAAGA,QAAQ;MAC3B;KACD;IAEDM,cAAcA,CAAChC,IAAgC,EAAE+B,KAAK;MACpDT,yBAAyB,CAACtB,IAAI,EAAE+B,KAAK,CAAC;IACxC,CAAC;IAEDE,aAAaA,CAACjC,IAA+B,EAAE+B,KAAK;MAClDT,yBAAyB,CAACtB,IAAI,EAAE+B,KAAK,CAAC;IACxC;GACD;AACH;AAEA;;;AAGM,SAAUG,0BAA0BA,CAACC,OAAgC;EAIzE,OAAO;IACLC,IAAI,EAAE,4BAA4B;IAClCC,OAAO,EAAEZ,4BAA4B,CAAC,EAAE,EAAEU,OAAO;GAClD;AACH","ignoreList":[]}
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AA6BA,OAAO,EAAwC,KAAK,gBAAgB,EAAE,MAAM,UAAU,CAAA;AAoCtF;;;;GAIG;AACH,MAAM,WAAW,mBAAmB;IAClC;;;;;OAKG;IACH,QAAQ,CAAC,WAAW,CAAC,EAAE,OAAO,CAAA;IAE9B;;;;;OAKG;IACH,QAAQ,CAAC,SAAS,CAAC,EAAE,OAAO,CAAA;IAE5B;;;;OAIG;IACH,QAAQ,CAAC,eAAe,CAAC,EAAE,OAAO,CAAA;IAElC;;;;OAIG;IACH,QAAQ,CAAC,OAAO,CAAC,EAAE,aAAa,CAAC,MAAM,CAAC,CAAA;IAExC;;;;OAIG;IACH,QAAQ,CAAC,OAAO,CAAC,EAAE,aAAa,CAAC,MAAM,CAAC,CAAA;CACzC;AAgHD;;;;GAIG;AACH,eAAO,MAAM,QAAQ,EAAE,gBAAgB,CAAC,mBAAmB,GAAG,SAAS,EAAE,OAAO,CAAmC,CAAA;AAEnH;;;;GAIG;AACH,eAAe,QAAQ,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AA6BA,OAAO,EAAwC,KAAK,gBAAgB,EAAE,MAAM,UAAU,CAAA;AAqCtF;;;;GAIG;AACH,MAAM,WAAW,mBAAmB;IAClC;;;;;OAKG;IACH,QAAQ,CAAC,WAAW,CAAC,EAAE,OAAO,CAAA;IAE9B;;;;;OAKG;IACH,QAAQ,CAAC,SAAS,CAAC,EAAE,OAAO,CAAA;IAE5B;;;;OAIG;IACH,QAAQ,CAAC,eAAe,CAAC,EAAE,OAAO,CAAA;IAElC;;;;OAIG;IACH,QAAQ,CAAC,OAAO,CAAC,EAAE,aAAa,CAAC,MAAM,CAAC,CAAA;IAExC;;;;OAIG;IACH,QAAQ,CAAC,OAAO,CAAC,EAAE,aAAa,CAAC,MAAM,CAAC,CAAA;CACzC;AAsHD;;;;GAIG;AACH,eAAO,MAAM,QAAQ,EAAE,gBAAgB,CAAC,mBAAmB,GAAG,SAAS,EAAE,OAAO,CAAmC,CAAA;AAEnH;;;;GAIG;AACH,eAAe,QAAQ,CAAA"}
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Pure call annotation transformer.
3
+ *
4
+ * This transformer adds `#__PURE__` comments to call expressions for better tree-shaking.
5
+ * It replicates the behavior of `babel-plugin-annotate-pure-calls` but integrated into
6
+ * the Effect unplugin.
7
+ *
8
+ * The `#__PURE__` annotation tells bundlers (Webpack, Rollup, esbuild) that a function call
9
+ * has no side effects and can be safely removed if the result is unused.
10
+ *
11
+ * @since 0.1.0
12
+ */
13
+ import type { Visitor } from "@babel/traverse";
14
+ /**
15
+ * Options for the annotate effects transformer.
16
+ */
17
+ export interface AnnotateEffectsOptions {
18
+ /**
19
+ * Filter function to determine if a file should be transformed.
20
+ */
21
+ readonly filter?: (filename: string) => boolean;
22
+ }
23
+ /**
24
+ * State passed through the transformer.
25
+ */
26
+ interface TransformState {
27
+ filename: string;
28
+ }
29
+ /**
30
+ * Creates a Babel visitor that adds PURE annotations to call expressions.
31
+ */
32
+ export declare function createAnnotateEffectsVisitor(filename: string, _options?: AnnotateEffectsOptions): Visitor<TransformState>;
33
+ /**
34
+ * Creates the annotate effects transformer plugin.
35
+ */
36
+ export declare function annotateEffectsTransformer(options?: AnnotateEffectsOptions): {
37
+ visitor: Visitor<TransformState>;
38
+ name: string;
39
+ };
40
+ export {};
41
+ //# sourceMappingURL=annotateEffects.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"annotateEffects.d.ts","sourceRoot":"","sources":["../../../src/transformers/annotateEffects.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AACH,OAAO,KAAK,EAAY,OAAO,EAAE,MAAM,iBAAiB,CAAA;AAGxD;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACrC;;OAEG;IACH,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC,QAAQ,EAAE,MAAM,KAAK,OAAO,CAAA;CAChD;AAED;;GAEG;AACH,UAAU,cAAc;IACtB,QAAQ,EAAE,MAAM,CAAA;CACjB;AAmID;;GAEG;AACH,wBAAgB,4BAA4B,CAC1C,QAAQ,EAAE,MAAM,EAChB,QAAQ,CAAC,EAAE,sBAAsB,GAChC,OAAO,CAAC,cAAc,CAAC,CAgBzB;AAED;;GAEG;AACH,wBAAgB,0BAA0B,CAAC,OAAO,CAAC,EAAE,sBAAsB,GAAG;IAC5E,OAAO,EAAE,OAAO,CAAC,cAAc,CAAC,CAAA;IAChC,IAAI,EAAE,MAAM,CAAA;CACb,CAKA"}
package/dist/esm/index.js CHANGED
@@ -2,6 +2,7 @@ import _generate from "@babel/generator";
2
2
  import { parse } from "@babel/parser";
3
3
  import _traverse from "@babel/traverse";
4
4
  import { createUnplugin } from "unplugin";
5
+ import { createAnnotateEffectsVisitor } from "./transformers/annotateEffects.js";
5
6
  import { createSourceTraceVisitor } from "./transformers/sourceTrace.js";
6
7
  import { createWithSpanTraceVisitor } from "./transformers/withSpanTrace.js";
7
8
  // Handle both ESM and CJS module exports for Babel packages
@@ -49,7 +50,7 @@ function shouldTransform(id, include, exclude) {
49
50
  * Creates the unplugin factory.
50
51
  */
51
52
  const unpluginFactory = (options = {}) => {
52
- const { annotateEffects: _annotateEffects = false, exclude = DEFAULT_EXCLUDE, include = DEFAULT_INCLUDE, sourceTrace = true, spanTrace = true } = options;
53
+ const { annotateEffects = false, exclude = DEFAULT_EXCLUDE, include = DEFAULT_INCLUDE, sourceTrace = true, spanTrace = true } = options;
53
54
  return {
54
55
  name: "@effect/unplugin",
55
56
  transformInclude(id) {
@@ -69,8 +70,13 @@ const unpluginFactory = (options = {}) => {
69
70
  if (spanTrace) {
70
71
  visitors.push(createWithSpanTraceVisitor(id));
71
72
  }
73
+ // Run annotateEffects separately (it has a simpler state)
74
+ if (annotateEffects) {
75
+ const annotateState = { filename: id };
76
+ traverse(ast, createAnnotateEffectsVisitor(id), undefined, annotateState);
77
+ }
72
78
  // Combine visitors
73
- if (visitors.length === 0) {
79
+ if (visitors.length === 0 && !annotateEffects) {
74
80
  return null;
75
81
  }
76
82
  // Initialize state for each visitor
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,140 @@
1
+ const PURE_ANNOTATION = "#__PURE__";
2
+ /**
3
+ * Checks if a node already has a PURE annotation.
4
+ */
5
+ function isPureAnnotated(node) {
6
+ const leadingComments = node.leadingComments;
7
+ if (!leadingComments) {
8
+ return false;
9
+ }
10
+ return leadingComments.some((comment) => /[@#]__PURE__/.test(comment.value));
11
+ }
12
+ /**
13
+ * Adds a PURE annotation comment to a node.
14
+ */
15
+ function annotateAsPure(path) {
16
+ if (isPureAnnotated(path.node)) {
17
+ return;
18
+ }
19
+ path.addComment("leading", PURE_ANNOTATION);
20
+ }
21
+ /**
22
+ * Checks if the parent is a CallExpression or NewExpression.
23
+ */
24
+ function hasCallableParent(path) {
25
+ const parentPath = path.parentPath;
26
+ if (!parentPath)
27
+ return false;
28
+ return parentPath.isCallExpression() || parentPath.isNewExpression();
29
+ }
30
+ /**
31
+ * Checks if this node is used as a callee (e.g., `foo()` where foo is the callee).
32
+ */
33
+ function isUsedAsCallee(path) {
34
+ if (!hasCallableParent(path)) {
35
+ return false;
36
+ }
37
+ const parentPath = path.parentPath;
38
+ return parentPath.get("callee") === path;
39
+ }
40
+ /**
41
+ * Checks if this node is inside a callee chain (e.g., `foo()()` or `foo.bar()`).
42
+ */
43
+ function isInCallee(path) {
44
+ let current = path;
45
+ do {
46
+ current = current.parentPath;
47
+ if (!current)
48
+ return false;
49
+ if (isUsedAsCallee(current)) {
50
+ return true;
51
+ }
52
+ } while (!current.isStatement() && !current.isFunction());
53
+ return false;
54
+ }
55
+ /**
56
+ * Checks if this expression is executed during module initialization
57
+ * (not inside a function that isn't immediately invoked).
58
+ */
59
+ function isExecutedDuringInitialization(path) {
60
+ let functionParent = path.getFunctionParent();
61
+ while (functionParent) {
62
+ if (!isUsedAsCallee(functionParent)) {
63
+ return false;
64
+ }
65
+ functionParent = functionParent.getFunctionParent();
66
+ }
67
+ return true;
68
+ }
69
+ /**
70
+ * Checks if this expression is in an assignment context
71
+ * (variable declaration, assignment expression, or class).
72
+ */
73
+ function isInAssignmentContext(path) {
74
+ const statement = path.getStatementParent();
75
+ if (!statement)
76
+ return false;
77
+ let currentPath = path;
78
+ do {
79
+ currentPath = currentPath.parentPath;
80
+ if (!currentPath)
81
+ return false;
82
+ if (currentPath.isVariableDeclaration() ||
83
+ currentPath.isAssignmentExpression() ||
84
+ currentPath.isClass()) {
85
+ return true;
86
+ }
87
+ } while (currentPath !== statement);
88
+ return false;
89
+ }
90
+ /**
91
+ * Visitor function for CallExpression and NewExpression nodes.
92
+ */
93
+ function callableExpressionVisitor(path, _state) {
94
+ // Skip if this is used as a callee (e.g., foo()())
95
+ if (isUsedAsCallee(path)) {
96
+ return;
97
+ }
98
+ // Skip if this is inside a callee chain
99
+ if (isInCallee(path)) {
100
+ return;
101
+ }
102
+ // Skip if not executed during initialization
103
+ if (!isExecutedDuringInitialization(path)) {
104
+ return;
105
+ }
106
+ // Must be in assignment context or export default
107
+ const statement = path.getStatementParent();
108
+ if (!isInAssignmentContext(path) && !statement?.isExportDefaultDeclaration()) {
109
+ return;
110
+ }
111
+ annotateAsPure(path);
112
+ }
113
+ /**
114
+ * Creates a Babel visitor that adds PURE annotations to call expressions.
115
+ */
116
+ export function createAnnotateEffectsVisitor(filename, _options) {
117
+ return {
118
+ Program: {
119
+ enter(_path, state) {
120
+ state.filename = filename;
121
+ }
122
+ },
123
+ CallExpression(path, state) {
124
+ callableExpressionVisitor(path, state);
125
+ },
126
+ NewExpression(path, state) {
127
+ callableExpressionVisitor(path, state);
128
+ }
129
+ };
130
+ }
131
+ /**
132
+ * Creates the annotate effects transformer plugin.
133
+ */
134
+ export function annotateEffectsTransformer(options) {
135
+ return {
136
+ name: "effect-annotate-pure-calls",
137
+ visitor: createAnnotateEffectsVisitor("", options)
138
+ };
139
+ }
140
+ //# sourceMappingURL=annotateEffects.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"annotateEffects.js","sourceRoot":"","sources":["../../../src/transformers/annotateEffects.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@clayroach/unplugin",
3
- "version": "0.1.0-source-trace.3",
3
+ "version": "0.1.0-source-trace.4",
4
4
  "description": "Universal bundler plugin for Effect transformations",
5
5
  "license": "MIT",
6
6
  "repository": {
package/src/index.ts CHANGED
@@ -28,6 +28,7 @@ import type { Scope, TraverseOptions, Visitor } from "@babel/traverse"
28
28
  import _traverse from "@babel/traverse"
29
29
  import type { Node } from "@babel/types"
30
30
  import { createUnplugin, type UnpluginFactory, type UnpluginInstance } from "unplugin"
31
+ import { createAnnotateEffectsVisitor } from "./transformers/annotateEffects.js"
31
32
  import { createSourceTraceVisitor } from "./transformers/sourceTrace.js"
32
33
  import { createWithSpanTraceVisitor } from "./transformers/withSpanTrace.js"
33
34
  import type { HoistingState } from "./utils/hoisting.js"
@@ -151,7 +152,7 @@ function shouldTransform(
151
152
  */
152
153
  const unpluginFactory: UnpluginFactory<EffectPluginOptions | undefined> = (options = {}) => {
153
154
  const {
154
- annotateEffects: _annotateEffects = false,
155
+ annotateEffects = false,
155
156
  exclude = DEFAULT_EXCLUDE,
156
157
  include = DEFAULT_INCLUDE,
157
158
  sourceTrace = true,
@@ -183,8 +184,14 @@ const unpluginFactory: UnpluginFactory<EffectPluginOptions | undefined> = (optio
183
184
  visitors.push(createWithSpanTraceVisitor(id))
184
185
  }
185
186
 
187
+ // Run annotateEffects separately (it has a simpler state)
188
+ if (annotateEffects) {
189
+ const annotateState = { filename: id }
190
+ traverse(ast, createAnnotateEffectsVisitor(id), undefined, annotateState)
191
+ }
192
+
186
193
  // Combine visitors
187
- if (visitors.length === 0) {
194
+ if (visitors.length === 0 && !annotateEffects) {
188
195
  return null
189
196
  }
190
197
 
@@ -0,0 +1,197 @@
1
+ /**
2
+ * Pure call annotation transformer.
3
+ *
4
+ * This transformer adds `#__PURE__` comments to call expressions for better tree-shaking.
5
+ * It replicates the behavior of `babel-plugin-annotate-pure-calls` but integrated into
6
+ * the Effect unplugin.
7
+ *
8
+ * The `#__PURE__` annotation tells bundlers (Webpack, Rollup, esbuild) that a function call
9
+ * has no side effects and can be safely removed if the result is unused.
10
+ *
11
+ * @since 0.1.0
12
+ */
13
+ import type { NodePath, Visitor } from "@babel/traverse"
14
+ import * as t from "@babel/types"
15
+
16
+ /**
17
+ * Options for the annotate effects transformer.
18
+ */
19
+ export interface AnnotateEffectsOptions {
20
+ /**
21
+ * Filter function to determine if a file should be transformed.
22
+ */
23
+ readonly filter?: (filename: string) => boolean
24
+ }
25
+
26
+ /**
27
+ * State passed through the transformer.
28
+ */
29
+ interface TransformState {
30
+ filename: string
31
+ }
32
+
33
+ const PURE_ANNOTATION = "#__PURE__"
34
+
35
+ /**
36
+ * Checks if a node already has a PURE annotation.
37
+ */
38
+ function isPureAnnotated(node: t.Node): boolean {
39
+ const leadingComments = node.leadingComments
40
+ if (!leadingComments) {
41
+ return false
42
+ }
43
+ return leadingComments.some((comment) => /[@#]__PURE__/.test(comment.value))
44
+ }
45
+
46
+ /**
47
+ * Adds a PURE annotation comment to a node.
48
+ */
49
+ function annotateAsPure(path: NodePath<t.CallExpression | t.NewExpression>): void {
50
+ if (isPureAnnotated(path.node)) {
51
+ return
52
+ }
53
+ path.addComment("leading", PURE_ANNOTATION)
54
+ }
55
+
56
+ /**
57
+ * Checks if the parent is a CallExpression or NewExpression.
58
+ */
59
+ function hasCallableParent(path: NodePath): boolean {
60
+ const parentPath = path.parentPath
61
+ if (!parentPath) return false
62
+ return parentPath.isCallExpression() || parentPath.isNewExpression()
63
+ }
64
+
65
+ /**
66
+ * Checks if this node is used as a callee (e.g., `foo()` where foo is the callee).
67
+ */
68
+ function isUsedAsCallee(path: NodePath): boolean {
69
+ if (!hasCallableParent(path)) {
70
+ return false
71
+ }
72
+ const parentPath = path.parentPath as NodePath<t.CallExpression | t.NewExpression>
73
+ return parentPath.get("callee") === path
74
+ }
75
+
76
+ /**
77
+ * Checks if this node is inside a callee chain (e.g., `foo()()` or `foo.bar()`).
78
+ */
79
+ function isInCallee(path: NodePath): boolean {
80
+ let current: NodePath | null = path
81
+ do {
82
+ current = current.parentPath
83
+ if (!current) return false
84
+ if (isUsedAsCallee(current)) {
85
+ return true
86
+ }
87
+ } while (!current.isStatement() && !current.isFunction())
88
+ return false
89
+ }
90
+
91
+ /**
92
+ * Checks if this expression is executed during module initialization
93
+ * (not inside a function that isn't immediately invoked).
94
+ */
95
+ function isExecutedDuringInitialization(path: NodePath): boolean {
96
+ let functionParent = path.getFunctionParent()
97
+ while (functionParent) {
98
+ if (!isUsedAsCallee(functionParent)) {
99
+ return false
100
+ }
101
+ functionParent = functionParent.getFunctionParent()
102
+ }
103
+ return true
104
+ }
105
+
106
+ /**
107
+ * Checks if this expression is in an assignment context
108
+ * (variable declaration, assignment expression, or class).
109
+ */
110
+ function isInAssignmentContext(path: NodePath): boolean {
111
+ const statement = path.getStatementParent()
112
+ if (!statement) return false
113
+
114
+ let currentPath: NodePath | null = path
115
+ do {
116
+ currentPath = currentPath.parentPath
117
+ if (!currentPath) return false
118
+
119
+ if (
120
+ currentPath.isVariableDeclaration() ||
121
+ currentPath.isAssignmentExpression() ||
122
+ currentPath.isClass()
123
+ ) {
124
+ return true
125
+ }
126
+ } while (currentPath !== statement)
127
+
128
+ return false
129
+ }
130
+
131
+ /**
132
+ * Visitor function for CallExpression and NewExpression nodes.
133
+ */
134
+ function callableExpressionVisitor(
135
+ path: NodePath<t.CallExpression | t.NewExpression>,
136
+ _state: TransformState
137
+ ): void {
138
+ // Skip if this is used as a callee (e.g., foo()())
139
+ if (isUsedAsCallee(path)) {
140
+ return
141
+ }
142
+
143
+ // Skip if this is inside a callee chain
144
+ if (isInCallee(path)) {
145
+ return
146
+ }
147
+
148
+ // Skip if not executed during initialization
149
+ if (!isExecutedDuringInitialization(path)) {
150
+ return
151
+ }
152
+
153
+ // Must be in assignment context or export default
154
+ const statement = path.getStatementParent()
155
+ if (!isInAssignmentContext(path) && !statement?.isExportDefaultDeclaration()) {
156
+ return
157
+ }
158
+
159
+ annotateAsPure(path)
160
+ }
161
+
162
+ /**
163
+ * Creates a Babel visitor that adds PURE annotations to call expressions.
164
+ */
165
+ export function createAnnotateEffectsVisitor(
166
+ filename: string,
167
+ _options?: AnnotateEffectsOptions
168
+ ): Visitor<TransformState> {
169
+ return {
170
+ Program: {
171
+ enter(_path, state) {
172
+ state.filename = filename
173
+ }
174
+ },
175
+
176
+ CallExpression(path: NodePath<t.CallExpression>, state) {
177
+ callableExpressionVisitor(path, state)
178
+ },
179
+
180
+ NewExpression(path: NodePath<t.NewExpression>, state) {
181
+ callableExpressionVisitor(path, state)
182
+ }
183
+ }
184
+ }
185
+
186
+ /**
187
+ * Creates the annotate effects transformer plugin.
188
+ */
189
+ export function annotateEffectsTransformer(options?: AnnotateEffectsOptions): {
190
+ visitor: Visitor<TransformState>
191
+ name: string
192
+ } {
193
+ return {
194
+ name: "effect-annotate-pure-calls",
195
+ visitor: createAnnotateEffectsVisitor("", options)
196
+ }
197
+ }