mirror of
https://github.com/tiennm99/ccs.git
synced 2026-07-16 02:11:28 +00:00
refactor(cliproxy): address review feedback on parity and refresh flow
- make refresh ownership handling exhaustive in provider refresher - extend backend/ui sync test to provider IDs and device-code providers - remove DEFAULT_CURSOR_PORT re-export from use-cursor hook - import cursor default port directly from shared defaults module
This commit is contained in:
@@ -26,6 +26,10 @@ export interface ProviderRefreshResult {
|
||||
delegated?: boolean;
|
||||
}
|
||||
|
||||
function assertNever(value: never): never {
|
||||
throw new Error(`Unhandled token refresh ownership: ${String(value)}`);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a provider's token refresh is delegated to CLIProxy
|
||||
*/
|
||||
@@ -47,24 +51,22 @@ export async function refreshToken(
|
||||
return await refreshGeminiTokenWrapper();
|
||||
}
|
||||
|
||||
if (isRefreshDelegated(provider)) {
|
||||
// CLIProxyAPIPlus handles refresh for these providers automatically.
|
||||
// No action needed from CCS — report success with delegated flag.
|
||||
return { success: true, delegated: true };
|
||||
}
|
||||
|
||||
const ownership = getTokenRefreshOwnership(provider);
|
||||
if (ownership === 'unsupported') {
|
||||
return {
|
||||
success: false,
|
||||
error: `Token refresh not yet implemented for ${provider}`,
|
||||
};
|
||||
switch (ownership) {
|
||||
case 'cliproxy':
|
||||
// CLIProxyAPIPlus handles refresh for these providers automatically.
|
||||
// No action needed from CCS — report success with delegated flag.
|
||||
return { success: true, delegated: true };
|
||||
case 'unsupported':
|
||||
case 'ccs':
|
||||
// Non-gemini CCS-owned refresh paths are not implemented yet.
|
||||
return {
|
||||
success: false,
|
||||
error: `Token refresh not yet implemented for ${provider}`,
|
||||
};
|
||||
default:
|
||||
return assertNever(ownership);
|
||||
}
|
||||
|
||||
return {
|
||||
success: false,
|
||||
error: `Unknown provider: ${provider}`,
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -7,10 +7,22 @@
|
||||
import { describe, expect, test } from 'bun:test';
|
||||
import { CLIPROXY_DEFAULT_PORT as BACKEND_CLIPROXY_DEFAULT_PORT } from '../../../src/cliproxy/config/port-manager';
|
||||
import { DEFAULT_CURSOR_PORT as BACKEND_CURSOR_DEFAULT_PORT } from '../../../src/cursor/cursor-models';
|
||||
import {
|
||||
CLIPROXY_PROVIDER_IDS as BACKEND_CLIPROXY_PROVIDER_IDS,
|
||||
getProvidersByOAuthFlow,
|
||||
} from '../../../src/cliproxy/provider-capabilities';
|
||||
import {
|
||||
CLIPROXY_DEFAULT_PORT as UI_CLIPROXY_DEFAULT_PORT,
|
||||
DEFAULT_CURSOR_PORT as UI_CURSOR_DEFAULT_PORT,
|
||||
} from '../../../ui/src/lib/default-ports';
|
||||
import {
|
||||
CLIPROXY_PROVIDERS as UI_CLIPROXY_PROVIDERS,
|
||||
DEVICE_CODE_PROVIDERS as UI_DEVICE_CODE_PROVIDERS,
|
||||
} from '../../../ui/src/lib/provider-config';
|
||||
|
||||
function sorted(values: readonly string[]): string[] {
|
||||
return [...values].sort((a, b) => a.localeCompare(b));
|
||||
}
|
||||
|
||||
describe('Default Port Sync', () => {
|
||||
test('CLIProxy default port is synced between backend and UI', () => {
|
||||
@@ -20,4 +32,12 @@ describe('Default Port Sync', () => {
|
||||
test('Cursor default port is synced between backend and UI', () => {
|
||||
expect(UI_CURSOR_DEFAULT_PORT).toBe(BACKEND_CURSOR_DEFAULT_PORT);
|
||||
});
|
||||
|
||||
test('CLIProxy provider IDs are synced between backend and UI', () => {
|
||||
expect(sorted(UI_CLIPROXY_PROVIDERS)).toEqual(sorted(BACKEND_CLIPROXY_PROVIDER_IDS));
|
||||
});
|
||||
|
||||
test('Device code providers are synced between backend and UI', () => {
|
||||
expect(sorted(UI_DEVICE_CODE_PROVIDERS)).toEqual(sorted(getProvidersByOAuthFlow('device_code')));
|
||||
});
|
||||
});
|
||||
|
||||
@@ -8,8 +8,6 @@ import { useMemo } from 'react';
|
||||
import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query';
|
||||
import { withApiBase } from '@/lib/api-client';
|
||||
|
||||
export { DEFAULT_CURSOR_PORT } from '@/lib/default-ports';
|
||||
|
||||
export interface CursorStatus {
|
||||
enabled: boolean;
|
||||
authenticated: boolean;
|
||||
|
||||
@@ -23,7 +23,8 @@ import {
|
||||
XCircle,
|
||||
} from 'lucide-react';
|
||||
import { cn } from '@/lib/utils';
|
||||
import { DEFAULT_CURSOR_PORT, useCursor } from '@/hooks/use-cursor';
|
||||
import { useCursor } from '@/hooks/use-cursor';
|
||||
import { DEFAULT_CURSOR_PORT } from '@/lib/default-ports';
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { Label } from '@/components/ui/label';
|
||||
|
||||
Reference in New Issue
Block a user