@gxp-dev/tools 2.0.43 → 2.0.46

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.
@@ -45,7 +45,10 @@ if (!isOneShot) {
45
45
  // TUI output is in project root's dist/tui, not bin/dist/tui
46
46
  const tuiPath = path.join(__dirname, '..', 'dist', 'tui', 'index.js');
47
47
 
48
- if (fs.existsSync(tuiPath)) {
48
+ // Check if we're in an interactive terminal (TTY); fall back to CLI if not
49
+ const isTTY = process.stdout.isTTY && process.stdin.isTTY;
50
+
51
+ if (fs.existsSync(tuiPath) && isTTY) {
49
52
  // Use dynamic import() for ESM modules (ink v5 is ESM-only)
50
53
  (async () => {
51
54
  try {
@@ -71,11 +74,16 @@ if (!isOneShot) {
71
74
 
72
75
  startTUI({ autoStart, args: tuiArgs });
73
76
  } catch (err) {
74
- // TUI dependencies not available, fall back to traditional CLI
75
- console.error('TUI error:', err.message);
77
+ // TUI not available or no TTY — fall back to traditional CLI
78
+ if (err.message !== 'NO_TTY') {
79
+ console.error('TUI error:', err.message);
80
+ }
76
81
  require("./lib/cli");
77
82
  }
78
83
  })();
84
+ } else if (!isTTY) {
85
+ // Non-interactive shell — skip TUI and run directly
86
+ require("./lib/cli");
79
87
  } else {
80
88
  // TUI not compiled yet, use traditional CLI
81
89
  console.log('Note: TUI not yet available. Run "npm run build:tui" to enable interactive mode.');
@@ -34,7 +34,7 @@ const REQUIRED_DEV_DEPENDENCIES = {
34
34
 
35
35
  // Default scripts for package.json
36
36
  const DEFAULT_SCRIPTS = {
37
- dev: "gxdev dev --with-socket",
37
+ dev: "gxdev dev",
38
38
  "dev-app": "gxdev dev",
39
39
  "dev-http": "gxdev dev --no-https",
40
40
  build: "gxdev build",
@@ -26,17 +26,7 @@ export function startTUI(options: TUIOptions = {}) {
26
26
  // If stdin doesn't support raw mode, we need to handle it gracefully
27
27
  // Ink 5.x uses stdin by default and requires raw mode for input
28
28
  if (!stdinIsTTY) {
29
- console.error('Warning: Terminal does not support interactive mode.');
30
- console.error('The TUI requires an interactive terminal (TTY) to function.');
31
- console.error('');
32
- console.error('Try running the command directly from your terminal, not from a script or pipe.');
33
- console.error('');
34
- console.error('Alternatively, use the non-TUI commands:');
35
- console.error(' npm run dev # Start Vite dev server');
36
- console.error(' npm run dev-http # Start HTTP dev server');
37
- console.error(' gxdev socket list # List socket events');
38
- process.exit(1);
39
- return;
29
+ throw new Error('NO_TTY');
40
30
  }
41
31
 
42
32
  const { waitUntilExit } = render(
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../bin/lib/tui/index.tsx"],"names":[],"mappings":";AAWA,UAAU,UAAU;IAClB,SAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAChC;AAED,wBAAgB,QAAQ,CAAC,OAAO,GAAE,UAAe,QAqChD;AASD,eAAe,QAAQ,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../bin/lib/tui/index.tsx"],"names":[],"mappings":";AAWA,UAAU,UAAU;IAClB,SAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAChC;AAED,wBAAgB,QAAQ,CAAC,OAAO,GAAE,UAAe,QA2BhD;AASD,eAAe,QAAQ,CAAC"}
package/dist/tui/index.js CHANGED
@@ -18,17 +18,7 @@ export function startTUI(options = {}) {
18
18
  // If stdin doesn't support raw mode, we need to handle it gracefully
19
19
  // Ink 5.x uses stdin by default and requires raw mode for input
20
20
  if (!stdinIsTTY) {
21
- console.error('Warning: Terminal does not support interactive mode.');
22
- console.error('The TUI requires an interactive terminal (TTY) to function.');
23
- console.error('');
24
- console.error('Try running the command directly from your terminal, not from a script or pipe.');
25
- console.error('');
26
- console.error('Alternatively, use the non-TUI commands:');
27
- console.error(' npm run dev # Start Vite dev server');
28
- console.error(' npm run dev-http # Start HTTP dev server');
29
- console.error(' gxdev socket list # List socket events');
30
- process.exit(1);
31
- return;
21
+ throw new Error('NO_TTY');
32
22
  }
33
23
  const { waitUntilExit } = render(_jsx(App, { autoStart: options.autoStart, args: options.args }));
34
24
  waitUntilExit().then(() => {
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../bin/lib/tui/index.tsx"],"names":[],"mappings":";;AAEA,OAAO,EAAE,MAAM,EAAE,MAAM,KAAK,CAAC;AAC7B,OAAO,MAAM,MAAM,QAAQ,CAAC;AAC5B,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,GAAG,MAAM,UAAU,CAAC;AAC3B,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AAErD,mEAAmE;AACnE,MAAM,CAAC,MAAM,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,MAAM,CAAC,EAAE,CAAC,CAAC;AAO1D,MAAM,UAAU,QAAQ,CAAC,UAAsB,EAAE;IAC/C,qEAAqE;IACrE,sBAAsB;IACtB,+BAA+B;IAC/B,qCAAqC;IACrC,4BAA4B;IAC5B,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC;IAC5B,MAAM,UAAU,GAAG,KAAK,CAAC,KAAK,KAAK,IAAI,CAAC;IAExC,qEAAqE;IACrE,gEAAgE;IAChE,IAAI,CAAC,UAAU,EAAE,CAAC;QAChB,OAAO,CAAC,KAAK,CAAC,sDAAsD,CAAC,CAAC;QACtE,OAAO,CAAC,KAAK,CAAC,6DAA6D,CAAC,CAAC;QAC7E,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;QAClB,OAAO,CAAC,KAAK,CAAC,iFAAiF,CAAC,CAAC;QACjG,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;QAClB,OAAO,CAAC,KAAK,CAAC,0CAA0C,CAAC,CAAC;QAC1D,OAAO,CAAC,KAAK,CAAC,8CAA8C,CAAC,CAAC;QAC9D,OAAO,CAAC,KAAK,CAAC,8CAA8C,CAAC,CAAC;QAC9D,OAAO,CAAC,KAAK,CAAC,4CAA4C,CAAC,CAAC;QAC5D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChB,OAAO;IACT,CAAC;IAED,MAAM,EAAE,aAAa,EAAE,GAAG,MAAM,CAC9B,KAAC,GAAG,IACF,SAAS,EAAE,OAAO,CAAC,SAAS,EAC5B,IAAI,EAAE,OAAO,CAAC,IAAI,GAClB,CACH,CAAC;IAEF,aAAa,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE;QACxB,iDAAiD;QACjD,cAAc,CAAC,YAAY,EAAE,CAAC;QAC9B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC,CAAC;AACL,CAAC;AAED,kCAAkC;AAClC,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AACpC,MAAM,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AACrF,IAAI,MAAM,EAAE,CAAC;IACX,QAAQ,EAAE,CAAC;AACb,CAAC;AAED,eAAe,QAAQ,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../bin/lib/tui/index.tsx"],"names":[],"mappings":";;AAEA,OAAO,EAAE,MAAM,EAAE,MAAM,KAAK,CAAC;AAC7B,OAAO,MAAM,MAAM,QAAQ,CAAC;AAC5B,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,GAAG,MAAM,UAAU,CAAC;AAC3B,OAAO,EAAE,cAAc,EAAE,MAAM,qBAAqB,CAAC;AAErD,mEAAmE;AACnE,MAAM,CAAC,MAAM,CAAC,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,MAAM,CAAC,EAAE,CAAC,CAAC;AAO1D,MAAM,UAAU,QAAQ,CAAC,UAAsB,EAAE;IAC/C,qEAAqE;IACrE,sBAAsB;IACtB,+BAA+B;IAC/B,qCAAqC;IACrC,4BAA4B;IAC5B,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC;IAC5B,MAAM,UAAU,GAAG,KAAK,CAAC,KAAK,KAAK,IAAI,CAAC;IAExC,qEAAqE;IACrE,gEAAgE;IAChE,IAAI,CAAC,UAAU,EAAE,CAAC;QAChB,MAAM,IAAI,KAAK,CAAC,QAAQ,CAAC,CAAC;IAC5B,CAAC;IAED,MAAM,EAAE,aAAa,EAAE,GAAG,MAAM,CAC9B,KAAC,GAAG,IACF,SAAS,EAAE,OAAO,CAAC,SAAS,EAC5B,IAAI,EAAE,OAAO,CAAC,IAAI,GAClB,CACH,CAAC;IAEF,aAAa,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE;QACxB,iDAAiD;QACjD,cAAc,CAAC,YAAY,EAAE,CAAC;QAC9B,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC,CAAC;AACL,CAAC;AAED,kCAAkC;AAClC,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AACpC,MAAM,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AACrF,IAAI,MAAM,EAAE,CAAC;IACX,QAAQ,EAAE,CAAC;AACb,CAAC;AAED,eAAe,QAAQ,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gxp-dev/tools",
3
- "version": "2.0.43",
3
+ "version": "2.0.46",
4
4
  "description": "Dev tools to create platform plugins",
5
5
  "type": "commonjs",
6
6
  "publishConfig": {
@@ -35,7 +35,9 @@ import { watch } from "vue";
35
35
  * @param {Object} store - The GxP Pinia store instance
36
36
  * @returns {Object} Vue plugin
37
37
  */
38
- export function createGxpStringsPlugin(store) {
38
+ export function createGxpStringsPlugin(store, options = {}) {
39
+ const devServerBaseUrl = (options.devServerBaseUrl || "").replace(/\/+$/, "");
40
+
39
41
  return {
40
42
  install(app) {
41
43
  // Register the v-gxp-string directive
@@ -98,7 +100,7 @@ export function createGxpStringsPlugin(store) {
98
100
  el._gxpSrcKey = key;
99
101
 
100
102
  // Initial update
101
- updateElementSrc(el, key, defaultSrc, store);
103
+ updateElementSrc(el, key, defaultSrc, store, devServerBaseUrl);
102
104
 
103
105
  // Watch for changes in the appropriate store based on attributes
104
106
  // Using deep: true to catch when entire object is replaced (async manifest load)
@@ -106,7 +108,7 @@ export function createGxpStringsPlugin(store) {
106
108
  const watchSource = getSrcWatchSource(el, key, store);
107
109
  if (watchSource) {
108
110
  el._gxpSrcUnwatch = watch(watchSource, () => {
109
- updateElementSrc(el, key, defaultSrc, store);
111
+ updateElementSrc(el, key, defaultSrc, store, devServerBaseUrl);
110
112
  }, { deep: true });
111
113
  }
112
114
  }
@@ -118,7 +120,7 @@ export function createGxpStringsPlugin(store) {
118
120
  if (!key) return;
119
121
 
120
122
  const defaultSrc = el._gxpSrcDefault || el.getAttribute("src") || "";
121
- updateElementSrc(el, key, defaultSrc, store);
123
+ updateElementSrc(el, key, defaultSrc, store, devServerBaseUrl);
122
124
  },
123
125
 
124
126
  // Cleanup when element is unmounted
@@ -139,7 +141,7 @@ export function createGxpStringsPlugin(store) {
139
141
  mounted() {
140
142
  this.$nextTick(() => {
141
143
  processGxpStringAttributes(this.$el, store);
142
- processGxpSrcAttributes(this.$el, store);
144
+ processGxpSrcAttributes(this.$el, store, devServerBaseUrl);
143
145
  });
144
146
 
145
147
  // Watch for manifest loading to re-process attributes
@@ -151,7 +153,7 @@ export function createGxpStringsPlugin(store) {
151
153
  if (loaded) {
152
154
  this.$nextTick(() => {
153
155
  reprocessGxpStringAttributes(rootEl, store);
154
- reprocessGxpSrcAttributes(rootEl, store);
156
+ reprocessGxpSrcAttributes(rootEl, store, devServerBaseUrl);
155
157
  });
156
158
  }
157
159
  }
@@ -161,7 +163,7 @@ export function createGxpStringsPlugin(store) {
161
163
  updated() {
162
164
  this.$nextTick(() => {
163
165
  processGxpStringAttributes(this.$el, store);
164
- processGxpSrcAttributes(this.$el, store);
166
+ processGxpSrcAttributes(this.$el, store, devServerBaseUrl);
165
167
  });
166
168
  },
167
169
  unmounted() {
@@ -260,11 +262,25 @@ function updateElementText(el, key, defaultValue, store) {
260
262
  }
261
263
  }
262
264
 
265
+ /**
266
+ * Resolve a default src path against the dev server base URL.
267
+ * Only applies to relative paths (starting with /) when a devServerBaseUrl is configured.
268
+ * Store-returned values are never prefixed — they are already absolute.
269
+ */
270
+ function resolveDefaultSrc(defaultSrc, devServerBaseUrl) {
271
+ if (!devServerBaseUrl || !defaultSrc) return defaultSrc;
272
+ // Only prefix relative paths, not already-absolute URLs
273
+ if (defaultSrc.startsWith("/") && !defaultSrc.startsWith("//")) {
274
+ return devServerBaseUrl + defaultSrc;
275
+ }
276
+ return defaultSrc;
277
+ }
278
+
263
279
  /**
264
280
  * Update element src attribute based on store value
265
281
  * Uses triggerState if gxp-state attribute is present, otherwise assetList
266
282
  */
267
- function updateElementSrc(el, key, defaultSrc, store) {
283
+ function updateElementSrc(el, key, defaultSrc, store, devServerBaseUrl) {
268
284
  if (!store) {
269
285
  return;
270
286
  }
@@ -279,7 +295,7 @@ function updateElementSrc(el, key, defaultSrc, store) {
279
295
  if (srcUrl && srcUrl !== defaultSrc) {
280
296
  el.setAttribute("src", srcUrl);
281
297
  } else if (defaultSrc) {
282
- el.setAttribute("src", defaultSrc);
298
+ el.setAttribute("src", resolveDefaultSrc(defaultSrc, devServerBaseUrl));
283
299
  }
284
300
  }
285
301
 
@@ -343,7 +359,7 @@ function reprocessGxpStringAttributes(rootEl, store) {
343
359
  * Process all elements with gxp-src attribute in a subtree
344
360
  * This handles elements that use the raw attribute without the v- directive
345
361
  */
346
- function processGxpSrcAttributes(rootEl, store) {
362
+ function processGxpSrcAttributes(rootEl, store, devServerBaseUrl) {
347
363
  if (!rootEl || !store) return;
348
364
 
349
365
  // Handle case where rootEl is a text node or comment
@@ -362,14 +378,14 @@ function processGxpSrcAttributes(rootEl, store) {
362
378
  el._gxpSrcKey = key;
363
379
 
364
380
  // Update src
365
- updateElementSrc(el, key, el._gxpSrcDefault, store);
381
+ updateElementSrc(el, key, el._gxpSrcDefault, store, devServerBaseUrl);
366
382
 
367
383
  // Set up watcher for this element (if not already watching)
368
384
  if (!el._gxpSrcUnwatch) {
369
385
  const watchSource = getSrcWatchSource(el, key, store);
370
386
  if (watchSource) {
371
387
  el._gxpSrcUnwatch = watch(watchSource, () => {
372
- updateElementSrc(el, key, el._gxpSrcDefault, store);
388
+ updateElementSrc(el, key, el._gxpSrcDefault, store, devServerBaseUrl);
373
389
  }, { deep: true });
374
390
  }
375
391
  }
@@ -380,7 +396,7 @@ function processGxpSrcAttributes(rootEl, store) {
380
396
  * Re-process all elements with gxp-src attribute in a subtree
381
397
  * This is called when manifest loads to update elements that were already processed
382
398
  */
383
- function reprocessGxpSrcAttributes(rootEl, store) {
399
+ function reprocessGxpSrcAttributes(rootEl, store, devServerBaseUrl) {
384
400
  if (!rootEl || !store) return;
385
401
  if (!rootEl.querySelectorAll) return;
386
402
 
@@ -391,7 +407,7 @@ function reprocessGxpSrcAttributes(rootEl, store) {
391
407
  if (!key) return;
392
408
 
393
409
  const defaultSrc = el._gxpSrcDefault || el.getAttribute("src") || "";
394
- updateElementSrc(el, key, defaultSrc, store);
410
+ updateElementSrc(el, key, defaultSrc, store, devServerBaseUrl);
395
411
  });
396
412
  }
397
413
 
@@ -407,8 +423,8 @@ export function processGxpStrings(rootElement, store) {
407
423
  * Standalone function to process gxp-src attributes
408
424
  * Can be called manually if needed
409
425
  */
410
- export function processGxpSrcs(rootElement, store) {
411
- processGxpSrcAttributes(rootElement, store);
426
+ export function processGxpSrcs(rootElement, store, devServerBaseUrl) {
427
+ processGxpSrcAttributes(rootElement, store, devServerBaseUrl);
412
428
  }
413
429
 
414
430
  /**
package/runtime/main.js CHANGED
@@ -24,7 +24,15 @@ async function init() {
24
24
  app.use(pinia);
25
25
 
26
26
  const gxpStore = useGxpStore();
27
- app.use(createGxpStringsPlugin(gxpStore));
27
+
28
+ // Build the dev server base URL so gxp-src default paths resolve to the
29
+ // local dev server instead of the current domain (important when the app
30
+ // is injected into the cloud platform via browser extension).
31
+ const devProtocol = import.meta.env.VITE_USE_HTTPS !== "false" ? "https" : "http";
32
+ const devPort = import.meta.env.VITE_NODE_PORT || "3060";
33
+ const devServerBaseUrl = `${devProtocol}://localhost:${devPort}`;
34
+
35
+ app.use(createGxpStringsPlugin(gxpStore, { devServerBaseUrl }));
28
36
 
29
37
  app.mount("#app");
30
38
  }
package/template/main.js CHANGED
@@ -24,7 +24,15 @@ async function init() {
24
24
  app.use(pinia);
25
25
 
26
26
  const gxpStore = useGxpStore();
27
- app.use(createGxpStringsPlugin(gxpStore));
27
+
28
+ // Build the dev server base URL so gxp-src default paths resolve to the
29
+ // local dev server instead of the current domain (important when the app
30
+ // is injected into the cloud platform via browser extension).
31
+ const devProtocol = import.meta.env.VITE_USE_HTTPS !== "false" ? "https" : "http";
32
+ const devPort = import.meta.env.VITE_NODE_PORT || "3060";
33
+ const devServerBaseUrl = `${devProtocol}://localhost:${devPort}`;
34
+
35
+ app.use(createGxpStringsPlugin(gxpStore, { devServerBaseUrl }));
28
36
 
29
37
  app.mount("#app");
30
38
  }