@pugi/cli 0.1.0-beta.2 → 0.1.0-beta.3

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.
@@ -47,7 +47,7 @@ import { dispatchEdit, } from '../core/edits/index.js';
47
47
  * packages/pugi-sdk/package.json); the publish workflow validates the
48
48
  * three are in lockstep.
49
49
  */
50
- const PUGI_CLI_VERSION = "0.1.0-beta.2";
50
+ const PUGI_CLI_VERSION = "0.1.0-beta.3";
51
51
  const handlers = {
52
52
  accounts,
53
53
  agents: dispatchAgents,
@@ -86,27 +86,31 @@ export async function renderRepl(options) {
86
86
  // Kick off the connect; the Repl renders the connecting state until
87
87
  // the session pushes `connection: 'on_watch'` from the SSE onOpen.
88
88
  void session.start();
89
- // α6.14.2 wave 5: paint the chafa-baked brand-pug ANSI render to
90
- // stdout BEFORE Ink mounts. Ink's layout engine would mis-measure
91
- // the truecolor escape sequences, so the pug must land verbatim.
92
- // The flag is passed into <Repl /> so the splash component knows to
93
- // skip its own hand-crafted PUG_MASCOT column — otherwise the
94
- // operator sees both the chafa pug AND the ASCII fallback stacked.
95
- // When skipSplash is true (operator opted out via --no-splash), we
96
- // suppress the pre-print too so the boot stays silent.
97
- const mascotPrePrinted = options.skipSplash === true ? false : printPugMascotPreInk(process.stdout);
98
89
  // α6.14.4 CEO dogfood 2026-05-25 (parity with Claude Code): enter
99
90
  // the terminal's alternate screen buffer so the REPL renders on a
100
91
  // fresh "screen" the operator cannot scroll above. On exit, leave
101
- // restores the previous terminal contents the conversation does
92
+ // restores the previous terminal contents - the conversation does
102
93
  // not pollute the operator's shell history. Skipped under --no-tty
103
94
  // and when stdout is not a TTY (pipe/CI), where the escapes would
104
95
  // appear as literal characters.
96
+ // ORDER MATTERS (beta.2 follow-up): alt-screen enter MUST happen
97
+ // BEFORE the chafa mascot pre-print. Reversed, the alt-screen clear
98
+ // wiped the freshly-painted pug and the operator saw nothing.
105
99
  const supportsAltScreen = process.stdout.isTTY === true;
106
100
  if (supportsAltScreen) {
107
101
  process.stdout.write('\x1b[?1049h');
108
102
  process.stdout.write('\x1b[H');
109
103
  }
104
+ // α6.14.2 wave 5: paint the chafa-baked brand-pug ANSI render to
105
+ // stdout BEFORE Ink mounts (but AFTER alt-screen enter). Ink's
106
+ // layout engine would mis-measure the truecolor escape sequences,
107
+ // so the pug must land verbatim. The flag is passed into <Repl />
108
+ // so the splash component knows to skip its own hand-crafted
109
+ // PUG_MASCOT column - otherwise the operator sees both the chafa
110
+ // pug AND the ASCII fallback stacked. When skipSplash is true
111
+ // (operator opted out via --no-splash), we suppress the pre-print
112
+ // too so the boot stays silent.
113
+ const mascotPrePrinted = options.skipSplash === true ? false : printPugMascotPreInk(process.stdout);
110
114
  const instance = render(React.createElement(Repl, {
111
115
  session,
112
116
  updateBanner: options.updateBanner ?? null,
package/dist/tui/repl.js CHANGED
@@ -178,7 +178,14 @@ export function Repl(props) {
178
178
  return undefined;
179
179
  return props.session.cancel();
180
180
  }, [props.session, modalActive]);
181
- return (_jsxs(Box, { flexDirection: "column", paddingX: 1, children: [props.updateBanner ? _jsx(UpdateBanner, { result: props.updateBanner }) : null, splashVisible ? (_jsx(ReplSplash, { cliVersion: state.cliVersion, workspaceLabel: state.workspaceLabel, plan: props.splashPlan, model: props.splashModel, tenant: props.splashTenant, onDismiss: dismissSplash, mascotPrePrinted: props.mascotPrePrinted === true })) : null, _jsx(Header, { state: state }), _jsx(Box, { flexDirection: "column", marginTop: 1, children: overlay === 'help' ? (_jsx(HelpOverlay, {})) : overlay === 'roster' ? (_jsx(RosterOverlay, {})) : overlay === 'farewell' ? (_jsx(FarewellOverlay, {})) : (_jsx(MainArea, { state: state, personaNames: personaNames, nowEpochMs: tickNow, hideToolStream: props.hideToolStream === true, toolStreamCollapsed: toolStreamCollapsed })) }), state.pendingAsk ? (_jsx(Box, { marginTop: 1, children: _jsx(AskModal, { tag: state.pendingAsk, onResolve: handleAskResolve }) })) : null, state.pendingPlanReview ? (_jsx(Box, { marginTop: 1, children: _jsx(PlanReviewModal, { tag: state.pendingPlanReview, onResolve: handlePlanReviewResolve }) })) : null, _jsxs(Box, { flexDirection: "column", marginTop: 1, children: [overlay === 'farewell' || modalActive ? null : (_jsx(InputBox, { onSubmit: handleSubmit, onExit: handleExit, onCancel: handleCancel, now: props.now,
181
+ // α6.14.4 CEO dogfood 2026-05-25: stretch to full alt-screen height
182
+ // (parity with Claude Code which fills the entire viewport). Without
183
+ // an explicit height the Box collapses to its natural content size
184
+ // and leaves ~2/3 of the alt-screen blank below the input bar.
185
+ // process.stdout.rows is the live terminal row count; the REPL
186
+ // re-renders on SIGWINCH via Ink's built-in resize listener.
187
+ const altScreenHeight = process.stdout.rows ?? 24;
188
+ return (_jsxs(Box, { flexDirection: "column", paddingX: 1, height: altScreenHeight, children: [props.updateBanner ? _jsx(UpdateBanner, { result: props.updateBanner }) : null, splashVisible ? (_jsx(ReplSplash, { cliVersion: state.cliVersion, workspaceLabel: state.workspaceLabel, plan: props.splashPlan, model: props.splashModel, tenant: props.splashTenant, onDismiss: dismissSplash, mascotPrePrinted: props.mascotPrePrinted === true })) : null, _jsx(Header, { state: state }), _jsx(Box, { flexDirection: "column", marginTop: 1, children: overlay === 'help' ? (_jsx(HelpOverlay, {})) : overlay === 'roster' ? (_jsx(RosterOverlay, {})) : overlay === 'farewell' ? (_jsx(FarewellOverlay, {})) : (_jsx(MainArea, { state: state, personaNames: personaNames, nowEpochMs: tickNow, hideToolStream: props.hideToolStream === true, toolStreamCollapsed: toolStreamCollapsed })) }), state.pendingAsk ? (_jsx(Box, { marginTop: 1, children: _jsx(AskModal, { tag: state.pendingAsk, onResolve: handleAskResolve }) })) : null, state.pendingPlanReview ? (_jsx(Box, { marginTop: 1, children: _jsx(PlanReviewModal, { tag: state.pendingPlanReview, onResolve: handlePlanReviewResolve }) })) : null, _jsxs(Box, { flexDirection: "column", marginTop: 1, children: [overlay === 'farewell' || modalActive ? null : (_jsx(InputBox, { onSubmit: handleSubmit, onExit: handleExit, onCancel: handleCancel, now: props.now,
182
189
  // Slug from process.cwd() (full path) so two workspaces with
183
190
  // the same basename do not share history. state.workspaceLabel
184
191
  // is the basename only. Codex review P2.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pugi/cli",
3
- "version": "0.1.0-beta.2",
3
+ "version": "0.1.0-beta.3",
4
4
  "description": "Pugi CLI - terminal-native software execution system",
5
5
  "homepage": "https://pugi.io",
6
6
  "repository": {
@@ -52,7 +52,7 @@
52
52
  "undici": "^8.3.0",
53
53
  "zod": "^3.23.0",
54
54
  "@pugi/personas": "0.1.2",
55
- "@pugi/sdk": "0.1.0-beta.2"
55
+ "@pugi/sdk": "0.1.0-beta.3"
56
56
  },
57
57
  "devDependencies": {
58
58
  "@types/node": "^22.0.0",