11import type { Interpolation , Theme } from "@emotion/react" ;
22import type { TimingStage } from "api/typesGenerated" ;
3+ import { T } from "lodash/fp" ;
34import { CircleAlertIcon , InfoIcon } from "lucide-react" ;
45import type { FC } from "react" ;
56import { Bar , ClickableBar } from "./Chart/Bar" ;
@@ -52,7 +53,7 @@ export type Stage = {
5253 tooltip : Omit < TooltipProps , "children" > ;
5354} ;
5455
55- type StageTiming = {
56+ export type StageTiming = {
5657 stage : Stage ;
5758 /**
5859 * Represents the number of resources included in this stage that can be
@@ -65,7 +66,7 @@ type StageTiming = {
6566 * duration of the stage and to position the stage within the chart. This can
6667 * be undefined if a stage has no timing data.
6768 */
68- range : TimeRange | undefined ;
69+ ranges : TimeRange [ ] | undefined ;
6970 /**
7071 * Display an error icon within the bar to indicate when a stage has failed.
7172 * This is used in the agent scripts stage.
@@ -83,11 +84,15 @@ export const StagesChart: FC<StagesChartProps> = ({
8384 onSelectStage,
8485} ) => {
8586 const totalRange = mergeTimeRanges (
86- timings . map ( ( t ) => t . range ) . filter ( ( t ) => t !== undefined ) ,
87+ timings
88+ . map ( ( t ) => t . ranges )
89+ . filter ( ( t ) => t !== undefined )
90+ . flat ( ) ,
8791 ) ;
8892 const totalTime = calcDuration ( totalRange ) ;
8993 const [ ticks , scale ] = makeTicks ( totalTime ) ;
9094 const sections = Array . from ( new Set ( timings . map ( ( t ) => t . stage . section ) ) ) ;
95+ console . log ( "timings" , timings ) ;
9196
9297 return (
9398 < Chart >
@@ -129,11 +134,12 @@ export const StagesChart: FC<StagesChartProps> = ({
129134 const stageTimings = timings . filter (
130135 ( t ) => t . stage . section === section ,
131136 ) ;
137+
132138 return (
133139 < XAxisSection key = { section } >
134140 { stageTimings . map ( ( t ) => {
135141 // If the stage has no timing data, we just want to render an empty row
136- if ( t . range === undefined ) {
142+ if ( t . ranges === undefined ) {
137143 return (
138144 < XAxisRow
139145 key = { t . stage . name }
@@ -142,53 +148,55 @@ export const StagesChart: FC<StagesChartProps> = ({
142148 ) ;
143149 }
144150
145- const value = calcDuration ( t . range ) ;
146- const offset = calcOffset ( t . range , totalRange ) ;
147- const validDuration = value > 0 && ! Number . isNaN ( value ) ;
151+ return t . ranges ?. map ( ( range , index ) => {
152+ const value = calcDuration ( range ) ;
153+ const offset = calcOffset ( range , totalRange ) ;
154+ const validDuration = value > 0 && ! Number . isNaN ( value ) ;
148155
149- return (
150- < XAxisRow
151- key = { t . stage . name }
152- yAxisLabelId = { encodeURIComponent ( t . stage . name ) }
153- >
154- { /** We only want to expand stages with more than one resource */ }
155- { t . visibleResources > 1 ? (
156- < ClickableBar
157- aria-label = { `View ${ t . stage . label } details` }
158- scale = { scale }
159- value = { value }
160- offset = { offset }
161- onClick = { ( ) => {
162- onSelectStage ( t . stage ) ;
163- } }
164- >
165- { t . error && (
166- < CircleAlertIcon
167- className = "size-icon-sm"
168- css = { {
169- color : "#F87171" ,
170- marginRight : 4 ,
171- } }
172- />
173- ) }
174- < Blocks count = { t . visibleResources } />
175- </ ClickableBar >
176- ) : (
177- < Bar scale = { scale } value = { value } offset = { offset } />
178- ) }
179- { validDuration ? (
180- < span > { formatTime ( value ) } </ span >
181- ) : (
182- < span
183- css = { ( theme ) => ( {
184- color : theme . palette . error . main ,
185- } ) }
186- >
187- Invalid
188- </ span >
189- ) }
190- </ XAxisRow >
191- ) ;
156+ return (
157+ < XAxisRow
158+ key = { t . stage . name + index }
159+ yAxisLabelId = { encodeURIComponent ( t . stage . name ) }
160+ >
161+ { /** We only want to expand stages with more than one resource */ }
162+ { t . visibleResources > 1 ? (
163+ < ClickableBar
164+ aria-label = { `View ${ t . stage . label } details` }
165+ scale = { scale }
166+ value = { value }
167+ offset = { offset }
168+ onClick = { ( ) => {
169+ onSelectStage ( t . stage ) ;
170+ } }
171+ >
172+ { t . error && (
173+ < CircleAlertIcon
174+ className = "size-icon-sm"
175+ css = { {
176+ color : "#F87171" ,
177+ marginRight : 4 ,
178+ } }
179+ />
180+ ) }
181+ < Blocks count = { t . visibleResources } />
182+ </ ClickableBar >
183+ ) : (
184+ < Bar scale = { scale } value = { value } offset = { offset } />
185+ ) }
186+ { validDuration ? (
187+ < span > { formatTime ( value ) } </ span >
188+ ) : (
189+ < span
190+ css = { ( theme ) => ( {
191+ color : theme . palette . error . main ,
192+ } ) }
193+ >
194+ Invalid
195+ </ span >
196+ ) }
197+ </ XAxisRow >
198+ ) ;
199+ } ) ;
192200 } ) }
193201 </ XAxisSection >
194202 ) ;
0 commit comments