11import { HttpClientTestingModule } from '@angular/common/http/testing' ;
2- import { discardPeriodicTasks , fakeAsync } from '@angular/core/testing' ;
2+ import { Provider } from '@angular/core' ;
3+ import { fakeAsync } from '@angular/core/testing' ;
34import { ActivatedRoute , convertToParamMap } from '@angular/router' ;
45import { RouterTestingModule } from '@angular/router/testing' ;
56import { IconLibraryTestingModule } from '@hypertrace/assets-library' ;
@@ -16,7 +17,8 @@ import {
1617 FilterAttributeType ,
1718 FilterBarComponent ,
1819 FilterBuilderLookupService ,
19- FilterOperator
20+ FilterOperator ,
21+ ToggleGroupComponent
2022} from '@hypertrace/components' ;
2123import { GraphQlRequestService } from '@hypertrace/graphql-client' ;
2224import { getMockFlexLayoutProviders , patchRouterNavigateForTest } from '@hypertrace/test-utils' ;
@@ -25,6 +27,10 @@ import { EMPTY, NEVER, of } from 'rxjs';
2527import { startWith } from 'rxjs/operators' ;
2628import { CartesianSeriesVisualizationType } from '../../shared/components/cartesian/chart' ;
2729import { ExploreQueryEditorComponent } from '../../shared/components/explore-query-editor/explore-query-editor.component' ;
30+ import { ExploreQueryGroupByEditorComponent } from '../../shared/components/explore-query-editor/group-by/explore-query-group-by-editor.component' ;
31+ import { ExploreQueryIntervalEditorComponent } from '../../shared/components/explore-query-editor/interval/explore-query-interval-editor.component' ;
32+ import { ExploreQueryLimitEditorComponent } from '../../shared/components/explore-query-editor/limit/explore-query-limit-editor.component' ;
33+ import { ExploreQuerySeriesEditorComponent } from '../../shared/components/explore-query-editor/series/explore-query-series-editor.component' ;
2834import { MetricAggregationType } from '../../shared/graphql/model/metrics/metric-aggregation' ;
2935import { GraphQlFieldFilter } from '../../shared/graphql/model/schema/filter/field/graphql-field-filter' ;
3036import { GraphQlOperatorType } from '../../shared/graphql/model/schema/filter/graphql-filter' ;
@@ -109,27 +115,37 @@ describe('Explorer component', () => {
109115
110116 const detectQueryChange = ( ) => {
111117 spectator . detectChanges ( ) ; // Detect whatever caused the change
112- spectator . tick ( 200 ) ; // Query emits async, tick here triggers building the DOM for the query
113- discardPeriodicTasks ( ) ; // Some of the newly instantiated components also uses async, need to wait for them to settle
114- spectator . tick ( 200 ) ;
118+ spectator . tick ( 50 ) ; // Query emits async, tick here triggers building the DOM for the query
119+ // Break up the ticks into multiple to account for various async handoffs
120+ spectator . tick ( ) ;
121+ spectator . tick ( 100 ) ;
115122 } ;
116123
117- const init = ( ...params : Parameters < typeof createComponent > ) => {
118- spectator = createComponent ( ...params ) ;
124+ const init = ( ...mockProviders : Provider [ ] ) => {
125+ spectator = createComponent ( {
126+ providers : [
127+ {
128+ provide : ActivatedRoute ,
129+ useValue : {
130+ queryParamMap : of ( convertToParamMap ( { } ) )
131+ }
132+ } ,
133+ ...mockProviders
134+ ]
135+ } ) ;
119136 spectator . tick ( ) ;
120137 patchRouterNavigateForTest ( spectator ) ;
121138 detectQueryChange ( ) ;
122139 querySpy = spectator . inject ( GraphQlRequestService ) . query ;
123140 } ;
124141
125142 test ( 'fires query on init for traces' , fakeAsync ( ( ) => {
126- init ( {
127- providers : [
128- mockProvider ( GraphQlRequestService , {
129- query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
130- } )
131- ]
132- } ) ;
143+ init (
144+ mockProvider ( GraphQlRequestService , {
145+ query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
146+ } )
147+ ) ;
148+
133149 // Traces tab is auto selected
134150 expect ( querySpy ) . toHaveBeenNthCalledWith (
135151 2 ,
@@ -142,8 +158,10 @@ describe('Explorer component', () => {
142158 expect . objectContaining ( { } )
143159 ) ;
144160
145- expect ( querySpy ) . toHaveBeenNthCalledWith (
146- 3 ,
161+ // RunFakeRxjs(({ expectObservable }) => {
162+ // ExpectObservable(spectator.component.resultsDashboard$).toBe('x', { x: undefined });
163+ // });
164+ expect ( querySpy ) . toHaveBeenCalledWith (
147165 expect . objectContaining ( {
148166 requestType : TRACES_GQL_REQUEST ,
149167 filters : [ ] ,
@@ -154,13 +172,11 @@ describe('Explorer component', () => {
154172 } ) ) ;
155173
156174 test ( 'fires query on filter change for traces' , fakeAsync ( ( ) => {
157- init ( {
158- providers : [
159- mockProvider ( GraphQlRequestService , {
160- query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
161- } )
162- ]
163- } ) ;
175+ init (
176+ mockProvider ( GraphQlRequestService , {
177+ query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
178+ } )
179+ ) ;
164180 const filterBar = spectator . query ( FilterBarComponent ) ! ;
165181
166182 // tslint:disable-next-line: no-object-literal-type-assertion
@@ -202,13 +218,11 @@ describe('Explorer component', () => {
202218 } ) ) ;
203219
204220 test ( 'fires query on init for spans' , fakeAsync ( ( ) => {
205- init ( {
206- providers : [
207- mockProvider ( GraphQlRequestService , {
208- query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
209- } )
210- ]
211- } ) ;
221+ init (
222+ mockProvider ( GraphQlRequestService , {
223+ query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
224+ } )
225+ ) ;
212226 querySpy . mockClear ( ) ;
213227
214228 // Select Spans tab
@@ -238,13 +252,11 @@ describe('Explorer component', () => {
238252 } ) ) ;
239253
240254 test ( 'fires query on init for traces' , fakeAsync ( ( ) => {
241- init ( {
242- providers : [
243- mockProvider ( GraphQlRequestService , {
244- query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
245- } )
246- ]
247- } ) ;
255+ init (
256+ mockProvider ( GraphQlRequestService , {
257+ query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
258+ } )
259+ ) ;
248260 // Select traces tab
249261 spectator . click ( spectator . queryAll ( 'ht-toggle-item' ) [ 1 ] ) ;
250262 detectQueryChange ( ) ;
@@ -291,13 +303,11 @@ describe('Explorer component', () => {
291303 } ) ) ;
292304
293305 test ( 'traces table fires query on series change' , fakeAsync ( ( ) => {
294- init ( {
295- providers : [
296- mockProvider ( GraphQlRequestService , {
297- query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
298- } )
299- ]
300- } ) ;
306+ init (
307+ mockProvider ( GraphQlRequestService , {
308+ query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
309+ } )
310+ ) ;
301311 spectator . query ( ExploreQueryEditorComponent ) ! . setSeries ( [ buildSeries ( 'second' , MetricAggregationType . Average ) ] ) ;
302312
303313 detectQueryChange ( ) ;
@@ -315,13 +325,11 @@ describe('Explorer component', () => {
315325 } ) ) ;
316326
317327 test ( 'visualization fires query on series change' , fakeAsync ( ( ) => {
318- init ( {
319- providers : [
320- mockProvider ( GraphQlRequestService , {
321- query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
322- } )
323- ]
324- } ) ;
328+ init (
329+ mockProvider ( GraphQlRequestService , {
330+ query : jest . fn ( ) . mockReturnValueOnce ( of ( mockAttributes ) ) . mockReturnValue ( EMPTY )
331+ } )
332+ ) ;
325333 querySpy . mockClear ( ) ;
326334
327335 spectator . query ( ExploreQueryEditorComponent ) ! . setSeries ( [ buildSeries ( 'second' , MetricAggregationType . Average ) ] ) ;
@@ -340,46 +348,60 @@ describe('Explorer component', () => {
340348 ) ;
341349 } ) ) ;
342350
343- test ( 'updates URL with query param when context toggled ' , fakeAsync ( ( ) => {
351+ test ( 'updates URL with query param when query updated ' , fakeAsync ( ( ) => {
344352 init ( ) ;
345353 const queryParamChangeSpy = spyOn ( spectator . inject ( NavigationService ) , 'addQueryParametersToUrl' ) ;
346- // Select Spans tab
347354 spectator . click ( spectator . queryAll ( 'ht-toggle-item' ) [ 1 ] ) ;
355+ spectator . query ( ExploreQueryEditorComponent ) ! . setSeries ( [ buildSeries ( 'second' , MetricAggregationType . Average ) ] ) ;
356+ spectator . query ( ExploreQueryEditorComponent ) ! . setInterval ( new TimeDuration ( 30 , TimeUnit . Second ) ) ;
357+ spectator . query ( ExploreQueryEditorComponent ) ! . updateGroupByKey (
358+ {
359+ keys : [ 'apiName' ] ,
360+ limit : 6 ,
361+ includeRest : true
362+ } ,
363+ 'apiName'
364+ ) ;
348365 detectQueryChange ( ) ;
349- expect ( queryParamChangeSpy ) . toHaveBeenLastCalledWith ( expect . objectContaining ( { scope : 'spans' } ) ) ;
350-
351- // Select Endpoint traces tab
352- spectator . click ( spectator . queryAll ( 'ht-toggle-item' ) [ 0 ] ) ;
353- detectQueryChange ( ) ;
354- expect ( queryParamChangeSpy ) . toHaveBeenLastCalledWith ( expect . objectContaining ( { scope : 'endpoint-traces' } ) ) ;
355- } ) ) ;
356-
357- test ( 'selects tab based on url' , fakeAsync ( ( ) => {
358- init ( {
359- providers : [
360- {
361- provide : ActivatedRoute ,
362- useValue : {
363- queryParamMap : of ( convertToParamMap ( { scope : 'spans' } ) )
364- }
365- }
366- ]
366+ expect ( queryParamChangeSpy ) . toHaveBeenLastCalledWith ( {
367+ scope : 'spans' ,
368+ series : [ 'column:avg(second)' ] ,
369+ group : 'apiName' ,
370+ limit : 6 ,
371+ other : true ,
372+ interval : '30s'
367373 } ) ;
368- expect ( spectator . component . context ) . toBe ( SPAN_SCOPE ) ;
369374 } ) ) ;
370375
371- test ( 'defaults to endpoints and sets url' , fakeAsync ( ( ) => {
376+ test ( 'sets state based on url' , fakeAsync ( ( ) => {
372377 init ( {
373- providers : [
374- {
375- provide : ActivatedRoute ,
376- useValue : {
377- queryParamMap : of ( convertToParamMap ( { } ) )
378- }
379- }
380- ]
378+ provide : ActivatedRoute ,
379+ useValue : {
380+ queryParamMap : of (
381+ convertToParamMap ( {
382+ scope : 'spans' ,
383+ series : 'line:distinct_count(apiName)' ,
384+ group : 'apiName' ,
385+ limit : '6' ,
386+ other : 'true' ,
387+ interval : '30s'
388+ } )
389+ )
390+ }
381391 } ) ;
382- expect ( spectator . component . context ) . toBe ( ObservabilityTraceType . Api ) ;
383- expect ( spectator . inject ( NavigationService ) . getQueryParameter ( 'scope' , 'unset' ) ) . toEqual ( 'endpoint-traces' ) ;
392+ expect ( spectator . query ( ToggleGroupComponent ) ?. activeItem ?. label ) . toBe ( 'Spans' ) ;
393+ expect ( spectator . query ( ExploreQueryGroupByEditorComponent ) ?. groupByKey ) . toBe ( 'apiName' ) ;
394+ expect ( spectator . query ( ExploreQueryLimitEditorComponent ) ?. limit ) . toBe ( 6 ) ;
395+ expect ( spectator . query ( ExploreQueryLimitEditorComponent ) ?. includeRest ) . toBe ( true ) ;
396+ expect ( spectator . query ( ExploreQuerySeriesEditorComponent ) ?. series ) . toEqual ( {
397+ specification : expect . objectContaining ( {
398+ aggregation : MetricAggregationType . DistinctCount ,
399+ name : 'apiName'
400+ } ) ,
401+ visualizationOptions : { type : CartesianSeriesVisualizationType . Line }
402+ } ) ;
403+ expect ( spectator . query ( ExploreQueryIntervalEditorComponent ) ?. interval ) . toEqual (
404+ new TimeDuration ( 30 , TimeUnit . Second )
405+ ) ;
384406 } ) ) ;
385407} ) ;
0 commit comments