mirror of
https://github.com/google-gemini/gemini-cli.git
synced 2026-05-16 23:02:51 -07:00
refactor(cli): extract prompt stash logic to hook and polish UI layout
This commit is contained in:
@@ -130,6 +130,7 @@ import { registerCleanup, runExitCleanup } from '../utils/cleanup.js';
|
||||
import { relaunchApp } from '../utils/processUtils.js';
|
||||
import type { SessionInfo } from '../utils/sessionUtils.js';
|
||||
import { useMessageQueue } from './hooks/useMessageQueue.js';
|
||||
import { usePromptStash } from './hooks/usePromptStash.js';
|
||||
import { useMcpStatus } from './hooks/useMcpStatus.js';
|
||||
import { useApprovalModeIndicator } from './hooks/useApprovalModeIndicator.js';
|
||||
import { useSessionStats } from './contexts/SessionContext.js';
|
||||
@@ -253,17 +254,7 @@ export const AppContainer = (props: AppContainerProps) => {
|
||||
QUEUE_ERROR_DISPLAY_DURATION_MS,
|
||||
);
|
||||
|
||||
const [stashedPrompt, setStashedPrompt] = useState<string | null>(null);
|
||||
const stashPrompt = useCallback((text: string) => {
|
||||
if (text.length > 0) {
|
||||
setStashedPrompt(text);
|
||||
}
|
||||
}, []);
|
||||
const popStashedPrompt = useCallback(() => {
|
||||
const prompt = stashedPrompt;
|
||||
setStashedPrompt(null);
|
||||
return prompt;
|
||||
}, [stashedPrompt]);
|
||||
const { stashedPrompt, stashPrompt, popStashedPrompt } = usePromptStash();
|
||||
|
||||
const [newAgents, setNewAgents] = useState<AgentDefinition[] | null>(null);
|
||||
const [constrainHeight, setConstrainHeight] = useState<boolean>(true);
|
||||
|
||||
@@ -1095,5 +1095,14 @@ describe('Composer', () => {
|
||||
const { lastFrame } = await renderComposer(uiState);
|
||||
expect(lastFrame()).toMatchSnapshot();
|
||||
});
|
||||
|
||||
it('matches snapshot with stashed prompt and queued messages', async () => {
|
||||
const uiState = createMockUIState({
|
||||
stashedPrompt: 'This is a stashed prompt',
|
||||
messageQueue: ['First queued message', 'Second queued message'],
|
||||
});
|
||||
const { lastFrame } = await renderComposer(uiState);
|
||||
expect(lastFrame()).toMatchSnapshot();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -523,13 +523,13 @@ export const Composer = ({ isFocused = true }: { isFocused?: boolean }) => {
|
||||
<ConfigInitDisplay message="Resuming session..." />
|
||||
)}
|
||||
|
||||
{showUiDetails && (
|
||||
<StashedPromptDisplay stashedPrompt={uiState.stashedPrompt} />
|
||||
)}
|
||||
|
||||
{showUiDetails && (
|
||||
<QueuedMessageDisplay messageQueue={uiState.messageQueue} />
|
||||
)}
|
||||
{showUiDetails &&
|
||||
(uiState.stashedPrompt || uiState.messageQueue.length > 0) && (
|
||||
<Box flexDirection="column" marginTop={1}>
|
||||
<StashedPromptDisplay stashedPrompt={uiState.stashedPrompt} />
|
||||
<QueuedMessageDisplay messageQueue={uiState.messageQueue} />
|
||||
</Box>
|
||||
)}
|
||||
|
||||
{showUiDetails && <TodoTray />}
|
||||
|
||||
|
||||
@@ -190,12 +190,6 @@ export const Help: React.FC<Help> = ({ commands }) => (
|
||||
</Text>{' '}
|
||||
- Cycle through your prompt history
|
||||
</Text>
|
||||
<Text color={theme.text.primary}>
|
||||
<Text bold color={theme.text.accent}>
|
||||
{formatCommand(Command.STASH_INPUT)}
|
||||
</Text>{' '}
|
||||
- Stash current prompt (restores on next submit)
|
||||
</Text>
|
||||
<Box height={1} />
|
||||
<Text color={theme.text.primary}>
|
||||
For a full list of shortcuts, see{' '}
|
||||
|
||||
@@ -20,7 +20,7 @@ export const QueuedMessageDisplay = ({
|
||||
}
|
||||
|
||||
return (
|
||||
<Box flexDirection="column" marginTop={1}>
|
||||
<Box flexDirection="column">
|
||||
<Box paddingLeft={2}>
|
||||
<Text dimColor>Queued (press ↑ to edit):</Text>
|
||||
</Box>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/**
|
||||
* @license
|
||||
* Copyright 2025 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/**
|
||||
* @license
|
||||
* Copyright 2025 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
@@ -18,7 +18,7 @@ export const StashedPromptDisplay = ({
|
||||
}
|
||||
|
||||
return (
|
||||
<Box paddingLeft={2} marginTop={1}>
|
||||
<Box paddingLeft={2}>
|
||||
<Text dimColor>Stashed (restores after submit)</Text>
|
||||
</Box>
|
||||
);
|
||||
|
||||
@@ -43,3 +43,17 @@ InputPrompt: Type your message or @path/to/file
|
||||
Footer
|
||||
"
|
||||
`;
|
||||
|
||||
exports[`Composer > Snapshots > matches snapshot with stashed prompt and queued messages 1`] = `
|
||||
"
|
||||
Stashed (restores after submit)
|
||||
First queued message
|
||||
Second queued message
|
||||
|
||||
? for shortcuts
|
||||
────────────────────────────────────────────────────────────────────────────────────────────────────
|
||||
ApprovalModeIndicator: default StatusDisplay
|
||||
InputPrompt: Type your message or @path/to/file
|
||||
Footer
|
||||
"
|
||||
`;
|
||||
|
||||
@@ -0,0 +1,40 @@
|
||||
/**
|
||||
* @license
|
||||
* Copyright 2026 Google LLC
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
import { useCallback, useState } from 'react';
|
||||
|
||||
export interface UsePromptStashReturn {
|
||||
/** The currently stashed prompt text, or null if nothing is stashed. */
|
||||
stashedPrompt: string | null;
|
||||
/** Save text to the stash, replacing any existing stash. No-op for empty strings. */
|
||||
stashPrompt: (text: string) => void;
|
||||
/** Pop and return the stashed prompt, clearing the stash. */
|
||||
popStashedPrompt: () => string | null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook for managing a single stashed prompt.
|
||||
*
|
||||
* Allows users to temporarily set aside their current input and restore it
|
||||
* after the next submit.
|
||||
*/
|
||||
export function usePromptStash(): UsePromptStashReturn {
|
||||
const [stashedPrompt, setStashedPrompt] = useState<string | null>(null);
|
||||
|
||||
const stashPrompt = useCallback((text: string) => {
|
||||
if (text.length > 0) {
|
||||
setStashedPrompt(text);
|
||||
}
|
||||
}, []);
|
||||
|
||||
const popStashedPrompt = useCallback(() => {
|
||||
const prompt = stashedPrompt;
|
||||
setStashedPrompt(null);
|
||||
return prompt;
|
||||
}, [stashedPrompt]);
|
||||
|
||||
return { stashedPrompt, stashPrompt, popStashedPrompt };
|
||||
}
|
||||
Reference in New Issue
Block a user