@@ -295,7 +295,8 @@ function TraceView({ run, trace, maximumLiveReloadingSetting, resizable }: Loade
295
295
return < > </ > ;
296
296
}
297
297
298
- const { events, parentRunFriendlyId, duration, rootSpanStatus, rootStartedAt } = trace ;
298
+ const { events, parentRunFriendlyId, duration, rootSpanStatus, rootStartedAt, queuedDuration } =
299
+ trace ;
299
300
const shouldLiveReload = events . length <= maximumLiveReloadingSetting ;
300
301
301
302
const changeToSpan = useDebounce ( ( selectedSpan : string ) => {
@@ -345,6 +346,7 @@ function TraceView({ run, trace, maximumLiveReloadingSetting, resizable }: Loade
345
346
totalDuration = { duration }
346
347
rootSpanStatus = { rootSpanStatus }
347
348
rootStartedAt = { rootStartedAt ? new Date ( rootStartedAt ) : undefined }
349
+ queuedDuration = { queuedDuration }
348
350
environmentType = { run . environment . type }
349
351
shouldLiveReload = { shouldLiveReload }
350
352
maximumLiveReloadingSetting = { maximumLiveReloadingSetting }
@@ -472,6 +474,7 @@ type TasksTreeViewProps = {
472
474
totalDuration : number ;
473
475
rootSpanStatus : "executing" | "completed" | "failed" ;
474
476
rootStartedAt : Date | undefined ;
477
+ queuedDuration : number | undefined ;
475
478
environmentType : RuntimeEnvironmentType ;
476
479
shouldLiveReload : boolean ;
477
480
maximumLiveReloadingSetting : number ;
@@ -491,6 +494,7 @@ function TasksTreeView({
491
494
totalDuration,
492
495
rootSpanStatus,
493
496
rootStartedAt,
497
+ queuedDuration,
494
498
environmentType,
495
499
shouldLiveReload,
496
500
maximumLiveReloadingSetting,
@@ -502,12 +506,14 @@ function TasksTreeView({
502
506
const [ errorsOnly , setErrorsOnly ] = useState ( false ) ;
503
507
const [ showDebug , setShowDebug ] = useState ( false ) ;
504
508
const [ showDurations , setShowDurations ] = useState ( true ) ;
509
+ const [ showQueueTime , setShowQueueTime ] = useState ( false ) ;
505
510
const [ scale , setScale ] = useState ( 0 ) ;
506
511
const parentRef = useRef < HTMLDivElement > ( null ) ;
507
512
const treeScrollRef = useRef < HTMLDivElement > ( null ) ;
508
513
const timelineScrollRef = useRef < HTMLDivElement > ( null ) ;
509
514
510
515
const displayEvents = showDebug ? events : events . filter ( ( event ) => ! event . data . isDebug ) ;
516
+ const queuedTime = showQueueTime ? undefined : queuedDuration ;
511
517
512
518
const {
513
519
nodes,
@@ -556,6 +562,12 @@ function TasksTreeView({
556
562
onCheckedChange = { ( e ) => setShowDebug ( e . valueOf ( ) ) }
557
563
/>
558
564
) }
565
+ < Switch
566
+ variant = "small"
567
+ label = "Queue time"
568
+ checked = { showQueueTime }
569
+ onCheckedChange = { ( e ) => setShowQueueTime ( e . valueOf ( ) ) }
570
+ />
559
571
< Switch
560
572
variant = "small"
561
573
label = "Errors only"
@@ -692,6 +704,7 @@ function TasksTreeView({
692
704
events = { events }
693
705
rootSpanStatus = { rootSpanStatus }
694
706
rootStartedAt = { rootStartedAt }
707
+ queuedDuration = { queuedTime }
695
708
parentRef = { parentRef }
696
709
timelineScrollRef = { timelineScrollRef }
697
710
nodes = { nodes }
@@ -754,7 +767,7 @@ function TasksTreeView({
754
767
755
768
type TimelineViewProps = Pick <
756
769
TasksTreeViewProps ,
757
- "totalDuration" | "rootSpanStatus" | "events" | "rootStartedAt"
770
+ "totalDuration" | "rootSpanStatus" | "events" | "rootStartedAt" | "queuedDuration"
758
771
> & {
759
772
scale : number ;
760
773
parentRef : React . RefObject < HTMLDivElement > ;
@@ -785,27 +798,32 @@ function TimelineView({
785
798
toggleNodeSelection,
786
799
showDurations,
787
800
treeScrollRef,
801
+ queuedDuration,
788
802
} : TimelineViewProps ) {
789
- const isAdmin = useHasAdminAccess ( ) ;
790
803
const timelineContainerRef = useRef < HTMLDivElement > ( null ) ;
791
804
const initialTimelineDimensions = useInitialDimensions ( timelineContainerRef ) ;
792
805
const minTimelineWidth = initialTimelineDimensions ?. width ?? 300 ;
793
806
const maxTimelineWidth = minTimelineWidth * 10 ;
794
807
795
808
//we want to live-update the duration if the root span is still executing
796
- const [ duration , setDuration ] = useState ( totalDuration ) ;
809
+ const [ duration , setDuration ] = useState ( queueAdjustedNs ( totalDuration , queuedDuration ) ) ;
797
810
useEffect ( ( ) => {
798
811
if ( rootSpanStatus !== "executing" || ! rootStartedAt ) {
799
- setDuration ( totalDuration ) ;
812
+ setDuration ( queueAdjustedNs ( totalDuration , queuedDuration ) ) ;
800
813
return ;
801
814
}
802
815
803
816
const interval = setInterval ( ( ) => {
804
- setDuration ( millisecondsToNanoseconds ( Date . now ( ) - rootStartedAt . getTime ( ) ) ) ;
817
+ setDuration (
818
+ queueAdjustedNs (
819
+ millisecondsToNanoseconds ( Date . now ( ) - rootStartedAt . getTime ( ) ) ,
820
+ queuedDuration
821
+ )
822
+ ) ;
805
823
} , 500 ) ;
806
824
807
825
return ( ) => clearInterval ( interval ) ;
808
- } , [ totalDuration , rootSpanStatus ] ) ;
826
+ } , [ totalDuration , rootSpanStatus , queuedDuration , rootStartedAt ] ) ;
809
827
810
828
return (
811
829
< div
@@ -820,7 +838,11 @@ function TimelineView({
820
838
maxWidth = { maxTimelineWidth }
821
839
>
822
840
{ /* Follows the cursor */ }
823
- < CurrentTimeIndicator totalDuration = { duration } rootStartedAt = { rootStartedAt } />
841
+ < CurrentTimeIndicator
842
+ totalDuration = { duration }
843
+ rootStartedAt = { rootStartedAt }
844
+ queuedDurationNs = { queuedDuration }
845
+ />
824
846
825
847
< Timeline . Row className = "grid h-full grid-rows-[2rem_1fr]" >
826
848
{ /* The duration labels */ }
@@ -941,7 +963,9 @@ function TimelineView({
941
963
eventIndex === 0 ? (
942
964
< Timeline . Point
943
965
key = { eventIndex }
944
- ms = { nanosecondsToMilliseconds ( event . offset ) }
966
+ ms = { nanosecondsToMilliseconds (
967
+ queueAdjustedNs ( event . offset , queuedDuration )
968
+ ) }
945
969
>
946
970
{ ( ms ) => (
947
971
< motion . div
@@ -956,7 +980,9 @@ function TimelineView({
956
980
) : (
957
981
< Timeline . Point
958
982
key = { eventIndex }
959
- ms = { nanosecondsToMilliseconds ( event . offset ) }
983
+ ms = { nanosecondsToMilliseconds (
984
+ queueAdjustedNs ( event . offset , queuedDuration )
985
+ ) }
960
986
className = "z-10"
961
987
>
962
988
{ ( ms ) => (
@@ -975,7 +1001,9 @@ function TimelineView({
975
1001
node . data . timelineEvents [ 0 ] &&
976
1002
node . data . timelineEvents [ 0 ] . offset < node . data . offset ? (
977
1003
< Timeline . Span
978
- startMs = { nanosecondsToMilliseconds ( node . data . timelineEvents [ 0 ] . offset ) }
1004
+ startMs = { nanosecondsToMilliseconds (
1005
+ queueAdjustedNs ( node . data . timelineEvents [ 0 ] . offset , queuedDuration )
1006
+ ) }
979
1007
durationMs = { nanosecondsToMilliseconds (
980
1008
node . data . offset - node . data . timelineEvents [ 0 ] . offset
981
1009
) }
@@ -988,7 +1016,9 @@ function TimelineView({
988
1016
) : null }
989
1017
< SpanWithDuration
990
1018
showDuration = { state . selected ? true : showDurations }
991
- startMs = { nanosecondsToMilliseconds ( node . data . offset ) }
1019
+ startMs = { nanosecondsToMilliseconds (
1020
+ queueAdjustedNs ( node . data . offset , queuedDuration )
1021
+ ) }
992
1022
durationMs = {
993
1023
node . data . duration
994
1024
? nanosecondsToMilliseconds ( node . data . duration )
@@ -998,7 +1028,11 @@ function TimelineView({
998
1028
/>
999
1029
</ >
1000
1030
) : (
1001
- < Timeline . Point ms = { nanosecondsToMilliseconds ( node . data . offset ) } >
1031
+ < Timeline . Point
1032
+ ms = { nanosecondsToMilliseconds (
1033
+ queueAdjustedNs ( node . data . offset , queuedDuration )
1034
+ ) }
1035
+ >
1002
1036
{ ( ms ) => (
1003
1037
< motion . div
1004
1038
className = { cn (
@@ -1027,6 +1061,14 @@ function TimelineView({
1027
1061
) ;
1028
1062
}
1029
1063
1064
+ function queueAdjustedNs ( timeNs : number , queuedDurationNs : number | undefined ) {
1065
+ if ( queuedDurationNs ) {
1066
+ return timeNs - queuedDurationNs ;
1067
+ }
1068
+
1069
+ return timeNs ;
1070
+ }
1071
+
1030
1072
function NodeText ( { node } : { node : TraceEvent } ) {
1031
1073
const className = "truncate" ;
1032
1074
return (
@@ -1220,9 +1262,11 @@ const edgeBoundary = 0.17;
1220
1262
function CurrentTimeIndicator ( {
1221
1263
totalDuration,
1222
1264
rootStartedAt,
1265
+ queuedDurationNs,
1223
1266
} : {
1224
1267
totalDuration : number ;
1225
1268
rootStartedAt : Date | undefined ;
1269
+ queuedDurationNs : number | undefined ;
1226
1270
} ) {
1227
1271
return (
1228
1272
< Timeline . FollowCursor >
@@ -1235,7 +1279,11 @@ function CurrentTimeIndicator({
1235
1279
offset = lerp ( 0.5 , 1 , ( ratio - ( 1 - edgeBoundary ) ) / edgeBoundary ) ;
1236
1280
}
1237
1281
1238
- const currentTime = rootStartedAt ? new Date ( rootStartedAt . getTime ( ) + ms ) : undefined ;
1282
+ const currentTime = rootStartedAt
1283
+ ? new Date (
1284
+ rootStartedAt . getTime ( ) + ms + nanosecondsToMilliseconds ( queuedDurationNs ?? 0 )
1285
+ )
1286
+ : undefined ;
1239
1287
const currentTimeComponent = currentTime ? < DateTimeShort date = { currentTime } /> : < > </ > ;
1240
1288
1241
1289
return (
0 commit comments