@floless/app 0.6.2 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/web/aware.js CHANGED
@@ -651,7 +651,12 @@
651
651
  function reportNodeId() {
652
652
  const app = currentId && apps.get(currentId);
653
653
  if (!app || !app.nodes.length) return null;
654
- // Qualify the app only if some node actually PRODUCES report HTML — its exec
654
+ // An html-report agent node renders report HTML — its `render` command returns
655
+ // an `html` field, which is exactly what extractReportHtml keys on. So it's a
656
+ // report producer regardless of exec code; prefer it directly as the viewer node.
657
+ const htmlReportNode = app.nodes.find((n) => n.agent === 'html-report');
658
+ if (htmlReportNode) return htmlReportNode.id;
659
+ // Otherwise, qualify the app only if some node actually PRODUCES report HTML — its exec
655
660
  // code returns an `html` field (the `data.result.html` extractReportHtml keys
656
661
  // on), or it forwards `{{ <node>.result.html }}` through its args (a
657
662
  // pass-through viewer). "any node has exec code" is NOT enough: a plain
@@ -2585,7 +2590,7 @@
2585
2590
  <div class="int-icon">${escapeHtml(VENDOR_ICON[i.vendor] || (i.name[0] || '?'))}</div>
2586
2591
  <div class="int-info">
2587
2592
  <div class="int-name">${escapeHtml(i.name)}</div>
2588
- <div class="int-kind">${escapeHtml(i.vendor || 'integration')} · agent <code>${escapeHtml(i.agent)}</code></div>
2593
+ <div class="int-kind">${i.agent === 'first-party' ? 'Built-in integration' : `${escapeHtml(i.vendor || 'integration')} · agent <code>${escapeHtml(i.agent)}</code>`}</div>
2589
2594
  <div class="int-scopes">${escapeHtml((i.network || []).join(' · ') || '—')}</div>
2590
2595
  <div class="int-meta">${escapeHtml(meta)}</div>
2591
2596
  <div class="int-row">
@@ -2636,6 +2641,10 @@
2636
2641
  if (slot) slot.innerHTML = 'Starting sign-in…';
2637
2642
  try {
2638
2643
  const res = await api(`/api/connect/${encodeURIComponent(id)}`, { method: 'POST', body });
2644
+ // A managed-preset pre-flight (e.g. port 80 already in use) refuses to start
2645
+ // and broadcasts the reason over SSE (connect-result). Clear the guard so the
2646
+ // user can retry after fixing it, and don't claim the browser opened.
2647
+ if (res && res.started === false) { connecting.delete(id); return; }
2639
2648
  if (slot) {
2640
2649
  if (res.flow === 'device-code' && res.prompt) {
2641
2650
  // Fallback flow: show the device code to enter at the verification URL.
package/launch.mjs CHANGED
@@ -123,7 +123,11 @@ function startServerDetached() {
123
123
  }
124
124
 
125
125
  function openBrowser(url) {
126
- if (isWin) spawn('cmd', ['/c', 'start', '', url], { windowsHide: true, detached: true }).unref();
126
+ // NO `detached` on Windows: Node #21825 makes `detached` defeat `windowsHide` for a CUI
127
+ // child (cmd.exe), flashing a console window. Without it, windowsHide hides cmd; `start`
128
+ // hands the URL to the browser via ShellExecute (independent of cmd's tree), so the browser
129
+ // still survives this launcher exiting. unref() keeps it from holding the event loop.
130
+ if (isWin) spawn('cmd', ['/c', 'start', '', url], { windowsHide: true }).unref();
127
131
  else spawn(process.platform === 'darwin' ? 'open' : 'xdg-open', [url], { detached: true }).unref();
128
132
  }
129
133
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@floless/app",
3
- "version": "0.6.2",
3
+ "version": "0.7.0",
4
4
  "type": "module",
5
5
  "description": "Thin localhost host for floless.app — serves web/ and shells the aware CLI. No engine, no LLM.",
6
6
  "bin": {