11import { useAtomValue } from "@effect/atom-react" ;
22import { scopeThreadRef } from "@t3tools/client-runtime/environment" ;
33import { resolveHandoffEndpoints } from "@t3tools/client-runtime/handoff" ;
4- import { resolveProviderInstanceDisplayName } from "@t3tools/client-runtime/state/provider-instance-display" ;
4+ import {
5+ normalizeProviderAccentColor ,
6+ resolveProviderInstanceDisplayName ,
7+ shouldShowInstanceBadge ,
8+ } from "@t3tools/client-runtime/state/provider-instance-display" ;
59import type {
610 EnvironmentId ,
711 OrchestrationV2ProjectedTurnItem ,
@@ -13,7 +17,7 @@ import { Fragment, useMemo } from "react";
1317import { Alert , Pressable , View , type ColorValue } from "react-native" ;
1418import { AppText as Text } from "../../components/AppText" ;
1519import { SymbolView } from "../../components/AppSymbol" ;
16- import { ProviderIcon } from "../../components/ProviderIcon" ;
20+ import { ProviderIcon , ProviderInstanceIcon } from "../../components/ProviderIcon" ;
1721import { environmentThreadDetails } from "../../state/threads" ;
1822import { serverEnvironment } from "../../state/server" ;
1923import { ThreadContextDivider } from "./thread-context-divider" ;
@@ -38,6 +42,7 @@ export function ThreadHandoffRow(props: {
3842 environmentId : EnvironmentId ;
3943 projectedItem : OrchestrationV2ProjectedTurnItem ;
4044 iconColor : ColorValue ;
45+ surfaceColor : string ;
4146} ) {
4247 const { item } = props . projectedItem ;
4348 const endpointsAtom = useMemo (
@@ -48,6 +53,7 @@ export function ThreadHandoffRow(props: {
4853 const config = useAtomValue ( serverEnvironment . configValueAtom ( props . environmentId ) ) ;
4954 if ( item . type !== "handoff" || endpoints === null ) return null ;
5055 const color = item . status === "failed" ? "#e11d48" : props . iconColor ;
56+ const endpointProps = { providers : config ?. providers ?? [ ] , surfaceColor : props . surfaceColor } ;
5157 return (
5258 < ThreadContextDivider
5359 label = "Context handoff"
@@ -63,13 +69,13 @@ export function ThreadHandoffRow(props: {
6369 ,
6470 </ Text >
6571 ) : null }
66- < HandoffEndpoint { ...endpoint } providers = { config ?. providers ?? [ ] } />
72+ < HandoffEndpoint { ...endpoint } { ... endpointProps } />
6773 </ Fragment >
6874 ) ) }
6975 { endpoints . from . length > 0 ? (
7076 < SymbolView name = "arrow.right" size = { 12 } tintColor = { color } />
7177 ) : null }
72- < HandoffEndpoint { ...endpoints . to } providers = { config ?. providers ?? [ ] } />
78+ < HandoffEndpoint { ...endpoints . to } { ... endpointProps } />
7379 </ View >
7480 </ ThreadContextDivider >
7581 ) ;
@@ -79,6 +85,7 @@ function HandoffEndpoint(props: {
7985 instanceId : ProviderInstanceId ;
8086 model ?: string | undefined ;
8187 providers : ReadonlyArray < ServerProvider > ;
88+ surfaceColor : string ;
8289} ) {
8390 const provider = props . providers . find ( ( candidate ) => candidate . instanceId === props . instanceId ) ;
8491 const model = provider ?. models . find ( ( candidate ) => candidate . slug === props . model ) ;
@@ -87,12 +94,21 @@ function HandoffEndpoint(props: {
8794 model ?. name ??
8895 props . model ??
8996 ( provider ? resolveProviderInstanceDisplayName ( provider ) : props . instanceId ) ;
97+ const accentColor = normalizeProviderAccentColor ( provider ?. accentColor ) ;
98+ // Same account badge as the thread rows: a handoff between two accounts of
99+ // one provider would otherwise show the same glyph on both sides.
100+ const showBadge =
101+ provider !== undefined &&
102+ shouldShowInstanceBadge (
103+ { driverKind : provider . driver , accentColor } ,
104+ props . providers . map ( ( candidate ) => ( { driverKind : candidate . driver } ) ) ,
105+ ) ;
90106 return (
91107 < Pressable
92108 accessibilityRole = "button"
93109 accessibilityLabel = { label }
94110 accessibilityHint = "Show provider account"
95- className = "min-h-6 max-w-full flex-row items-center justify-center gap-1"
111+ className = "min-h-6 max-w-full flex-row items-center justify-center gap-1.5 "
96112 hitSlop = { { top : 8 , bottom : 8 } }
97113 onPress = { ( ) =>
98114 Alert . alert (
@@ -101,11 +117,23 @@ function HandoffEndpoint(props: {
101117 )
102118 }
103119 >
104- < ProviderIcon
105- provider = { provider ?. driver ?? props . instanceId }
106- iconUrl = { provider ?. iconUrl }
107- size = { 12 }
108- />
120+ { showBadge && provider !== undefined ? (
121+ < ProviderInstanceIcon
122+ provider = { provider . driver }
123+ iconUrl = { provider . iconUrl }
124+ size = { 14 }
125+ displayName = { resolveProviderInstanceDisplayName ( provider ) }
126+ accentColor = { accentColor }
127+ showBadge
128+ surfaceColor = { props . surfaceColor }
129+ />
130+ ) : (
131+ < ProviderIcon
132+ provider = { provider ?. driver ?? props . instanceId }
133+ iconUrl = { provider ?. iconUrl }
134+ size = { 12 }
135+ />
136+ ) }
109137 < Text numberOfLines = { 1 } className = "shrink text-xs text-foreground-muted" >
110138 { label }
111139 </ Text >
0 commit comments