import { ChatSessionMode, type AiProvider, type ChatSession, type AiModel } from '../lib/api'; import { WorkspaceMode } from '../lib/types'; import WorkspaceModeIndicator from './WorkspaceModeIndicator'; interface SessionPanelProps { session: ChatSession | null; workspaceMode: WorkspaceMode; sessionLocked: boolean; providers: AiProvider[]; selectedProviderId: string; selectedModelId: string; sessionReasoningEffort: string; sessionNumCtx: number; isEditingProvider: boolean; editProviderId: string; editModelId: string; isUpdatingProvider: boolean; isEditingName: boolean; editName: string; isUpdatingName: boolean; isUpdatingMode: boolean; isUpdatingReasoning: boolean; isUpdatingNumCtx: boolean; onWorkspaceModeChange: (mode: WorkspaceMode) => void; onModeChange: (e: React.ChangeEvent) => void; onReasoningChange: (e: React.ChangeEvent) => void; onNumCtxChange: (e: React.ChangeEvent) => void; onNumCtxCommit: (e: React.MouseEvent | React.TouchEvent) => void; onStartEditProvider: () => void; onSaveProvider: () => void; onCancelEditProvider: () => void; onEditProviderIdChange: (id: string) => void; onEditModelIdChange: (id: string) => void; onStartEditName: () => void; onSaveName: () => void; onCancelEditName: () => void; onEditNameChange: (name: string) => void; getProviderName: (id: string) => string; getModelName: (providerId: string, modelId: string) => string; getSortedModels: (providerId: string) => AiProvider['models']; truncateModelName: (name: string, maxLength?: number) => string; getSelectedModelCapabilities: () => { hasThinking: boolean } | null; getSelectedModel: () => AiModel | null; contextWindowUsage: number; } export default function SessionPanel({ session, workspaceMode, sessionLocked, providers, selectedProviderId, selectedModelId, sessionReasoningEffort, sessionNumCtx, isEditingProvider, editProviderId, editModelId, isUpdatingProvider, isEditingName, editName, isUpdatingName, isUpdatingMode, isUpdatingReasoning, isUpdatingNumCtx, onWorkspaceModeChange, onModeChange, onReasoningChange, onNumCtxChange, onNumCtxCommit, onStartEditProvider, onSaveProvider, onCancelEditProvider, onEditProviderIdChange, onEditModelIdChange, onStartEditName, onSaveName, onCancelEditName, onEditNameChange, getProviderName, getModelName, getSortedModels, truncateModelName, getSelectedModelCapabilities, getSelectedModel, contextWindowUsage, }: SessionPanelProps) { const usagePercent = sessionNumCtx > 0 ? (contextWindowUsage / sessionNumCtx) * 100 : 0; return (

Session

Name
{isEditingName ? (
onEditNameChange(e.target.value)} onKeyDown={(e) => { if (e.key === 'Enter') { e.preventDefault(); onSaveName(); } if (e.key === 'Escape') { e.preventDefault(); onCancelEditName(); } }} className="flex-1 px-2 py-1.5 bg-bg-tertiary border border-border-default rounded text-text-primary text-sm focus:border-brand focus:outline-none" autoFocus />
) : (
{session?.name}
)}
{isEditingProvider ? (
Provider
Model
) : (
Provider
{getProviderName(selectedProviderId)}
Model
{getModelName(selectedProviderId, selectedModelId)}
)}
Mode
Reasoning
{providers.find(p => p._id === selectedProviderId)?.apiType !== 'openai' && (
Context Window
{sessionNumCtx.toLocaleString()}
)}
Context Window Usage
E
= 80 ? 'bg-red-500' : usagePercent >= 50 ? 'bg-yellow-500' : 'bg-green-500' }`} style={{ width: `${Math.min(usagePercent, 100)}%` }} />
F
{contextWindowUsage.toLocaleString()} tokens {sessionNumCtx.toLocaleString()} max
); }