diff options
| author | matt korwel <[email protected]> | 2025-06-20 10:46:41 -0700 |
|---|---|---|
| committer | GitHub <[email protected]> | 2025-06-20 10:46:41 -0700 |
| commit | 7c8a1da8fe0856e7ebedcd543f82e20f09816222 (patch) | |
| tree | 28e597e682bad94d7799028d73449209df1866cb /packages/cli/src | |
| parent | 7c4af82da4ee4322daeb0ab78acafda4a73dc7e9 (diff) | |
Auth blocking (#1261)
Diffstat (limited to 'packages/cli/src')
| -rw-r--r-- | packages/cli/src/ui/App.tsx | 11 | ||||
| -rw-r--r-- | packages/cli/src/ui/components/AuthInProgress.tsx | 51 | ||||
| -rw-r--r-- | packages/cli/src/ui/hooks/useAuthCommand.ts | 11 |
3 files changed, 73 insertions, 0 deletions
diff --git a/packages/cli/src/ui/App.tsx b/packages/cli/src/ui/App.tsx index b89a20ed..ad65adc6 100644 --- a/packages/cli/src/ui/App.tsx +++ b/packages/cli/src/ui/App.tsx @@ -33,6 +33,7 @@ import { InputPrompt } from './components/InputPrompt.js'; import { Footer } from './components/Footer.js'; import { ThemeDialog } from './components/ThemeDialog.js'; import { AuthDialog } from './components/AuthDialog.js'; +import { AuthInProgress } from './components/AuthInProgress.js'; import { EditorSettingsDialog } from './components/EditorSettingsDialog.js'; import { Colors } from './colors.js'; import { Help } from './components/Help.js'; @@ -138,6 +139,8 @@ const App = ({ config, settings, startupWarnings = [] }: AppProps) => { openAuthDialog, handleAuthSelect, handleAuthHighlight, + isAuthenticating, + cancelAuthentication, } = useAuthCommand(settings, setAuthError, config); useEffect(() => { @@ -585,6 +588,14 @@ const App = ({ config, settings, startupWarnings = [] }: AppProps) => { terminalWidth={mainAreaWidth} /> </Box> + ) : isAuthenticating ? ( + <AuthInProgress + onTimeout={() => { + setAuthError('Authentication timed out. Please try again.'); + cancelAuthentication(); + openAuthDialog(); + }} + /> ) : isAuthDialogOpen ? ( <Box flexDirection="column"> <AuthDialog diff --git a/packages/cli/src/ui/components/AuthInProgress.tsx b/packages/cli/src/ui/components/AuthInProgress.tsx new file mode 100644 index 00000000..804e2ff8 --- /dev/null +++ b/packages/cli/src/ui/components/AuthInProgress.tsx @@ -0,0 +1,51 @@ +/** + * @license + * Copyright 2025 Google LLC + * SPDX-License-Identifier: Apache-2.0 + */ + +import React, { useState, useEffect } from 'react'; +import { Box, Text } from 'ink'; +import Spinner from 'ink-spinner'; +import { Colors } from '../colors.js'; + +interface AuthInProgressProps { + onTimeout: () => void; +} + +export function AuthInProgress({ + onTimeout, +}: AuthInProgressProps): React.JSX.Element { + const [timedOut, setTimedOut] = useState(false); + + useEffect(() => { + const timer = setTimeout(() => { + setTimedOut(true); + onTimeout(); + }, 30000); + + return () => clearTimeout(timer); + }, [onTimeout]); + + return ( + <Box + borderStyle="round" + borderColor={Colors.Gray} + flexDirection="column" + padding={1} + width="100%" + > + {timedOut ? ( + <Text color={Colors.AccentRed}> + Authentication timed out. Please try again. + </Text> + ) : ( + <Box> + <Text> + <Spinner type="dots" /> Waiting for auth... + </Text> + </Box> + )} + </Box> + ); +} diff --git a/packages/cli/src/ui/hooks/useAuthCommand.ts b/packages/cli/src/ui/hooks/useAuthCommand.ts index 2c2b5f93..5cc67a07 100644 --- a/packages/cli/src/ui/hooks/useAuthCommand.ts +++ b/packages/cli/src/ui/hooks/useAuthCommand.ts @@ -31,6 +31,8 @@ export const useAuthCommand = ( setIsAuthDialogOpen(true); }, []); + const [isAuthenticating, setIsAuthenticating] = useState(false); + useEffect(() => { const authFlow = async () => { if (isAuthDialogOpen || !settings.merged.selectedAuthType) { @@ -38,6 +40,7 @@ export const useAuthCommand = ( } try { + setIsAuthenticating(true); await performAuthFlow( settings.merged.selectedAuthType as AuthType, config, @@ -51,6 +54,8 @@ Message: ${getErrorMessage(e)}` : `Failed to login. Message: ${getErrorMessage(e)}`; setAuthError(errorMessage); openAuthDialog(); + } finally { + setIsAuthenticating(false); } }; @@ -73,10 +78,16 @@ Message: ${getErrorMessage(e)}` // For now, we don't do anything on highlight. }, []); + const cancelAuthentication = useCallback(() => { + setIsAuthenticating(false); + }, []); + return { isAuthDialogOpen, openAuthDialog, handleAuthSelect, handleAuthHighlight, + isAuthenticating, + cancelAuthentication, }; }; |
