@gtkx/cli 2.0.0-beta.1 → 2.0.0-beta.2

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 (165) hide show
  1. package/dist/builder.d.ts +1 -0
  2. package/dist/builder.d.ts.map +1 -1
  3. package/dist/builder.js +17 -5
  4. package/dist/builder.js.map +1 -1
  5. package/dist/cli.js +2 -0
  6. package/dist/cli.js.map +1 -1
  7. package/dist/codegen/run-codegen.d.ts +4 -2
  8. package/dist/codegen/run-codegen.d.ts.map +1 -1
  9. package/dist/codegen/run-codegen.js +13 -8
  10. package/dist/codegen/run-codegen.js.map +1 -1
  11. package/dist/codegen/store-resolver.d.ts +1 -1
  12. package/dist/codegen/store-resolver.d.ts.map +1 -1
  13. package/dist/codegen/store-resolver.js +2 -2
  14. package/dist/codegen/store-resolver.js.map +1 -1
  15. package/dist/commands/build.d.ts +5 -0
  16. package/dist/commands/build.d.ts.map +1 -1
  17. package/dist/commands/build.js +83 -10
  18. package/dist/commands/build.js.map +1 -1
  19. package/dist/commands/codegen.d.ts +1 -0
  20. package/dist/commands/codegen.d.ts.map +1 -1
  21. package/dist/commands/codegen.js +6 -5
  22. package/dist/commands/codegen.js.map +1 -1
  23. package/dist/commands/deploy.d.ts +1 -0
  24. package/dist/commands/deploy.d.ts.map +1 -1
  25. package/dist/commands/deploy.js +4 -2
  26. package/dist/commands/deploy.js.map +1 -1
  27. package/dist/commands/dev.d.ts +8 -0
  28. package/dist/commands/dev.d.ts.map +1 -1
  29. package/dist/commands/dev.js +19 -1
  30. package/dist/commands/dev.js.map +1 -1
  31. package/dist/deploy/freedesktop/metainfo.d.ts.map +1 -1
  32. package/dist/deploy/freedesktop/metainfo.js +41 -2
  33. package/dist/deploy/freedesktop/metainfo.js.map +1 -1
  34. package/dist/deploy/nfpm/config.d.ts.map +1 -1
  35. package/dist/deploy/nfpm/config.js +5 -2
  36. package/dist/deploy/nfpm/config.js.map +1 -1
  37. package/dist/deploy/nfpm/contents.d.ts.map +1 -1
  38. package/dist/deploy/nfpm/contents.js +8 -0
  39. package/dist/deploy/nfpm/contents.js.map +1 -1
  40. package/dist/deploy/node-runtime/elf.d.ts +2 -1
  41. package/dist/deploy/node-runtime/elf.d.ts.map +1 -1
  42. package/dist/deploy/node-runtime/elf.js +32 -5
  43. package/dist/deploy/node-runtime/elf.js.map +1 -1
  44. package/dist/deploy/node-runtime/index.d.ts +2 -1
  45. package/dist/deploy/node-runtime/index.d.ts.map +1 -1
  46. package/dist/deploy/node-runtime/index.js +73 -4
  47. package/dist/deploy/node-runtime/index.js.map +1 -1
  48. package/dist/deploy/notices/node-runtime.js +2 -2
  49. package/dist/deploy/notices/node-runtime.js.map +1 -1
  50. package/dist/deploy/payload/launcher.d.ts.map +1 -1
  51. package/dist/deploy/payload/launcher.js +14 -1
  52. package/dist/deploy/payload/launcher.js.map +1 -1
  53. package/dist/deploy/payload/stage.js +1 -1
  54. package/dist/deploy/payload/stage.js.map +1 -1
  55. package/dist/deploy/run-deploy.d.ts +1 -0
  56. package/dist/deploy/run-deploy.d.ts.map +1 -1
  57. package/dist/deploy/run-deploy.js +100 -14
  58. package/dist/deploy/run-deploy.js.map +1 -1
  59. package/dist/deploy/settings/build-manifest.d.ts +6 -1
  60. package/dist/deploy/settings/build-manifest.d.ts.map +1 -1
  61. package/dist/deploy/settings/build-manifest.js +15 -4
  62. package/dist/deploy/settings/build-manifest.js.map +1 -1
  63. package/dist/deploy/settings/extra-files.d.ts +1 -1
  64. package/dist/deploy/settings/extra-files.d.ts.map +1 -1
  65. package/dist/deploy/settings/extra-files.js +22 -1
  66. package/dist/deploy/settings/extra-files.js.map +1 -1
  67. package/dist/deploy/settings/index.d.ts +1 -0
  68. package/dist/deploy/settings/index.d.ts.map +1 -1
  69. package/dist/deploy/settings/index.js +2 -1
  70. package/dist/deploy/settings/index.js.map +1 -1
  71. package/dist/deploy/settings/paths.d.ts +2 -1
  72. package/dist/deploy/settings/paths.d.ts.map +1 -1
  73. package/dist/deploy/settings/paths.js +113 -5
  74. package/dist/deploy/settings/paths.js.map +1 -1
  75. package/dist/deploy/targets/flatpak-source.d.ts.map +1 -1
  76. package/dist/deploy/targets/flatpak-source.js +11 -2
  77. package/dist/deploy/targets/flatpak-source.js.map +1 -1
  78. package/dist/deploy/types.d.ts +1 -0
  79. package/dist/deploy/types.d.ts.map +1 -1
  80. package/dist/deploy/types.js.map +1 -1
  81. package/dist/dev/headless.d.ts +3 -0
  82. package/dist/dev/headless.d.ts.map +1 -0
  83. package/dist/dev/headless.js +35 -0
  84. package/dist/dev/headless.js.map +1 -0
  85. package/dist/dev/runner-deps.js +1 -1
  86. package/dist/dev/runner-deps.js.map +1 -1
  87. package/dist/i18n/source-messages.d.ts.map +1 -1
  88. package/dist/i18n/source-messages.js +835 -1
  89. package/dist/i18n/source-messages.js.map +1 -1
  90. package/dist/internal/build-manifest.d.ts +5 -2
  91. package/dist/internal/build-manifest.d.ts.map +1 -1
  92. package/dist/internal/build-manifest.js +15 -2
  93. package/dist/internal/build-manifest.js.map +1 -1
  94. package/dist/internal/build-output.d.ts +8 -0
  95. package/dist/internal/build-output.d.ts.map +1 -0
  96. package/dist/internal/build-output.js +69 -0
  97. package/dist/internal/build-output.js.map +1 -0
  98. package/dist/internal/entry-arg.d.ts +4 -1
  99. package/dist/internal/entry-arg.d.ts.map +1 -1
  100. package/dist/internal/entry-arg.js +7 -1
  101. package/dist/internal/entry-arg.js.map +1 -1
  102. package/dist/internal/output-directory.d.ts +15 -0
  103. package/dist/internal/output-directory.d.ts.map +1 -0
  104. package/dist/internal/output-directory.js +490 -0
  105. package/dist/internal/output-directory.js.map +1 -0
  106. package/dist/internal/prepare-project.d.ts +2 -0
  107. package/dist/internal/prepare-project.d.ts.map +1 -1
  108. package/dist/internal/prepare-project.js +3 -3
  109. package/dist/internal/prepare-project.js.map +1 -1
  110. package/dist/internal/source-imports.js +1 -1
  111. package/dist/internal/source-imports.js.map +1 -1
  112. package/dist/mcp/client.js +2 -2
  113. package/dist/mcp/client.js.map +1 -1
  114. package/dist/vite-plugins/build-manifest.d.ts +5 -1
  115. package/dist/vite-plugins/build-manifest.d.ts.map +1 -1
  116. package/dist/vite-plugins/build-manifest.js +2 -1
  117. package/dist/vite-plugins/build-manifest.js.map +1 -1
  118. package/dist/vite-plugins/i18n.d.ts.map +1 -1
  119. package/dist/vite-plugins/i18n.js +58 -6
  120. package/dist/vite-plugins/i18n.js.map +1 -1
  121. package/dist/vite-plugins/index.d.ts +8 -1
  122. package/dist/vite-plugins/index.d.ts.map +1 -1
  123. package/dist/vite-plugins/index.js +6 -2
  124. package/dist/vite-plugins/index.js.map +1 -1
  125. package/dist/vite-plugins/self-contained.d.ts.map +1 -1
  126. package/dist/vite-plugins/self-contained.js +159 -158
  127. package/dist/vite-plugins/self-contained.js.map +1 -1
  128. package/package.json +9 -9
  129. package/src/builder.ts +18 -5
  130. package/src/cli.ts +3 -0
  131. package/src/codegen/run-codegen.ts +15 -7
  132. package/src/codegen/store-resolver.ts +2 -2
  133. package/src/commands/build.ts +13 -2
  134. package/src/commands/codegen.ts +6 -5
  135. package/src/commands/deploy.ts +4 -2
  136. package/src/commands/dev.ts +20 -1
  137. package/src/deploy/freedesktop/metainfo.ts +73 -21
  138. package/src/deploy/nfpm/config.ts +5 -2
  139. package/src/deploy/nfpm/contents.ts +8 -0
  140. package/src/deploy/node-runtime/elf.ts +43 -5
  141. package/src/deploy/node-runtime/index.ts +105 -5
  142. package/src/deploy/notices/node-runtime.ts +2 -2
  143. package/src/deploy/payload/launcher.ts +20 -1
  144. package/src/deploy/payload/stage.ts +1 -1
  145. package/src/deploy/run-deploy.ts +56 -16
  146. package/src/deploy/settings/build-manifest.ts +28 -3
  147. package/src/deploy/settings/extra-files.ts +26 -2
  148. package/src/deploy/settings/index.ts +3 -1
  149. package/src/deploy/settings/paths.ts +70 -5
  150. package/src/deploy/targets/flatpak-source.ts +13 -2
  151. package/src/deploy/types.ts +1 -0
  152. package/src/dev/headless.ts +40 -0
  153. package/src/dev/runner-deps.ts +1 -1
  154. package/src/i18n/source-messages.ts +1220 -2
  155. package/src/internal/build-manifest.ts +25 -1
  156. package/src/internal/build-output.ts +99 -0
  157. package/src/internal/entry-arg.ts +8 -1
  158. package/src/internal/output-directory.ts +699 -0
  159. package/src/internal/prepare-project.ts +5 -5
  160. package/src/internal/source-imports.ts +1 -1
  161. package/src/mcp/client.ts +2 -2
  162. package/src/vite-plugins/build-manifest.ts +7 -1
  163. package/src/vite-plugins/i18n.ts +86 -5
  164. package/src/vite-plugins/index.ts +14 -7
  165. package/src/vite-plugins/self-contained.ts +184 -185
@@ -1,193 +1,195 @@
1
+ import { parseSync, traverse } from "@babel/core";
1
2
  import { isBuiltin } from "node:module";
2
3
  import { posix } from "node:path";
3
- import { parseSync, Visitor } from "vite";
4
4
  const REQUIRE_FACTORY = "createRequire";
5
5
  const REQUIRE_BINDING = "require";
6
6
  const RESOLVE_PROPERTY = "resolve";
7
- const MODULE_BUILTIN = "node:module";
7
+ const URL_PROPERTY = "url";
8
+ const MODULE_BUILTINS = new Set(["module", "node:module"]);
8
9
  const OUTPUT_DIRECTORY = ".";
9
10
  const RELATIVE_SPECIFIER = /^\.\.?(?:\/|$)/;
10
- const exportName = (name) => (name.type === "Identifier" ? name.name : null);
11
- const referenceName = (node) => (node.type === "Identifier" ? node.name : null);
12
- const countName = (declarations, name) => {
13
- if (name !== null) {
14
- declarations.set(name, (declarations.get(name) ?? 0) + 1);
11
+ const importedName = (path) => {
12
+ if (!path.isImportSpecifier()) {
13
+ return null;
15
14
  }
15
+ const { imported } = path.node;
16
+ return imported.type === "Identifier" ? imported.name : imported.value;
16
17
  };
17
- const boundPattern = (item) => {
18
- if (item === null) {
18
+ const importKind = (path) => {
19
+ const declaration = path.parentPath;
20
+ if (!declaration.isImportDeclaration() || !MODULE_BUILTINS.has(declaration.node.source.value)) {
19
21
  return null;
20
22
  }
21
- if (item.type === "Property") {
22
- return item.value;
23
+ if (importedName(path) === REQUIRE_FACTORY) {
24
+ return "factory";
25
+ }
26
+ return path.isImportNamespaceSpecifier() || path.isImportDefaultSpecifier() ? "module" : null;
27
+ };
28
+ const memberName = (path) => {
29
+ if (!path.isMemberExpression()) {
30
+ return null;
23
31
  }
24
- if (item.type === "RestElement") {
25
- return item.argument;
32
+ const property = path.get("property");
33
+ if (path.node.computed) {
34
+ return property.isStringLiteral() ? property.node.value : null;
26
35
  }
27
- return item.type === "TSParameterProperty" ? item.parameter : item;
36
+ return property.isIdentifier() ? property.node.name : null;
28
37
  };
29
- const countPatterns = (declarations, items) => {
30
- for (const item of items) {
31
- countPattern(declarations, boundPattern(item));
38
+ const isImportMeta = (path) => path.isMetaProperty() && path.node.meta.name === "import" && path.node.property.name === "meta";
39
+ const isDirectMetaUrl = (path) => {
40
+ if (!path.isMemberExpression() || memberName(path) !== URL_PROPERTY) {
41
+ return false;
32
42
  }
43
+ const object = path.get("object");
44
+ return isImportMeta(object);
33
45
  };
34
- const countPattern = (declarations, pattern) => {
35
- if (pattern === null) {
36
- return;
46
+ const bindingKind = (binding, seen) => {
47
+ if (seen.has(binding)) {
48
+ return null;
37
49
  }
38
- if (pattern.type === "Identifier") {
39
- countName(declarations, pattern.name);
40
- return;
50
+ const next = new Set(seen).add(binding);
51
+ const imported = importKind(binding.path);
52
+ if (imported !== null) {
53
+ return imported;
41
54
  }
42
- if (pattern.type === "AssignmentPattern") {
43
- countPattern(declarations, pattern.left);
44
- return;
55
+ if (!binding.path.isVariableDeclarator()) {
56
+ return null;
45
57
  }
46
- countPatterns(declarations, pattern.type === "ObjectPattern" ? pattern.properties : pattern.elements);
47
- };
48
- const countFunction = (declarations, node) => {
49
- countPattern(declarations, node.id);
50
- countPatterns(declarations, node.params);
51
- };
52
- const declarationVisitor = (declarations) => ({
53
- ArrowFunctionExpression: (node) => {
54
- countFunction(declarations, node);
55
- },
56
- CatchClause: (node) => {
57
- countPattern(declarations, node.param);
58
- },
59
- ClassDeclaration: (node) => {
60
- countPattern(declarations, node.id);
61
- },
62
- ClassExpression: (node) => {
63
- countPattern(declarations, node.id);
64
- },
65
- ExportSpecifier: (node) => {
66
- countName(declarations, exportName(node.local));
67
- },
68
- FunctionDeclaration: (node) => {
69
- countFunction(declarations, node);
70
- },
71
- FunctionExpression: (node) => {
72
- countFunction(declarations, node);
73
- },
74
- ImportDefaultSpecifier: (node) => {
75
- countPattern(declarations, node.local);
76
- },
77
- ImportNamespaceSpecifier: (node) => {
78
- countPattern(declarations, node.local);
79
- },
80
- ImportSpecifier: (node) => {
81
- countPattern(declarations, node.local);
82
- },
83
- VariableDeclarator: (node) => {
84
- countPattern(declarations, node.id);
85
- },
86
- });
87
- const isUnshadowed = (name, bindings) => (bindings.declarations.get(name) ?? 0) <= 1;
88
- const templateString = (node) => {
89
- const [quasi] = node.quasis;
90
- return quasi === undefined || node.expressions.length > 0 ? null : quasi.value.cooked;
91
- };
92
- const literalString = (node) => {
93
- if (node?.type === "TemplateLiteral") {
94
- return templateString(node);
95
- }
96
- return node?.type === "Literal" && typeof node.value === "string" ? node.value : null;
97
- };
98
- const isMetaUrl = (node, bindings) => {
99
- if (node.type === "MemberExpression") {
100
- return node.object.type === "MetaProperty";
101
- }
102
- const name = referenceName(node);
103
- return name !== null && bindings.urls.has(name) && isUnshadowed(name, bindings);
104
- };
105
- const hasMetaUrl = (node, bindings) => node.arguments.some((argument) => isMetaUrl(argument, bindings));
106
- const isRequireName = (name, bindings) => name !== null && (name === REQUIRE_BINDING || bindings.requires.has(name)) && isUnshadowed(name, bindings);
107
- const isFactoryName = (name, bindings) => name !== null && (name === REQUIRE_FACTORY || bindings.factories.has(name)) && isUnshadowed(name, bindings);
108
- const isRequireFactory = (node, bindings) => node.type === "CallExpression" &&
109
- (isFactoryName(referenceName(node.callee), bindings) || hasMetaUrl(node, bindings));
110
- const isResolveTarget = (object, bindings) => object.type === "MetaProperty" ||
111
- isRequireName(referenceName(object), bindings) ||
112
- isRequireFactory(object, bindings);
113
- const isResolveMember = (callee, bindings) => callee.type === "MemberExpression" &&
114
- !callee.computed &&
115
- callee.property.type === "Identifier" &&
116
- callee.property.name === RESOLVE_PROPERTY &&
117
- isResolveTarget(callee.object, bindings);
118
- const isResolvingCall = (call, bindings) => hasMetaUrl(call, bindings) ||
119
- isRequireName(referenceName(call.callee), bindings) ||
120
- isRequireFactory(call.callee, bindings) ||
121
- isResolveMember(call.callee, bindings);
122
- const collectFactories = (node, bindings) => {
123
- if (node.source.value !== MODULE_BUILTIN) {
124
- return;
58
+ const initializer = binding.path.get("init");
59
+ return initializer.node === null ? null : expressionKind(initializer, next);
60
+ };
61
+ const nameKind = (scope, name, seen) => {
62
+ const binding = scope.getBinding(name);
63
+ if (binding !== undefined) {
64
+ return bindingKind(binding, seen);
125
65
  }
126
- for (const specifier of node.specifiers) {
127
- if (specifier.type === "ImportSpecifier" && exportName(specifier.imported) === REQUIRE_FACTORY) {
128
- bindings.factories.add(specifier.local.name);
129
- }
66
+ if (name === REQUIRE_FACTORY) {
67
+ return "factory";
130
68
  }
69
+ return name === REQUIRE_BINDING ? "require" : null;
131
70
  };
132
- const collectBinding = (node, bindings) => {
133
- const { id, init } = node;
134
- if (init === null || id.type !== "Identifier") {
135
- return;
71
+ const isModuleExpression = (path, seen) => {
72
+ if (path.isIdentifier()) {
73
+ return nameKind(path.scope, path.node.name, seen) === "module";
74
+ }
75
+ if (!path.isCallExpression()) {
76
+ return false;
77
+ }
78
+ const [source] = path.get("arguments");
79
+ const callee = path.get("callee");
80
+ const sourceName = source === undefined ? null : literalString(source);
81
+ return (sourceName !== null &&
82
+ MODULE_BUILTINS.has(sourceName) &&
83
+ isRequireExpression(callee, seen));
84
+ };
85
+ const isFactoryExpression = (path, seen) => {
86
+ if (path.isIdentifier()) {
87
+ return nameKind(path.scope, path.node.name, seen) === "factory";
88
+ }
89
+ if (!path.isMemberExpression() || memberName(path) !== REQUIRE_FACTORY) {
90
+ return false;
91
+ }
92
+ return isModuleExpression(path.get("object"), seen);
93
+ };
94
+ const isRequireFactoryCall = (path, seen) => {
95
+ if (!path.isCallExpression()) {
96
+ return false;
97
+ }
98
+ const callee = path.get("callee");
99
+ return isFactoryExpression(callee, seen);
100
+ };
101
+ const expressionKind = (path, seen) => {
102
+ if (isDirectMetaUrl(path)) {
103
+ return "url";
136
104
  }
137
- if (isMetaUrl(init, bindings)) {
138
- bindings.urls.add(id.name);
105
+ if (path.isIdentifier()) {
106
+ return nameKind(path.scope, path.node.name, seen);
139
107
  }
140
- if (isRequireFactory(init, bindings)) {
141
- bindings.requires.add(id.name);
108
+ if (isFactoryExpression(path, seen)) {
109
+ return "factory";
142
110
  }
111
+ if (isModuleExpression(path, seen)) {
112
+ return "module";
113
+ }
114
+ return isRequireFactoryCall(path, seen) ? "require" : null;
115
+ };
116
+ const isMetaUrl = (path) => isDirectMetaUrl(path) ||
117
+ (path.isIdentifier() && nameKind(path.scope, path.node.name, new Set()) === "url");
118
+ const isRequireExpression = (path, seen = new Set()) => isRequireFactoryCall(path, seen) ||
119
+ (path.isIdentifier() && nameKind(path.scope, path.node.name, seen) === "require");
120
+ const hasMetaUrlArgument = (path) => {
121
+ if (!path.isCallExpression()) {
122
+ return false;
123
+ }
124
+ return path.get("arguments").some((argument) => isMetaUrl(argument));
125
+ };
126
+ const isResolveMember = (path) => {
127
+ if (!path.isMemberExpression() || memberName(path) !== RESOLVE_PROPERTY) {
128
+ return false;
129
+ }
130
+ const object = path.get("object");
131
+ return isImportMeta(object) || isRequireExpression(object);
132
+ };
133
+ const isResolvingCall = (path) => {
134
+ if (!path.isCallExpression()) {
135
+ return false;
136
+ }
137
+ const callee = path.get("callee");
138
+ return hasMetaUrlArgument(path) || isRequireExpression(callee) || isResolveMember(callee);
139
+ };
140
+ const literalString = (path) => {
141
+ if (path.isStringLiteral()) {
142
+ return path.node.value;
143
+ }
144
+ if (!path.isTemplateLiteral() || path.node.expressions.length > 0) {
145
+ return null;
146
+ }
147
+ return path.node.quasis[0]?.value.cooked ?? null;
143
148
  };
144
149
  const collectSource = (scan, source) => {
145
150
  if (source !== null) {
146
151
  scan.sources.push(source);
147
152
  }
148
153
  };
149
- const collectCall = (scan, node) => {
150
- if (node.arguments.some((argument) => literalString(argument) !== null)) {
151
- scan.calls.push(node);
152
- }
153
- };
154
- const scanVisitor = (scan) => ({
155
- CallExpression: (node) => {
156
- collectCall(scan, node);
157
- },
158
- ExportAllDeclaration: (node) => {
159
- collectSource(scan, node.source.value);
160
- },
161
- ExportNamedDeclaration: (node) => {
162
- collectSource(scan, node.source?.value ?? null);
163
- },
164
- ImportDeclaration: (node) => {
165
- collectFactories(node, scan.bindings);
166
- collectSource(scan, node.source.value);
167
- },
168
- ImportExpression: (node) => {
169
- collectSource(scan, literalString(node.source));
170
- },
171
- VariableDeclarator: (node) => {
172
- collectBinding(node, scan.bindings);
173
- },
174
- });
154
+ const collectCallSources = (scan, path) => {
155
+ if (!isResolvingCall(path) || !path.isCallExpression()) {
156
+ return;
157
+ }
158
+ for (const argument of path.get("arguments")) {
159
+ collectSource(scan, literalString(argument));
160
+ }
161
+ };
175
162
  const scanChunk = (chunk) => {
176
- const scan = {
177
- bindings: { declarations: new Map(), factories: new Set(), requires: new Set(), urls: new Set() },
178
- calls: [],
179
- sources: [],
180
- };
181
- const { program } = parseSync(chunk.fileName, chunk.code);
182
- new Visitor(declarationVisitor(scan.bindings.declarations)).visit(program);
183
- new Visitor(scanVisitor(scan)).visit(program);
163
+ const scan = { sources: [] };
164
+ const ast = parseSync(chunk.code, {
165
+ ast: true,
166
+ babelrc: false,
167
+ configFile: false,
168
+ filename: chunk.fileName,
169
+ sourceType: "module",
170
+ });
171
+ if (ast === null) {
172
+ throw new Error(`Cannot inspect ${chunk.fileName}`);
173
+ }
174
+ traverse(ast, {
175
+ CallExpression: (path) => {
176
+ collectCallSources(scan, path);
177
+ },
178
+ ExportAllDeclaration: (path) => {
179
+ collectSource(scan, path.node.source.value);
180
+ },
181
+ ExportNamedDeclaration: (path) => {
182
+ collectSource(scan, path.node.source?.value ?? null);
183
+ },
184
+ ImportDeclaration: (path) => {
185
+ collectSource(scan, path.node.source.value);
186
+ },
187
+ ImportExpression: (path) => {
188
+ collectSource(scan, literalString(path.get("source")));
189
+ },
190
+ });
184
191
  return scan;
185
192
  };
186
- const callSpecifiers = (scan) => scan.calls
187
- .filter((call) => isResolvingCall(call, scan.bindings))
188
- .flatMap((call) => call.arguments)
189
- .map((argument) => literalString(argument))
190
- .filter((specifier) => specifier !== null);
191
193
  const isReachable = (specifier, directory, emitted) => {
192
194
  if (isBuiltin(specifier)) {
193
195
  return true;
@@ -199,9 +201,8 @@ const isReachable = (specifier, directory, emitted) => {
199
201
  return target === OUTPUT_DIRECTORY || emitted.has(target);
200
202
  };
201
203
  const unreachableSpecifiers = (chunk, emitted) => {
202
- const scan = scanChunk(chunk);
203
204
  const directory = posix.dirname(chunk.fileName);
204
- return new Set([...scan.sources, ...callSpecifiers(scan)])
205
+ return new Set(scanChunk(chunk).sources)
205
206
  .values()
206
207
  .filter((specifier) => !isReachable(specifier, directory, emitted))
207
208
  .toArray()
@@ -1 +1 @@
1
- {"version":3,"file":"self-contained.js","sourceRoot":"","sources":["../../src/vite-plugins/self-contained.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ESTree, Plugin, VisitorObject } from \"vite\";\nimport { isBuiltin } from \"node:module\";\nimport { posix } from \"node:path\";\nimport { parseSync, Visitor } from \"vite\";\n\ntype Bindings = {\n declarations: Map<string, number>;\n factories: Set<string>;\n requires: Set<string>;\n urls: Set<string>;\n};\n\ntype Scan = {\n bindings: Bindings;\n calls: ESTree.CallExpression[];\n sources: string[];\n};\n\ntype Chunk = {\n fileName: string;\n code: string;\n};\n\ntype PatternItem =\n | ESTree.BindingPattern |\n ESTree.BindingProperty |\n ESTree.BindingRestElement |\n ESTree.FormalParameterRest |\n ESTree.TSParameterProperty |\n null;\n\nconst REQUIRE_FACTORY = \"createRequire\";\nconst REQUIRE_BINDING = \"require\";\nconst RESOLVE_PROPERTY = \"resolve\";\nconst MODULE_BUILTIN = \"node:module\";\nconst OUTPUT_DIRECTORY = \".\";\nconst RELATIVE_SPECIFIER = /^\\.\\.?(?:\\/|$)/;\n\nconst exportName = (name: ESTree.ModuleExportName): string | null => (name.type === \"Identifier\" ? name.name : null);\nconst referenceName = (node: ESTree.Argument): string | null => (node.type === \"Identifier\" ? node.name : null);\n\nconst countName = (declarations: Map<string, number>, name: string | null): void => {\n if (name !== null) {\n declarations.set(name, (declarations.get(name) ?? 0) + 1);\n }\n};\n\nconst boundPattern = (item: PatternItem): ESTree.BindingPattern | null => {\n if (item === null) {\n return null;\n }\n\n if (item.type === \"Property\") {\n return item.value;\n }\n\n if (item.type === \"RestElement\") {\n return item.argument;\n }\n\n return item.type === \"TSParameterProperty\" ? item.parameter : item;\n};\n\nconst countPatterns = (declarations: Map<string, number>, items: PatternItem[]): void => {\n for (const item of items) {\n countPattern(declarations, boundPattern(item));\n }\n};\n\nconst countPattern = (declarations: Map<string, number>, pattern: ESTree.BindingPattern | null): void => {\n if (pattern === null) {\n return;\n }\n\n if (pattern.type === \"Identifier\") {\n countName(declarations, pattern.name);\n\n return;\n }\n\n if (pattern.type === \"AssignmentPattern\") {\n countPattern(declarations, pattern.left);\n\n return;\n }\n\n countPatterns(declarations, pattern.type === \"ObjectPattern\" ? pattern.properties : pattern.elements);\n};\n\nconst countFunction = (\n declarations: Map<string, number>,\n node: ESTree.ArrowFunctionExpression | ESTree.Function,\n): void => {\n countPattern(declarations, node.id);\n countPatterns(declarations, node.params);\n};\n\nconst declarationVisitor = (declarations: Map<string, number>): VisitorObject => ({\n ArrowFunctionExpression: (node) => {\n countFunction(declarations, node);\n },\n CatchClause: (node) => {\n countPattern(declarations, node.param);\n },\n ClassDeclaration: (node) => {\n countPattern(declarations, node.id);\n },\n ClassExpression: (node) => {\n countPattern(declarations, node.id);\n },\n ExportSpecifier: (node) => {\n countName(declarations, exportName(node.local));\n },\n FunctionDeclaration: (node) => {\n countFunction(declarations, node);\n },\n FunctionExpression: (node) => {\n countFunction(declarations, node);\n },\n ImportDefaultSpecifier: (node) => {\n countPattern(declarations, node.local);\n },\n ImportNamespaceSpecifier: (node) => {\n countPattern(declarations, node.local);\n },\n ImportSpecifier: (node) => {\n countPattern(declarations, node.local);\n },\n VariableDeclarator: (node) => {\n countPattern(declarations, node.id);\n },\n});\n\nconst isUnshadowed = (name: string, bindings: Bindings): boolean => (bindings.declarations.get(name) ?? 0) <= 1;\n\nconst templateString = (node: ESTree.TemplateLiteral): string | null => {\n const [quasi] = node.quasis;\n\n return quasi === undefined || node.expressions.length > 0 ? null : quasi.value.cooked;\n};\n\nconst literalString = (node: ESTree.Argument | null): string | null => {\n if (node?.type === \"TemplateLiteral\") {\n return templateString(node);\n }\n\n return node?.type === \"Literal\" && typeof node.value === \"string\" ? node.value : null;\n};\n\nconst isMetaUrl = (node: ESTree.Argument, bindings: Bindings): boolean => {\n if (node.type === \"MemberExpression\") {\n return node.object.type === \"MetaProperty\";\n }\n\n const name = referenceName(node);\n\n return name !== null && bindings.urls.has(name) && isUnshadowed(name, bindings);\n};\n\nconst hasMetaUrl = (node: ESTree.CallExpression, bindings: Bindings): boolean =>\n node.arguments.some((argument) => isMetaUrl(argument, bindings));\n\nconst isRequireName = (name: string | null, bindings: Bindings): boolean =>\n name !== null && (name === REQUIRE_BINDING || bindings.requires.has(name)) && isUnshadowed(name, bindings);\n\nconst isFactoryName = (name: string | null, bindings: Bindings): boolean =>\n name !== null && (name === REQUIRE_FACTORY || bindings.factories.has(name)) && isUnshadowed(name, bindings);\n\nconst isRequireFactory = (node: ESTree.Argument, bindings: Bindings): boolean =>\n node.type === \"CallExpression\" &&\n (isFactoryName(referenceName(node.callee), bindings) || hasMetaUrl(node, bindings));\n\nconst isResolveTarget = (object: ESTree.Expression, bindings: Bindings): boolean =>\n object.type === \"MetaProperty\" ||\n isRequireName(referenceName(object), bindings) ||\n isRequireFactory(object, bindings);\n\nconst isResolveMember = (callee: ESTree.Expression, bindings: Bindings): boolean =>\n callee.type === \"MemberExpression\" &&\n !callee.computed &&\n callee.property.type === \"Identifier\" &&\n callee.property.name === RESOLVE_PROPERTY &&\n isResolveTarget(callee.object, bindings);\n\nconst isResolvingCall = (call: ESTree.CallExpression, bindings: Bindings): boolean =>\n hasMetaUrl(call, bindings) ||\n isRequireName(referenceName(call.callee), bindings) ||\n isRequireFactory(call.callee, bindings) ||\n isResolveMember(call.callee, bindings);\n\nconst collectFactories = (node: ESTree.ImportDeclaration, bindings: Bindings): void => {\n if (node.source.value !== MODULE_BUILTIN) {\n return;\n }\n\n for (const specifier of node.specifiers) {\n if (specifier.type === \"ImportSpecifier\" && exportName(specifier.imported) === REQUIRE_FACTORY) {\n bindings.factories.add(specifier.local.name);\n }\n }\n};\n\nconst collectBinding = (node: ESTree.VariableDeclarator, bindings: Bindings): void => {\n const { id, init } = node;\n\n if (init === null || id.type !== \"Identifier\") {\n return;\n }\n\n if (isMetaUrl(init, bindings)) {\n bindings.urls.add(id.name);\n }\n\n if (isRequireFactory(init, bindings)) {\n bindings.requires.add(id.name);\n }\n};\n\nconst collectSource = (scan: Scan, source: string | null): void => {\n if (source !== null) {\n scan.sources.push(source);\n }\n};\n\nconst collectCall = (scan: Scan, node: ESTree.CallExpression): void => {\n if (node.arguments.some((argument) => literalString(argument) !== null)) {\n scan.calls.push(node);\n }\n};\n\nconst scanVisitor = (scan: Scan): VisitorObject => ({\n CallExpression: (node) => {\n collectCall(scan, node);\n },\n ExportAllDeclaration: (node) => {\n collectSource(scan, node.source.value);\n },\n ExportNamedDeclaration: (node) => {\n collectSource(scan, node.source?.value ?? null);\n },\n ImportDeclaration: (node) => {\n collectFactories(node, scan.bindings);\n collectSource(scan, node.source.value);\n },\n ImportExpression: (node) => {\n collectSource(scan, literalString(node.source));\n },\n VariableDeclarator: (node) => {\n collectBinding(node, scan.bindings);\n },\n});\n\nconst scanChunk = (chunk: Chunk): Scan => {\n const scan: Scan = {\n bindings: { declarations: new Map(), factories: new Set(), requires: new Set(), urls: new Set() },\n calls: [],\n sources: [],\n };\n\n const { program } = parseSync(chunk.fileName, chunk.code);\n new Visitor(declarationVisitor(scan.bindings.declarations)).visit(program);\n new Visitor(scanVisitor(scan)).visit(program);\n\n return scan;\n};\n\nconst callSpecifiers = (scan: Scan): string[] =>\n scan.calls\n .filter((call) => isResolvingCall(call, scan.bindings))\n .flatMap((call) => call.arguments)\n .map((argument) => literalString(argument))\n .filter((specifier) => specifier !== null);\n\nconst isReachable = (specifier: string, directory: string, emitted: Set<string>): boolean => {\n if (isBuiltin(specifier)) {\n return true;\n }\n\n if (!RELATIVE_SPECIFIER.test(specifier)) {\n return false;\n }\n\n const target = posix.normalize(posix.join(directory, specifier));\n\n return target === OUTPUT_DIRECTORY || emitted.has(target);\n};\n\nconst unreachableSpecifiers = (chunk: Chunk, emitted: Set<string>): string[] => {\n const scan = scanChunk(chunk);\n const directory = posix.dirname(chunk.fileName);\n\n return new Set([...scan.sources, ...callSpecifiers(scan)])\n .values()\n .filter((specifier) => !isReachable(specifier, directory, emitted))\n .toArray()\n .toSorted((left, right) => left.localeCompare(right));\n};\n\nconst assertSelfContained = (chunk: Chunk, emitted: Set<string>): void => {\n const specifiers = unreachableSpecifiers(chunk, emitted);\n\n if (specifiers.length === 0) {\n return;\n }\n\n throw new Error(\n [\n `${chunk.fileName} resolves ${specifiers.join(\", \")} at runtime,`,\n \"so the built app only starts where that resolution succeeds from wherever it was installed.\",\n \"The artifact may resolve node: builtins and the files the build emits beside it, nothing else:\",\n \"bundle the module, emit the file, or read the data at build time.\",\n ].join(\" \"),\n );\n};\n\nfunction gtkxSelfContained(): Plugin {\n return {\n name: \"gtkx:self-contained\",\n apply: \"build\",\n\n generateBundle(_options, bundle) {\n const emitted = new Set(Object.keys(bundle));\n\n for (const output of Object.values(bundle)) {\n if (output.type === \"chunk\") {\n assertSelfContained({ fileName: output.fileName, code: output.code }, emitted);\n }\n }\n },\n };\n}\n\nexport { gtkxSelfContained };\n"]}
1
+ {"version":3,"file":"self-contained.js","sourceRoot":"","sources":["../../src/vite-plugins/self-contained.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Plugin } from \"vite\";\nimport { type NodePath, parseSync, type Scope, traverse } from \"@babel/core\";\nimport { isBuiltin } from \"node:module\";\nimport { posix } from \"node:path\";\n\ntype BindingKind = \"factory\" | \"module\" | \"require\" | \"url\";\n\ntype ResolvedBinding = NonNullable<ReturnType<Scope[\"getBinding\"]>>;\n\ntype Scan = {\n sources: string[];\n};\n\ntype Chunk = {\n fileName: string;\n code: string;\n};\n\nconst REQUIRE_FACTORY = \"createRequire\";\nconst REQUIRE_BINDING = \"require\";\nconst RESOLVE_PROPERTY = \"resolve\";\nconst URL_PROPERTY = \"url\";\nconst MODULE_BUILTINS = new Set([\"module\", \"node:module\"]);\nconst OUTPUT_DIRECTORY = \".\";\nconst RELATIVE_SPECIFIER = /^\\.\\.?(?:\\/|$)/;\n\nconst importedName = (path: NodePath): string | null => {\n if (!path.isImportSpecifier()) {\n return null;\n }\n\n const { imported } = path.node;\n\n return imported.type === \"Identifier\" ? imported.name : imported.value;\n};\n\nconst importKind = (path: NodePath): BindingKind | null => {\n const declaration = path.parentPath;\n\n if (!declaration.isImportDeclaration() || !MODULE_BUILTINS.has(declaration.node.source.value)) {\n return null;\n }\n\n if (importedName(path) === REQUIRE_FACTORY) {\n return \"factory\";\n }\n\n return path.isImportNamespaceSpecifier() || path.isImportDefaultSpecifier() ? \"module\" : null;\n};\n\nconst memberName = (path: NodePath): string | null => {\n if (!path.isMemberExpression()) {\n return null;\n }\n\n const property = path.get(\"property\");\n\n if (path.node.computed) {\n return property.isStringLiteral() ? property.node.value : null;\n }\n\n return property.isIdentifier() ? property.node.name : null;\n};\n\nconst isImportMeta = (path: NodePath): boolean =>\n path.isMetaProperty() && path.node.meta.name === \"import\" && path.node.property.name === \"meta\";\n\nconst isDirectMetaUrl = (path: NodePath): boolean => {\n if (!path.isMemberExpression() || memberName(path) !== URL_PROPERTY) {\n return false;\n }\n\n const object = path.get(\"object\");\n\n return isImportMeta(object);\n};\n\nconst bindingKind = (binding: ResolvedBinding, seen: Set<ResolvedBinding>): BindingKind | null => {\n if (seen.has(binding)) {\n return null;\n }\n\n const next = new Set(seen).add(binding);\n const imported = importKind(binding.path);\n\n if (imported !== null) {\n return imported;\n }\n\n if (!binding.path.isVariableDeclarator()) {\n return null;\n }\n\n const initializer = binding.path.get(\"init\");\n\n return initializer.node === null ? null : expressionKind(initializer, next);\n};\n\nconst nameKind = (scope: Scope, name: string, seen: Set<ResolvedBinding>): BindingKind | null => {\n const binding = scope.getBinding(name);\n\n if (binding !== undefined) {\n return bindingKind(binding, seen);\n }\n\n if (name === REQUIRE_FACTORY) {\n return \"factory\";\n }\n\n return name === REQUIRE_BINDING ? \"require\" : null;\n};\n\nconst isModuleExpression = (path: NodePath, seen: Set<ResolvedBinding>): boolean => {\n if (path.isIdentifier()) {\n return nameKind(path.scope, path.node.name, seen) === \"module\";\n }\n\n if (!path.isCallExpression()) {\n return false;\n }\n\n const [source] = path.get(\"arguments\");\n const callee = path.get(\"callee\");\n const sourceName = source === undefined ? null : literalString(source);\n\n return (\n sourceName !== null &&\n MODULE_BUILTINS.has(sourceName) &&\n isRequireExpression(callee, seen)\n );\n};\n\nconst isFactoryExpression = (path: NodePath, seen: Set<ResolvedBinding>): boolean => {\n if (path.isIdentifier()) {\n return nameKind(path.scope, path.node.name, seen) === \"factory\";\n }\n\n if (!path.isMemberExpression() || memberName(path) !== REQUIRE_FACTORY) {\n return false;\n }\n\n return isModuleExpression(path.get(\"object\"), seen);\n};\n\nconst isRequireFactoryCall = (path: NodePath, seen: Set<ResolvedBinding>): boolean => {\n if (!path.isCallExpression()) {\n return false;\n }\n\n const callee = path.get(\"callee\");\n\n return isFactoryExpression(callee, seen);\n};\n\nconst expressionKind = (path: NodePath, seen: Set<ResolvedBinding>): BindingKind | null => {\n if (isDirectMetaUrl(path)) {\n return \"url\";\n }\n\n if (path.isIdentifier()) {\n return nameKind(path.scope, path.node.name, seen);\n }\n\n if (isFactoryExpression(path, seen)) {\n return \"factory\";\n }\n\n if (isModuleExpression(path, seen)) {\n return \"module\";\n }\n\n return isRequireFactoryCall(path, seen) ? \"require\" : null;\n};\n\nconst isMetaUrl = (path: NodePath): boolean =>\n isDirectMetaUrl(path) ||\n (path.isIdentifier() && nameKind(path.scope, path.node.name, new Set()) === \"url\");\n\nconst isRequireExpression = (path: NodePath, seen: Set<ResolvedBinding> = new Set()): boolean =>\n isRequireFactoryCall(path, seen) ||\n (path.isIdentifier() && nameKind(path.scope, path.node.name, seen) === \"require\");\n\nconst hasMetaUrlArgument = (path: NodePath): boolean => {\n if (!path.isCallExpression()) {\n return false;\n }\n\n return path.get(\"arguments\").some((argument) => isMetaUrl(argument));\n};\n\nconst isResolveMember = (path: NodePath): boolean => {\n if (!path.isMemberExpression() || memberName(path) !== RESOLVE_PROPERTY) {\n return false;\n }\n\n const object = path.get(\"object\");\n\n return isImportMeta(object) || isRequireExpression(object);\n};\n\nconst isResolvingCall = (path: NodePath): boolean => {\n if (!path.isCallExpression()) {\n return false;\n }\n\n const callee = path.get(\"callee\");\n\n return hasMetaUrlArgument(path) || isRequireExpression(callee) || isResolveMember(callee);\n};\n\nconst literalString = (path: NodePath): string | null => {\n if (path.isStringLiteral()) {\n return path.node.value;\n }\n\n if (!path.isTemplateLiteral() || path.node.expressions.length > 0) {\n return null;\n }\n\n return path.node.quasis[0]?.value.cooked ?? null;\n};\n\nconst collectSource = (scan: Scan, source: string | null): void => {\n if (source !== null) {\n scan.sources.push(source);\n }\n};\n\nconst collectCallSources = (scan: Scan, path: NodePath): void => {\n if (!isResolvingCall(path) || !path.isCallExpression()) {\n return;\n }\n\n for (const argument of path.get(\"arguments\")) {\n collectSource(scan, literalString(argument));\n }\n};\n\nconst scanChunk = (chunk: Chunk): Scan => {\n const scan: Scan = { sources: [] };\n const ast = parseSync(chunk.code, {\n ast: true,\n babelrc: false,\n configFile: false,\n filename: chunk.fileName,\n sourceType: \"module\",\n });\n\n if (ast === null) {\n throw new Error(`Cannot inspect ${chunk.fileName}`);\n }\n\n traverse(ast, {\n CallExpression: (path) => {\n collectCallSources(scan, path);\n },\n ExportAllDeclaration: (path) => {\n collectSource(scan, path.node.source.value);\n },\n ExportNamedDeclaration: (path) => {\n collectSource(scan, path.node.source?.value ?? null);\n },\n ImportDeclaration: (path) => {\n collectSource(scan, path.node.source.value);\n },\n ImportExpression: (path) => {\n collectSource(scan, literalString(path.get(\"source\")));\n },\n });\n\n return scan;\n};\n\nconst isReachable = (specifier: string, directory: string, emitted: Set<string>): boolean => {\n if (isBuiltin(specifier)) {\n return true;\n }\n\n if (!RELATIVE_SPECIFIER.test(specifier)) {\n return false;\n }\n\n const target = posix.normalize(posix.join(directory, specifier));\n\n return target === OUTPUT_DIRECTORY || emitted.has(target);\n};\n\nconst unreachableSpecifiers = (chunk: Chunk, emitted: Set<string>): string[] => {\n const directory = posix.dirname(chunk.fileName);\n\n return new Set(scanChunk(chunk).sources)\n .values()\n .filter((specifier) => !isReachable(specifier, directory, emitted))\n .toArray()\n .toSorted((left, right) => left.localeCompare(right));\n};\n\nconst assertSelfContained = (chunk: Chunk, emitted: Set<string>): void => {\n const specifiers = unreachableSpecifiers(chunk, emitted);\n\n if (specifiers.length === 0) {\n return;\n }\n\n throw new Error(\n [\n `${chunk.fileName} resolves ${specifiers.join(\", \")} at runtime,`,\n \"so the built app only starts where that resolution succeeds from wherever it was installed.\",\n \"The artifact may resolve node: builtins and the files the build emits beside it, nothing else:\",\n \"bundle the module, emit the file, or read the data at build time.\",\n ].join(\" \"),\n );\n};\n\nfunction gtkxSelfContained(): Plugin {\n return {\n name: \"gtkx:self-contained\",\n apply: \"build\",\n\n generateBundle(_options, bundle) {\n const emitted = new Set(Object.keys(bundle));\n\n for (const output of Object.values(bundle)) {\n if (output.type === \"chunk\") {\n assertSelfContained({ fileName: output.fileName, code: output.code }, emitted);\n }\n }\n },\n };\n}\n\nexport { gtkxSelfContained };\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gtkx/cli",
3
- "version": "2.0.0-beta.1",
3
+ "version": "2.0.0-beta.2",
4
4
  "description": "GTK app toolchain for React: scaffold, dev server, build, docs.",
5
5
  "keywords": [
6
6
  "gtkx",
@@ -70,16 +70,16 @@
70
70
  "dependencies": {
71
71
  "@babel/core": "^8.0.1",
72
72
  "@babel/preset-typescript": "^8.0.1",
73
- "@gtkx/codegen": "2.0.0-beta.1",
74
- "@gtkx/config": "2.0.0-beta.1",
75
- "@gtkx/mcp": "2.0.0-beta.1",
76
- "@gtkx/runtime": "2.0.0-beta.1",
77
- "@gtkx/utils": "2.0.0-beta.1",
78
- "@gtkx/vitest": "2.0.0-beta.1",
73
+ "@gtkx/codegen": "2.0.0-beta.2",
74
+ "@gtkx/config": "2.0.0-beta.2",
75
+ "@gtkx/mcp": "2.0.0-beta.2",
76
+ "@gtkx/runtime": "2.0.0-beta.2",
77
+ "@gtkx/utils": "2.0.0-beta.2",
78
+ "@gtkx/vitest": "2.0.0-beta.2",
79
79
  "@swc/core": "^1.16.1",
80
80
  "babel-plugin-react-compiler": "^1.0.0",
81
81
  "citty": "^0.2.2",
82
- "create-gtkx": "2.0.0-beta.1",
82
+ "create-gtkx": "2.0.0-beta.2",
83
83
  "fast-xml-builder": "^1.3.1",
84
84
  "fast-xml-parser": "^5.11.1",
85
85
  "hosted-git-info": "^10.1.1",
@@ -89,7 +89,7 @@
89
89
  "yaml": "^2.9.0"
90
90
  },
91
91
  "devDependencies": {
92
- "@gtkx/testing": "2.0.0-beta.1",
92
+ "@gtkx/testing": "2.0.0-beta.2",
93
93
  "@types/babel__core": "^7.20.5",
94
94
  "@types/hosted-git-info": "^3.0.5",
95
95
  "@types/react-refresh": "^0.14.7",
package/src/builder.ts CHANGED
@@ -1,6 +1,7 @@
1
- import { join, posix } from "node:path";
1
+ import { loadConfig } from "@gtkx/config";
2
+ import { join, posix, relative, resolve } from "node:path";
2
3
  import { type InlineConfig, mergeConfig, build as viteBuild } from "vite";
3
- import { createBuildManifestCollector } from "./internal/build-manifest.js";
4
+ import { configDigest, createBuildManifestCollector } from "./internal/build-manifest.js";
4
5
  import { gtkxBuildManifest } from "./vite-plugins/build-manifest.js";
5
6
  import { BUNDLE_FILENAME, ESM_EXTENSION } from "./vite-plugins/esm-extension.js";
6
7
  import { gtkxVitePlugins } from "./vite-plugins/index.js";
@@ -10,6 +11,7 @@ import { gtkxWorker } from "./vite-plugins/worker.js";
10
11
 
11
12
  type BuildOptions = {
12
13
  entry: string;
14
+ configFile?: string | undefined;
13
15
  shouldPreserveI18nMetadata?: boolean | undefined;
14
16
  vite?: InlineConfig | undefined;
15
17
  };
@@ -34,16 +36,27 @@ const buildDefaults: InlineConfig = {
34
36
 
35
37
  const build = async (options: BuildOptions): Promise<string> => {
36
38
  const { entry, shouldPreserveI18nMetadata = true, vite: viteConfig } = options;
37
- const root = viteConfig?.root ?? process.cwd();
39
+ const root = resolve(viteConfig?.root ?? process.cwd());
38
40
  const assetsDir = viteConfig?.build?.assetsDir ?? DEFAULT_ASSETS_DIR;
39
41
  const buildManifest = createBuildManifestCollector();
42
+ const loadedConfig = await loadConfig(root, { mode: BUILD_MODE, configFile: options.configFile });
43
+ const buildConfigIdentity = {
44
+ configFile: posix.normalize(relative(root, loadedConfig.configFile).replaceAll("\\", "/")),
45
+ configDigest: configDigest(loadedConfig.config),
46
+ };
40
47
 
41
48
  const forced: InlineConfig = {
42
49
  plugins: [
43
- ...gtkxVitePlugins(BUILD_MODE, entry, buildManifest, shouldPreserveI18nMetadata),
50
+ ...gtkxVitePlugins({
51
+ mode: BUILD_MODE,
52
+ entryPath: entry,
53
+ buildManifest,
54
+ shouldPreserveI18nMetadata,
55
+ configFile: options.configFile,
56
+ }),
44
57
  gtkxWorker(),
45
58
  gtkxNative(root),
46
- gtkxBuildManifest(root, buildManifest),
59
+ gtkxBuildManifest(root, buildManifest, buildConfigIdentity),
47
60
  gtkxSelfContained(),
48
61
  ],
49
62
  build: {
package/src/cli.ts CHANGED
@@ -1,8 +1,11 @@
1
+ import { assertSupportedNodeVersion } from "@gtkx/config/internal";
1
2
  import { defineCommand, runMain } from "citty";
2
3
  import packageManifest from "../package.json" with { type: "json" };
3
4
  import { splitApplicationArgs } from "./internal/application-args.js";
4
5
  import { withErrorBoundary } from "./internal/errors.js";
5
6
 
7
+ assertSupportedNodeVersion();
8
+
6
9
  const version = packageManifest.version;
7
10
  const { cliArgs } = splitApplicationArgs(process.argv.slice(2));
8
11
 
@@ -24,6 +24,7 @@ import { type CodegenContext, type CodegenStore, resolveCodegenContext } from ".
24
24
  type RunCodegenOptions = {
25
25
  cwd?: string;
26
26
  mode?: string | undefined;
27
+ configFile?: string | undefined;
27
28
  isForced?: boolean;
28
29
  inputs?: CodegenInputs;
29
30
  resolved?: LoadedConfig;
@@ -58,6 +59,7 @@ type PreparedCodegen = CodegenInputs & { isForced: boolean };
58
59
  type EnsureGeneratedOptions = {
59
60
  shouldAnnounce?: boolean;
60
61
  mode?: string;
62
+ configFile?: string | undefined;
61
63
  shouldPreserveI18nMetadata?: boolean | undefined;
62
64
  };
63
65
 
@@ -131,7 +133,10 @@ const prepareCodegen = (options: RunCodegenOptions, cwd: string, config: Config)
131
133
 
132
134
  const runCodegen = async (options: RunCodegenOptions = {}): Promise<RunCodegenResult> => {
133
135
  const cwd = options.cwd ?? process.cwd();
134
- const { config, configFile } = options.resolved ?? (await loadConfig(cwd, { mode: options.mode }));
136
+ const { config, configFile } = options.resolved ?? (await loadConfig(cwd, {
137
+ mode: options.mode,
138
+ configFile: options.configFile,
139
+ }));
135
140
  await syncI18n(cwd, config.applicationId, options.shouldPreserveI18nMetadata);
136
141
  emitSchemaEnv(cwd);
137
142
 
@@ -190,9 +195,9 @@ const syncI18n = async (
190
195
  await emitI18nTypes(root);
191
196
  };
192
197
 
193
- const isCodegenDisabled = async (cwd: string, mode?: string): Promise<boolean> => {
198
+ const isCodegenDisabled = async (cwd: string, mode?: string, configFile?: string): Promise<boolean> => {
194
199
  try {
195
- const { config } = await loadConfig(cwd, { mode });
200
+ const { config } = await loadConfig(cwd, { mode, configFile });
196
201
 
197
202
  return config.codegen === false;
198
203
  } catch {
@@ -257,18 +262,21 @@ const ensureGeneratedIn = async (
257
262
 
258
263
  /* eslint-disable-next-line unicorn/consistent-boolean-name -- the boolean reports whether codegen ran */
259
264
  const ensureGenerated = async (cwd: string, options: EnsureGeneratedOptions = {}): Promise<boolean> =>
260
- isPreflightSkipped(options) ? false : generate(await resolveCodegenContext(cwd, options.mode), options);
265
+ isPreflightSkipped(options)
266
+ ? false
267
+ : generate(await resolveCodegenContext(cwd, options.mode, options.configFile), options);
261
268
 
262
269
  const resolveConfigWatch = async (
263
270
  cwd: string,
264
271
  mode?: string,
272
+ configFile?: string,
265
273
  ): Promise<{ paths: string[]; regenerate: () => Promise<void> }> => {
266
- const { configFile, root } = await loadConfig(cwd, { mode });
274
+ const loaded = await loadConfig(cwd, { mode, configFile });
267
275
 
268
276
  return {
269
- paths: [resolve(root, configFile)],
277
+ paths: [resolve(loaded.root, loaded.configFile)],
270
278
  regenerate: async () => {
271
- await runCodegen({ cwd: root, mode });
279
+ await runCodegen({ cwd: loaded.root, mode, configFile: loaded.configFile });
272
280
  },
273
281
  };
274
282
  };
@@ -61,8 +61,8 @@ const resolveCodegenStore = (dir: string): CodegenStore => {
61
61
  };
62
62
  };
63
63
 
64
- const resolveCodegenContext = async (cwd: string, mode?: string): Promise<CodegenContext> => {
65
- const { config, configFile } = await loadConfig(cwd, { mode });
64
+ const resolveCodegenContext = async (cwd: string, mode?: string, selectedConfig?: string): Promise<CodegenContext> => {
65
+ const { config, configFile } = await loadConfig(cwd, { mode, configFile: selectedConfig });
66
66
 
67
67
  return { root: cwd, config, configFile };
68
68
  };