diff --git a/apps/api/src/api/tool_instances.py b/apps/api/src/api/tool_instances.py index ff3aadf..4dd95f2 100644 --- a/apps/api/src/api/tool_instances.py +++ b/apps/api/src/api/tool_instances.py @@ -1483,6 +1483,7 @@ async def get_user_sessions( "url": instance.url, "clone_mode": instance.clone_mode, "branch": instance.branch, + "created_at": instance.created_at.isoformat() if instance.created_at else None, }) return {"sessions": sessions} diff --git a/apps/web/src/api/sessions.ts b/apps/web/src/api/sessions.ts index 04c570d..ae552d6 100644 --- a/apps/web/src/api/sessions.ts +++ b/apps/web/src/api/sessions.ts @@ -29,6 +29,7 @@ export interface Session { probe_status?: string; clone_mode?: string; branch?: string | null; + created_at?: string; } export async function listInstances( diff --git a/apps/web/src/components/mobile-terminal-header.tsx b/apps/web/src/components/mobile-terminal-header.tsx index fd71ef4..920de97 100644 --- a/apps/web/src/components/mobile-terminal-header.tsx +++ b/apps/web/src/components/mobile-terminal-header.tsx @@ -6,6 +6,7 @@ interface MobileTerminalHeaderProps { onBack?: () => void; onMenuToggle?: () => void; onClose?: () => void; + onFontSizeChange?: (delta: number) => void; isVisible: boolean; connectionStatus?: "connecting" | "connected" | "disconnected" | "error"; } @@ -15,6 +16,7 @@ export const MobileTerminalHeader: React.FC = ({ onBack, onMenuToggle, onClose, + onFontSizeChange, isVisible, connectionStatus = "connecting", }) => { @@ -56,6 +58,26 @@ export const MobileTerminalHeader: React.FC = ({
+ {onFontSizeChange && ( + <> + + + + )} {onClose && ( )} - {tunnelHealth[session.id] && tunnelHealth[session.id].tunnel_status === "unreachable" && ( + {!isTerminalOnly && tunnelHealth[session.id] && tunnelHealth[session.id].tunnel_status === "unreachable" && (
- ))} + )})} )} diff --git a/apps/web/src/styles.css b/apps/web/src/styles.css index d8c6a6d..934a325 100644 --- a/apps/web/src/styles.css +++ b/apps/web/src/styles.css @@ -2960,19 +2960,28 @@ a.nav-item, background: #2d2d2d; border-bottom: 1px solid #3e3e3e; flex-shrink: 0; - transition: transform 0.3s ease, opacity 0.3s ease; + transition: transform 0.3s ease, opacity 0.3s ease, height 0.3s ease, padding 0.3s ease, margin 0.3s ease; z-index: 100; + overflow: hidden; } .mobile-terminal-header.hidden { transform: translateY(-100%); opacity: 0; pointer-events: none; + height: 0; + padding-top: 0; + padding-bottom: 0; + margin-top: 0; + margin-bottom: 0; + border-width: 0; + flex-shrink: 1; } .mobile-terminal-header.visible { transform: translateY(0); opacity: 1; + height: auto; } .mobile-terminal-header-left,