@ethlete/components 1.0.0-next.29 → 1.0.0-next.30
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +26 -0
- package/fesm2022/ethlete-components.mjs +1033 -48
- package/fesm2022/ethlete-components.mjs.map +1 -1
- package/package.json +1 -1
- package/types/ethlete-components.d.ts +263 -2
|
@@ -5,13 +5,14 @@ import { injectStyleManager, SurfaceInteractiveDirective, RuntimeError, createCa
|
|
|
5
5
|
import { NgTemplateOutlet, DOCUMENT as DOCUMENT$1, NgComponentOutlet, Location, isPlatformBrowser } from '@angular/common';
|
|
6
6
|
import { DomSanitizer } from '@angular/platform-browser';
|
|
7
7
|
import { endOfMonth, startOfWeek, startOfMonth, addDays, addYears, addMonths, startOfDay, isSameMonth, getDate, setDate, lastDayOfMonth, isBefore, format, isSameDay, isAfter, parse, isValid, setMilliseconds, setSeconds, setMinutes, setHours } from 'date-fns';
|
|
8
|
-
import { withArgs, queryStateSignal, isQueryStateSuccess, isQueryStateFailure, isQueryStateLoading, queryComputed } from '@ethlete/query';
|
|
9
|
-
import { defer, filter, take, map, finalize, timer, switchMap, EMPTY, tap, Subject, fromEvent, merge, takeUntil, of, isObservable, from, catchError, distinctUntilChanged, concat, scan, combineLatest, debounceTime, animationFrameScheduler, exhaustMap, Observable, shareReplay
|
|
8
|
+
import { withArgs, queryStateSignal, isQueryStateSuccess, isQueryStateFailure, isQueryStateLoading, queryComputed, queryDevtoolsEntries, createQueryErrorResponse } from '@ethlete/query';
|
|
9
|
+
import { defer, filter, take, map, finalize, timer, switchMap, EMPTY, tap, Subject, fromEvent, merge, takeUntil, of, isObservable, from, catchError, distinctUntilChanged, concat, scan, combineLatest, debounceTime, animationFrameScheduler, interval, exhaustMap, Observable, shareReplay } from 'rxjs';
|
|
10
10
|
import { toObservable, takeUntilDestroyed, toSignal, outputToObservable, outputFromObservable, rxResource } from '@angular/core/rxjs-interop';
|
|
11
11
|
import { createManagedMetadataKey, metadata, validate, FORM_FIELD } from '@angular/forms/signals';
|
|
12
12
|
import { tap as tap$1 } from 'rxjs/operators';
|
|
13
13
|
import * as i1$1 from '@angular/router';
|
|
14
14
|
import { Router, RouterLink, RouterLinkActive, NavigationEnd } from '@angular/router';
|
|
15
|
+
import { HttpErrorResponse } from '@angular/common/http';
|
|
15
16
|
|
|
16
17
|
class ButtonPropertiesStylesComponent {
|
|
17
18
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: ButtonPropertiesStylesComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
@@ -2912,6 +2913,7 @@ const OVERLAY_ERROR_CODES = {
|
|
|
2912
2913
|
NO_CLOSEST_OVERLAY: 1205,
|
|
2913
2914
|
NESTED_OVERLAY_MAIN: 1206,
|
|
2914
2915
|
REF_OUTSIDE_OVERLAY: 1207,
|
|
2916
|
+
MISSING_OVERLAY_MAIN: 1208,
|
|
2915
2917
|
};
|
|
2916
2918
|
|
|
2917
2919
|
const getClosestOverlay = (element, openOverlays) => {
|
|
@@ -28417,6 +28419,51 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImpor
|
|
|
28417
28419
|
}]
|
|
28418
28420
|
}], ctorParameters: () => [] });
|
|
28419
28421
|
|
|
28422
|
+
const OVERLAY_MAIN_TOKEN = new InjectionToken('OVERLAY_MAIN_TOKEN');
|
|
28423
|
+
class OverlayMainDirective {
|
|
28424
|
+
constructor() {
|
|
28425
|
+
this.parent = inject(OVERLAY_MAIN_TOKEN, { optional: true, skipSelf: true });
|
|
28426
|
+
this.elementRef = inject(ElementRef);
|
|
28427
|
+
this.overlayRef = inject(OVERLAY_REF, { optional: true });
|
|
28428
|
+
this.overlayManager = injectOverlayManager();
|
|
28429
|
+
this.enabled = input(true, { ...(ngDevMode ? { debugName: "enabled" } : /* istanbul ignore next */ {}), alias: 'etOverlayMain', transform: booleanAttribute });
|
|
28430
|
+
}
|
|
28431
|
+
ngOnInit() {
|
|
28432
|
+
this.overlayRef = resolveClosestOverlay({
|
|
28433
|
+
overlayRef: this.overlayRef,
|
|
28434
|
+
element: this.elementRef,
|
|
28435
|
+
openOverlays: this.overlayManager.openOverlays(),
|
|
28436
|
+
});
|
|
28437
|
+
if (this.parent) {
|
|
28438
|
+
if (this.overlayRef.id === this.parent.overlayRef?.id && this.parent.enabled() && this.enabled()) {
|
|
28439
|
+
throw new RuntimeError(OVERLAY_ERROR_CODES.NESTED_OVERLAY_MAIN, '[OverlayMainDirective] An overlay must not contain nested <et-overlay-main> elements or etOverlayMain directives.');
|
|
28440
|
+
}
|
|
28441
|
+
}
|
|
28442
|
+
}
|
|
28443
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: OverlayMainDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
28444
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "22.0.7", type: OverlayMainDirective, isStandalone: true, selector: "[etOverlayMain], et-overlay-main", inputs: { enabled: { classPropertyName: "enabled", publicName: "etOverlayMain", isSignal: true, isRequired: false, transformFunction: null } }, host: { properties: { "class.et-overlay-main": "enabled()" } }, providers: [
|
|
28445
|
+
{
|
|
28446
|
+
provide: OVERLAY_MAIN_TOKEN,
|
|
28447
|
+
useExisting: OverlayMainDirective,
|
|
28448
|
+
},
|
|
28449
|
+
], ngImport: i0 }); }
|
|
28450
|
+
}
|
|
28451
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: OverlayMainDirective, decorators: [{
|
|
28452
|
+
type: Directive,
|
|
28453
|
+
args: [{
|
|
28454
|
+
selector: '[etOverlayMain], et-overlay-main',
|
|
28455
|
+
providers: [
|
|
28456
|
+
{
|
|
28457
|
+
provide: OVERLAY_MAIN_TOKEN,
|
|
28458
|
+
useExisting: OverlayMainDirective,
|
|
28459
|
+
},
|
|
28460
|
+
],
|
|
28461
|
+
host: {
|
|
28462
|
+
'[class.et-overlay-main]': 'enabled()',
|
|
28463
|
+
},
|
|
28464
|
+
}]
|
|
28465
|
+
}], propDecorators: { enabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "etOverlayMain", required: false }] }] } });
|
|
28466
|
+
|
|
28420
28467
|
const OVERLAY_BODY_TOKEN = new InjectionToken('OVERLAY_BODY_TOKEN');
|
|
28421
28468
|
class OverlayBodyComponent {
|
|
28422
28469
|
constructor() {
|
|
@@ -28424,6 +28471,7 @@ class OverlayBodyComponent {
|
|
|
28424
28471
|
this.elementRef = inject(ElementRef);
|
|
28425
28472
|
this.scrollObserver = inject(ScrollObserverDirective);
|
|
28426
28473
|
this.overlayManager = injectOverlayManager();
|
|
28474
|
+
this.overlayMain = inject(OVERLAY_MAIN_TOKEN, { optional: true });
|
|
28427
28475
|
this.dividers = input(false, /* @ts-ignore */
|
|
28428
28476
|
...(ngDevMode ? [{ debugName: "dividers" }] : /* istanbul ignore next */ []));
|
|
28429
28477
|
this.dividersEnabled = computed(() => this.dividers() === 'dynamic' || this.dividers() === 'static', /* @ts-ignore */
|
|
@@ -28451,6 +28499,9 @@ class OverlayBodyComponent {
|
|
|
28451
28499
|
nextFrame(() => this.enableDividerAnimations.set(true));
|
|
28452
28500
|
}
|
|
28453
28501
|
ngOnInit() {
|
|
28502
|
+
if (!this.overlayMain) {
|
|
28503
|
+
throw new RuntimeError(OVERLAY_ERROR_CODES.MISSING_OVERLAY_MAIN, '[OverlayBodyComponent] An overlay body must be used inside an <et-overlay-main> element or a host with the etOverlayMain directive.');
|
|
28504
|
+
}
|
|
28454
28505
|
this.overlayRef = resolveClosestOverlay({
|
|
28455
28506
|
overlayRef: this.overlayRef,
|
|
28456
28507
|
element: this.elementRef,
|
|
@@ -28663,8 +28714,12 @@ class OverlayFooterDirective {
|
|
|
28663
28714
|
this.overlayRef = inject(OVERLAY_REF, { optional: true });
|
|
28664
28715
|
this.elementRef = inject(ElementRef);
|
|
28665
28716
|
this.overlayManager = injectOverlayManager();
|
|
28717
|
+
this.overlayMain = inject(OVERLAY_MAIN_TOKEN, { optional: true });
|
|
28666
28718
|
}
|
|
28667
28719
|
ngOnInit() {
|
|
28720
|
+
if (!this.overlayMain) {
|
|
28721
|
+
throw new RuntimeError(OVERLAY_ERROR_CODES.MISSING_OVERLAY_MAIN, '[OverlayFooterDirective] An overlay footer must be used inside an <et-overlay-main> element or a host with the etOverlayMain directive.');
|
|
28722
|
+
}
|
|
28668
28723
|
this.overlayRef = resolveClosestOverlay({
|
|
28669
28724
|
overlayRef: this.overlayRef,
|
|
28670
28725
|
element: this.elementRef,
|
|
@@ -28701,8 +28756,12 @@ class OverlayHeaderDirective {
|
|
|
28701
28756
|
this.overlayRef = inject(OVERLAY_REF, { optional: true });
|
|
28702
28757
|
this.elementRef = inject(ElementRef);
|
|
28703
28758
|
this.overlayManager = injectOverlayManager();
|
|
28759
|
+
this.overlayMain = inject(OVERLAY_MAIN_TOKEN, { optional: true });
|
|
28704
28760
|
}
|
|
28705
28761
|
ngOnInit() {
|
|
28762
|
+
if (!this.overlayMain) {
|
|
28763
|
+
throw new RuntimeError(OVERLAY_ERROR_CODES.MISSING_OVERLAY_MAIN, '[OverlayHeaderDirective] An overlay header must be used inside an <et-overlay-main> element or a host with the etOverlayMain directive.');
|
|
28764
|
+
}
|
|
28706
28765
|
this.overlayRef = resolveClosestOverlay({
|
|
28707
28766
|
overlayRef: this.overlayRef,
|
|
28708
28767
|
element: this.elementRef,
|
|
@@ -28776,51 +28835,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImpor
|
|
|
28776
28835
|
}]
|
|
28777
28836
|
}], ctorParameters: () => [] });
|
|
28778
28837
|
|
|
28779
|
-
const OVERLAY_MAIN_TOKEN = new InjectionToken('OVERLAY_MAIN_TOKEN');
|
|
28780
|
-
class OverlayMainDirective {
|
|
28781
|
-
constructor() {
|
|
28782
|
-
this.parent = inject(OVERLAY_MAIN_TOKEN, { optional: true, skipSelf: true });
|
|
28783
|
-
this.elementRef = inject(ElementRef);
|
|
28784
|
-
this.overlayRef = inject(OVERLAY_REF, { optional: true });
|
|
28785
|
-
this.overlayManager = injectOverlayManager();
|
|
28786
|
-
this.enabled = input(true, { ...(ngDevMode ? { debugName: "enabled" } : /* istanbul ignore next */ {}), alias: 'etOverlayMain', transform: booleanAttribute });
|
|
28787
|
-
}
|
|
28788
|
-
ngOnInit() {
|
|
28789
|
-
this.overlayRef = resolveClosestOverlay({
|
|
28790
|
-
overlayRef: this.overlayRef,
|
|
28791
|
-
element: this.elementRef,
|
|
28792
|
-
openOverlays: this.overlayManager.openOverlays(),
|
|
28793
|
-
});
|
|
28794
|
-
if (this.parent) {
|
|
28795
|
-
if (this.overlayRef.id === this.parent.overlayRef?.id && this.parent.enabled() && this.enabled()) {
|
|
28796
|
-
throw new RuntimeError(OVERLAY_ERROR_CODES.NESTED_OVERLAY_MAIN, '[OverlayMainDirective] An overlay must not contain nested <et-overlay-main> elements or etOverlayMain directives.');
|
|
28797
|
-
}
|
|
28798
|
-
}
|
|
28799
|
-
}
|
|
28800
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: OverlayMainDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
28801
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "22.0.7", type: OverlayMainDirective, isStandalone: true, selector: "[etOverlayMain], et-overlay-main", inputs: { enabled: { classPropertyName: "enabled", publicName: "etOverlayMain", isSignal: true, isRequired: false, transformFunction: null } }, host: { properties: { "class.et-overlay-main": "enabled()" } }, providers: [
|
|
28802
|
-
{
|
|
28803
|
-
provide: OVERLAY_MAIN_TOKEN,
|
|
28804
|
-
useExisting: OverlayMainDirective,
|
|
28805
|
-
},
|
|
28806
|
-
], ngImport: i0 }); }
|
|
28807
|
-
}
|
|
28808
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: OverlayMainDirective, decorators: [{
|
|
28809
|
-
type: Directive,
|
|
28810
|
-
args: [{
|
|
28811
|
-
selector: '[etOverlayMain], et-overlay-main',
|
|
28812
|
-
providers: [
|
|
28813
|
-
{
|
|
28814
|
-
provide: OVERLAY_MAIN_TOKEN,
|
|
28815
|
-
useExisting: OverlayMainDirective,
|
|
28816
|
-
},
|
|
28817
|
-
],
|
|
28818
|
-
host: {
|
|
28819
|
-
'[class.et-overlay-main]': 'enabled()',
|
|
28820
|
-
},
|
|
28821
|
-
}]
|
|
28822
|
-
}], propDecorators: { enabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "etOverlayMain", required: false }] }] } });
|
|
28823
|
-
|
|
28824
28838
|
const isWritableSignal = (value) => isSignal(value) && typeof value.set === 'function';
|
|
28825
28839
|
const splitOpenerConfig = (config) => {
|
|
28826
28840
|
const { afterClosed, beforeClosed, afterOpened, ...overlayConfig } = config ?? {};
|
|
@@ -29937,6 +29951,977 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImpor
|
|
|
29937
29951
|
}]
|
|
29938
29952
|
}], ctorParameters: () => [], propDecorators: { pageDividers: [{ type: i0.Input, args: [{ isSignal: true, alias: "pageDividers", required: false }] }], sidebarContent: [{ type: i0.ViewChild, args: ['sidebarContentTpl', { isSignal: true }] }], sidebarHeaderContent: [{ type: i0.ContentChild, args: [i0.forwardRef(() => OVERLAY_HEADER_TEMPLATE_TOKEN), { isSignal: true }] }] } });
|
|
29939
29953
|
|
|
29954
|
+
const kindOf = (value) => {
|
|
29955
|
+
if (value === null)
|
|
29956
|
+
return 'null';
|
|
29957
|
+
if (value === undefined)
|
|
29958
|
+
return 'undefined';
|
|
29959
|
+
if (Array.isArray(value))
|
|
29960
|
+
return 'array';
|
|
29961
|
+
return typeof value;
|
|
29962
|
+
};
|
|
29963
|
+
/**
|
|
29964
|
+
* A recursive, collapsible, searchable JSON tree used by the query devtools value explorer. Renders
|
|
29965
|
+
* the *transformed* value the app actually sees (post `transformResponse`). Self-recurses via its
|
|
29966
|
+
* own selector.
|
|
29967
|
+
*/
|
|
29968
|
+
class QueryDevtoolsJsonComponent {
|
|
29969
|
+
constructor() {
|
|
29970
|
+
this.value = input(/* @ts-ignore */
|
|
29971
|
+
...(ngDevMode ? [undefined, { debugName: "value" }] : /* istanbul ignore next */ []));
|
|
29972
|
+
this.nodeKey = input(null, /* @ts-ignore */
|
|
29973
|
+
...(ngDevMode ? [{ debugName: "nodeKey" }] : /* istanbul ignore next */ []));
|
|
29974
|
+
this.depth = input(0, /* @ts-ignore */
|
|
29975
|
+
...(ngDevMode ? [{ debugName: "depth" }] : /* istanbul ignore next */ []));
|
|
29976
|
+
/** Lowercased search term; when set, the tree auto-expands and matches are highlighted. */
|
|
29977
|
+
this.search = input('', /* @ts-ignore */
|
|
29978
|
+
...(ngDevMode ? [{ debugName: "search" }] : /* istanbul ignore next */ []));
|
|
29979
|
+
/** Full path of this node from the explorer root, used as the key for persisted expansion. */
|
|
29980
|
+
this.path = input('', /* @ts-ignore */
|
|
29981
|
+
...(ngDevMode ? [{ debugName: "path" }] : /* istanbul ignore next */ []));
|
|
29982
|
+
/** Persisted paths explicitly expanded (overrides the depth default). */
|
|
29983
|
+
this.expandedPaths = input(null, /* @ts-ignore */
|
|
29984
|
+
...(ngDevMode ? [{ debugName: "expandedPaths" }] : /* istanbul ignore next */ []));
|
|
29985
|
+
/** Persisted paths explicitly collapsed (overrides the depth default). */
|
|
29986
|
+
this.collapsedPaths = input(null, /* @ts-ignore */
|
|
29987
|
+
...(ngDevMode ? [{ debugName: "collapsedPaths" }] : /* istanbul ignore next */ []));
|
|
29988
|
+
/** When provided, expansion is externally persisted via this callback instead of local state. */
|
|
29989
|
+
this.toggleFn = input(null, /* @ts-ignore */
|
|
29990
|
+
...(ngDevMode ? [{ debugName: "toggleFn" }] : /* istanbul ignore next */ []));
|
|
29991
|
+
this.kind = computed(() => kindOf(this.value()), /* @ts-ignore */
|
|
29992
|
+
...(ngDevMode ? [{ debugName: "kind" }] : /* istanbul ignore next */ []));
|
|
29993
|
+
this.isContainer = computed(() => this.kind() === 'array' || this.kind() === 'object', /* @ts-ignore */
|
|
29994
|
+
...(ngDevMode ? [{ debugName: "isContainer" }] : /* istanbul ignore next */ []));
|
|
29995
|
+
this.entries = computed(() => {
|
|
29996
|
+
const value = this.value();
|
|
29997
|
+
if (Array.isArray(value))
|
|
29998
|
+
return value.map((v, i) => ({ k: String(i), v }));
|
|
29999
|
+
if (value && typeof value === 'object') {
|
|
30000
|
+
return Object.entries(value).map(([k, v]) => ({ k, v }));
|
|
30001
|
+
}
|
|
30002
|
+
return [];
|
|
30003
|
+
}, /* @ts-ignore */
|
|
30004
|
+
...(ngDevMode ? [{ debugName: "entries" }] : /* istanbul ignore next */ []));
|
|
30005
|
+
this.localExpanded = linkedSignal(() => this.depth() < 1, /* @ts-ignore */
|
|
30006
|
+
...(ngDevMode ? [{ debugName: "localExpanded" }] : /* istanbul ignore next */ []));
|
|
30007
|
+
this.expanded = computed(() => {
|
|
30008
|
+
// Externally-persisted mode: resolve from the expanded/collapsed path sets, else the depth default.
|
|
30009
|
+
if (this.toggleFn()) {
|
|
30010
|
+
const path = this.path();
|
|
30011
|
+
if (this.collapsedPaths()?.has(path))
|
|
30012
|
+
return false;
|
|
30013
|
+
if (this.expandedPaths()?.has(path))
|
|
30014
|
+
return true;
|
|
30015
|
+
return this.depth() < 1;
|
|
30016
|
+
}
|
|
30017
|
+
return this.localExpanded();
|
|
30018
|
+
}, /* @ts-ignore */
|
|
30019
|
+
...(ngDevMode ? [{ debugName: "expanded" }] : /* istanbul ignore next */ []));
|
|
30020
|
+
this.effectiveExpanded = computed(() => (this.search() ? true : this.expanded()), /* @ts-ignore */
|
|
30021
|
+
...(ngDevMode ? [{ debugName: "effectiveExpanded" }] : /* istanbul ignore next */ []));
|
|
30022
|
+
this.preview = computed(() => {
|
|
30023
|
+
const value = this.value();
|
|
30024
|
+
if (Array.isArray(value))
|
|
30025
|
+
return value.length ? `[…] ${value.length}` : '[]';
|
|
30026
|
+
const count = value ? Object.keys(value).length : 0;
|
|
30027
|
+
return count ? `{…} ${count}` : '{}';
|
|
30028
|
+
}, /* @ts-ignore */
|
|
30029
|
+
...(ngDevMode ? [{ debugName: "preview" }] : /* istanbul ignore next */ []));
|
|
30030
|
+
this.display = computed(() => {
|
|
30031
|
+
const value = this.value();
|
|
30032
|
+
const kind = this.kind();
|
|
30033
|
+
if (kind === 'string')
|
|
30034
|
+
return `"${value}"`;
|
|
30035
|
+
if (kind === 'null')
|
|
30036
|
+
return 'null';
|
|
30037
|
+
if (kind === 'undefined')
|
|
30038
|
+
return 'undefined';
|
|
30039
|
+
return String(value);
|
|
30040
|
+
}, /* @ts-ignore */
|
|
30041
|
+
...(ngDevMode ? [{ debugName: "display" }] : /* istanbul ignore next */ []));
|
|
30042
|
+
this.keyHit = computed(() => {
|
|
30043
|
+
const term = this.search();
|
|
30044
|
+
const key = this.nodeKey();
|
|
30045
|
+
return !!term && !!key && key.toLowerCase().includes(term);
|
|
30046
|
+
}, /* @ts-ignore */
|
|
30047
|
+
...(ngDevMode ? [{ debugName: "keyHit" }] : /* istanbul ignore next */ []));
|
|
30048
|
+
this.valueHit = computed(() => {
|
|
30049
|
+
const term = this.search();
|
|
30050
|
+
return !!term && this.display().toLowerCase().includes(term);
|
|
30051
|
+
}, /* @ts-ignore */
|
|
30052
|
+
...(ngDevMode ? [{ debugName: "valueHit" }] : /* istanbul ignore next */ []));
|
|
30053
|
+
}
|
|
30054
|
+
childPath(key) {
|
|
30055
|
+
const path = this.path();
|
|
30056
|
+
return path ? `${path}.${key}` : key;
|
|
30057
|
+
}
|
|
30058
|
+
toggle() {
|
|
30059
|
+
const toggleFn = this.toggleFn();
|
|
30060
|
+
if (toggleFn) {
|
|
30061
|
+
toggleFn(this.path(), !this.expanded());
|
|
30062
|
+
return;
|
|
30063
|
+
}
|
|
30064
|
+
this.localExpanded.set(!this.localExpanded());
|
|
30065
|
+
}
|
|
30066
|
+
copyValue() {
|
|
30067
|
+
try {
|
|
30068
|
+
navigator.clipboard?.writeText(JSON.stringify(this.value(), null, 2));
|
|
30069
|
+
}
|
|
30070
|
+
catch {
|
|
30071
|
+
// clipboard unavailable
|
|
30072
|
+
}
|
|
30073
|
+
}
|
|
30074
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: QueryDevtoolsJsonComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
30075
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.7", type: QueryDevtoolsJsonComponent, isStandalone: true, selector: "et-query-devtools-json", inputs: { value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null }, nodeKey: { classPropertyName: "nodeKey", publicName: "nodeKey", isSignal: true, isRequired: false, transformFunction: null }, depth: { classPropertyName: "depth", publicName: "depth", isSignal: true, isRequired: false, transformFunction: null }, search: { classPropertyName: "search", publicName: "search", isSignal: true, isRequired: false, transformFunction: null }, path: { classPropertyName: "path", publicName: "path", isSignal: true, isRequired: false, transformFunction: null }, expandedPaths: { classPropertyName: "expandedPaths", publicName: "expandedPaths", isSignal: true, isRequired: false, transformFunction: null }, collapsedPaths: { classPropertyName: "collapsedPaths", publicName: "collapsedPaths", isSignal: true, isRequired: false, transformFunction: null }, toggleFn: { classPropertyName: "toggleFn", publicName: "toggleFn", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
30076
|
+
@if (isContainer()) {
|
|
30077
|
+
<div class="et-query-devtools-json-node">
|
|
30078
|
+
<button
|
|
30079
|
+
[attr.aria-expanded]="effectiveExpanded()"
|
|
30080
|
+
(click)="toggle()"
|
|
30081
|
+
class="et-query-devtools-json-row et-query-devtools-json-toggle"
|
|
30082
|
+
type="button"
|
|
30083
|
+
>
|
|
30084
|
+
<span class="et-query-devtools-json-caret">{{ effectiveExpanded() ? '▾' : '▸' }}</span>
|
|
30085
|
+
@if (nodeKey() !== null) {
|
|
30086
|
+
<span [class.et-query-devtools-json-hit]="keyHit()" class="et-query-devtools-json-key">{{
|
|
30087
|
+
nodeKey()
|
|
30088
|
+
}}</span>
|
|
30089
|
+
<span class="et-query-devtools-json-colon">:</span>
|
|
30090
|
+
}
|
|
30091
|
+
<span class="et-query-devtools-json-preview">{{ preview() }}</span>
|
|
30092
|
+
</button>
|
|
30093
|
+
|
|
30094
|
+
@if (effectiveExpanded()) {
|
|
30095
|
+
<div class="et-query-devtools-json-children">
|
|
30096
|
+
@for (entry of entries(); track entry.k) {
|
|
30097
|
+
<et-query-devtools-json
|
|
30098
|
+
[value]="entry.v"
|
|
30099
|
+
[nodeKey]="entry.k"
|
|
30100
|
+
[depth]="depth() + 1"
|
|
30101
|
+
[path]="childPath(entry.k)"
|
|
30102
|
+
[search]="search()"
|
|
30103
|
+
[expandedPaths]="expandedPaths()"
|
|
30104
|
+
[collapsedPaths]="collapsedPaths()"
|
|
30105
|
+
[toggleFn]="toggleFn()"
|
|
30106
|
+
/>
|
|
30107
|
+
}
|
|
30108
|
+
</div>
|
|
30109
|
+
}
|
|
30110
|
+
</div>
|
|
30111
|
+
} @else {
|
|
30112
|
+
<div [attr.data-kind]="kind()" class="et-query-devtools-json-row et-query-devtools-json-leaf">
|
|
30113
|
+
@if (nodeKey() !== null) {
|
|
30114
|
+
<span [class.et-query-devtools-json-hit]="keyHit()" class="et-query-devtools-json-key">{{ nodeKey() }}</span>
|
|
30115
|
+
<span class="et-query-devtools-json-colon">:</span>
|
|
30116
|
+
}
|
|
30117
|
+
<span [class.et-query-devtools-json-hit]="valueHit()" class="et-query-devtools-json-value">{{
|
|
30118
|
+
display()
|
|
30119
|
+
}}</span>
|
|
30120
|
+
<button (click)="copyValue()" class="et-query-devtools-json-copy" type="button" title="Copy value">⧉</button>
|
|
30121
|
+
</div>
|
|
30122
|
+
}
|
|
30123
|
+
`, isInline: true, dependencies: [{ kind: "component", type: QueryDevtoolsJsonComponent, selector: "et-query-devtools-json", inputs: ["value", "nodeKey", "depth", "search", "path", "expandedPaths", "collapsedPaths", "toggleFn"] }], encapsulation: i0.ViewEncapsulation.None }); }
|
|
30124
|
+
}
|
|
30125
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: QueryDevtoolsJsonComponent, decorators: [{
|
|
30126
|
+
type: Component,
|
|
30127
|
+
args: [{
|
|
30128
|
+
selector: 'et-query-devtools-json',
|
|
30129
|
+
template: `
|
|
30130
|
+
@if (isContainer()) {
|
|
30131
|
+
<div class="et-query-devtools-json-node">
|
|
30132
|
+
<button
|
|
30133
|
+
[attr.aria-expanded]="effectiveExpanded()"
|
|
30134
|
+
(click)="toggle()"
|
|
30135
|
+
class="et-query-devtools-json-row et-query-devtools-json-toggle"
|
|
30136
|
+
type="button"
|
|
30137
|
+
>
|
|
30138
|
+
<span class="et-query-devtools-json-caret">{{ effectiveExpanded() ? '▾' : '▸' }}</span>
|
|
30139
|
+
@if (nodeKey() !== null) {
|
|
30140
|
+
<span [class.et-query-devtools-json-hit]="keyHit()" class="et-query-devtools-json-key">{{
|
|
30141
|
+
nodeKey()
|
|
30142
|
+
}}</span>
|
|
30143
|
+
<span class="et-query-devtools-json-colon">:</span>
|
|
30144
|
+
}
|
|
30145
|
+
<span class="et-query-devtools-json-preview">{{ preview() }}</span>
|
|
30146
|
+
</button>
|
|
30147
|
+
|
|
30148
|
+
@if (effectiveExpanded()) {
|
|
30149
|
+
<div class="et-query-devtools-json-children">
|
|
30150
|
+
@for (entry of entries(); track entry.k) {
|
|
30151
|
+
<et-query-devtools-json
|
|
30152
|
+
[value]="entry.v"
|
|
30153
|
+
[nodeKey]="entry.k"
|
|
30154
|
+
[depth]="depth() + 1"
|
|
30155
|
+
[path]="childPath(entry.k)"
|
|
30156
|
+
[search]="search()"
|
|
30157
|
+
[expandedPaths]="expandedPaths()"
|
|
30158
|
+
[collapsedPaths]="collapsedPaths()"
|
|
30159
|
+
[toggleFn]="toggleFn()"
|
|
30160
|
+
/>
|
|
30161
|
+
}
|
|
30162
|
+
</div>
|
|
30163
|
+
}
|
|
30164
|
+
</div>
|
|
30165
|
+
} @else {
|
|
30166
|
+
<div [attr.data-kind]="kind()" class="et-query-devtools-json-row et-query-devtools-json-leaf">
|
|
30167
|
+
@if (nodeKey() !== null) {
|
|
30168
|
+
<span [class.et-query-devtools-json-hit]="keyHit()" class="et-query-devtools-json-key">{{ nodeKey() }}</span>
|
|
30169
|
+
<span class="et-query-devtools-json-colon">:</span>
|
|
30170
|
+
}
|
|
30171
|
+
<span [class.et-query-devtools-json-hit]="valueHit()" class="et-query-devtools-json-value">{{
|
|
30172
|
+
display()
|
|
30173
|
+
}}</span>
|
|
30174
|
+
<button (click)="copyValue()" class="et-query-devtools-json-copy" type="button" title="Copy value">⧉</button>
|
|
30175
|
+
</div>
|
|
30176
|
+
}
|
|
30177
|
+
`,
|
|
30178
|
+
encapsulation: ViewEncapsulation.None,
|
|
30179
|
+
imports: [QueryDevtoolsJsonComponent],
|
|
30180
|
+
}]
|
|
30181
|
+
}], propDecorators: { value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }], nodeKey: [{ type: i0.Input, args: [{ isSignal: true, alias: "nodeKey", required: false }] }], depth: [{ type: i0.Input, args: [{ isSignal: true, alias: "depth", required: false }] }], search: [{ type: i0.Input, args: [{ isSignal: true, alias: "search", required: false }] }], path: [{ type: i0.Input, args: [{ isSignal: true, alias: "path", required: false }] }], expandedPaths: [{ type: i0.Input, args: [{ isSignal: true, alias: "expandedPaths", required: false }] }], collapsedPaths: [{ type: i0.Input, args: [{ isSignal: true, alias: "collapsedPaths", required: false }] }], toggleFn: [{ type: i0.Input, args: [{ isSignal: true, alias: "toggleFn", required: false }] }] } });
|
|
30182
|
+
|
|
30183
|
+
/**
|
|
30184
|
+
* The floating toggle button for the query devtools. Rendered with `ShadowDom` encapsulation so the
|
|
30185
|
+
* host application's global CSS (Tailwind resets, button styles, …) can never touch it and its own
|
|
30186
|
+
* styles can never leak out. Uses px (not rem) internally so it doesn't depend on the host's root
|
|
30187
|
+
* font-size; theme accent colour is read from an inherited custom property with a fallback.
|
|
30188
|
+
*/
|
|
30189
|
+
class QueryDevtoolsToggleComponent {
|
|
30190
|
+
constructor() {
|
|
30191
|
+
this.openChange = output();
|
|
30192
|
+
}
|
|
30193
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: QueryDevtoolsToggleComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
30194
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "22.0.7", type: QueryDevtoolsToggleComponent, isStandalone: true, selector: "et-query-devtools-toggle", outputs: { openChange: "openChange" }, ngImport: i0, template: `
|
|
30195
|
+
<button (click)="openChange.emit()" type="button" title="Toggle query devtools (Ctrl/Cmd + Alt + Q)">
|
|
30196
|
+
<svg viewBox="0 0 24 24" aria-hidden="true">
|
|
30197
|
+
<ellipse cx="12" cy="6" rx="7.5" ry="3" />
|
|
30198
|
+
<path d="M4.5 6v6c0 1.66 3.36 3 7.5 3s7.5-1.34 7.5-3V6" />
|
|
30199
|
+
<path d="M4.5 12v6c0 1.66 3.36 3 7.5 3s7.5-1.34 7.5-3v-6" />
|
|
30200
|
+
</svg>
|
|
30201
|
+
<span class="label">Query</span>
|
|
30202
|
+
</button>
|
|
30203
|
+
`, isInline: true, styles: [":host{position:fixed;inset-block-end:16px;inset-inline-end:16px;z-index:2147483001}button{--_accent: var(--et-theme-color-primary-solid, #60a5fa);position:relative;display:inline-flex;align-items:center;gap:8px;padding:10px 16px 10px 14px;border:none;border-radius:999px;background:linear-gradient(135deg,#1f1f23,#2a2a30);color:#fafafa;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;font-size:13px;font-weight:600;letter-spacing:.02em;cursor:pointer;box-shadow:0 6px 20px #00000059,inset 0 0 0 1px #ffffff14;transition:transform .15s ease,box-shadow .2s ease}button:before{content:\"\";position:absolute;inset:0;border-radius:inherit;padding:1px;background:linear-gradient(135deg,var(--_accent),transparent 60%);-webkit-mask:linear-gradient(#000 0 0) content-box,linear-gradient(#000 0 0);-webkit-mask-composite:xor;mask-composite:exclude;opacity:.7;transition:opacity .2s ease}button:hover{transform:translateY(-2px);box-shadow:0 10px 28px #0006,0 0 0 4px color-mix(in srgb,var(--_accent) 22%,transparent),inset 0 0 0 1px #ffffff1a}button:hover:before{opacity:1}svg{inline-size:16px;block-size:16px;fill:none;stroke:var(--_accent);stroke-width:1.6;stroke-linecap:round;stroke-linejoin:round}.label{line-height:1}\n"], encapsulation: i0.ViewEncapsulation.ShadowDom }); }
|
|
30204
|
+
}
|
|
30205
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: QueryDevtoolsToggleComponent, decorators: [{
|
|
30206
|
+
type: Component,
|
|
30207
|
+
args: [{ selector: 'et-query-devtools-toggle', template: `
|
|
30208
|
+
<button (click)="openChange.emit()" type="button" title="Toggle query devtools (Ctrl/Cmd + Alt + Q)">
|
|
30209
|
+
<svg viewBox="0 0 24 24" aria-hidden="true">
|
|
30210
|
+
<ellipse cx="12" cy="6" rx="7.5" ry="3" />
|
|
30211
|
+
<path d="M4.5 6v6c0 1.66 3.36 3 7.5 3s7.5-1.34 7.5-3V6" />
|
|
30212
|
+
<path d="M4.5 12v6c0 1.66 3.36 3 7.5 3s7.5-1.34 7.5-3v-6" />
|
|
30213
|
+
</svg>
|
|
30214
|
+
<span class="label">Query</span>
|
|
30215
|
+
</button>
|
|
30216
|
+
`, encapsulation: ViewEncapsulation.ShadowDom, styles: [":host{position:fixed;inset-block-end:16px;inset-inline-end:16px;z-index:2147483001}button{--_accent: var(--et-theme-color-primary-solid, #60a5fa);position:relative;display:inline-flex;align-items:center;gap:8px;padding:10px 16px 10px 14px;border:none;border-radius:999px;background:linear-gradient(135deg,#1f1f23,#2a2a30);color:#fafafa;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;font-size:13px;font-weight:600;letter-spacing:.02em;cursor:pointer;box-shadow:0 6px 20px #00000059,inset 0 0 0 1px #ffffff14;transition:transform .15s ease,box-shadow .2s ease}button:before{content:\"\";position:absolute;inset:0;border-radius:inherit;padding:1px;background:linear-gradient(135deg,var(--_accent),transparent 60%);-webkit-mask:linear-gradient(#000 0 0) content-box,linear-gradient(#000 0 0);-webkit-mask-composite:xor;mask-composite:exclude;opacity:.7;transition:opacity .2s ease}button:hover{transform:translateY(-2px);box-shadow:0 10px 28px #0006,0 0 0 4px color-mix(in srgb,var(--_accent) 22%,transparent),inset 0 0 0 1px #ffffff1a}button:hover:before{opacity:1}svg{inline-size:16px;block-size:16px;fill:none;stroke:var(--_accent);stroke-width:1.6;stroke-linecap:round;stroke-linejoin:round}.label{line-height:1}\n"] }]
|
|
30217
|
+
}], propDecorators: { openChange: [{ type: i0.Output, args: ["openChange"] }] } });
|
|
30218
|
+
|
|
30219
|
+
const STORAGE_KEY = 'ethlete:query:devtools:v4';
|
|
30220
|
+
const MAX_EVENTS = 100;
|
|
30221
|
+
const DEFAULT_HEIGHT = 360;
|
|
30222
|
+
const MIN_HEIGHT = 200;
|
|
30223
|
+
const readPersistedState = () => {
|
|
30224
|
+
try {
|
|
30225
|
+
const raw = sessionStorage.getItem(STORAGE_KEY);
|
|
30226
|
+
return raw ? JSON.parse(raw) : {};
|
|
30227
|
+
}
|
|
30228
|
+
catch {
|
|
30229
|
+
return {};
|
|
30230
|
+
}
|
|
30231
|
+
};
|
|
30232
|
+
/**
|
|
30233
|
+
* Slims a value for a shareable report: long strings are truncated and long arrays keep only the
|
|
30234
|
+
* first couple of entries, replacing the repetitive tail with a `… (N more)` marker, so a big
|
|
30235
|
+
* response collapses to a representative sample.
|
|
30236
|
+
*/
|
|
30237
|
+
const slimForReport = (value, depth = 0) => {
|
|
30238
|
+
if (typeof value === 'string')
|
|
30239
|
+
return value.length > 200 ? `${value.slice(0, 200)}…` : value;
|
|
30240
|
+
if (depth > 6)
|
|
30241
|
+
return '…';
|
|
30242
|
+
if (Array.isArray(value)) {
|
|
30243
|
+
if (value.length > 3) {
|
|
30244
|
+
return [...value.slice(0, 2).map((v) => slimForReport(v, depth + 1)), `… (${value.length - 2} more)`];
|
|
30245
|
+
}
|
|
30246
|
+
return value.map((v) => slimForReport(v, depth + 1));
|
|
30247
|
+
}
|
|
30248
|
+
if (value && typeof value === 'object') {
|
|
30249
|
+
const out = {};
|
|
30250
|
+
for (const [key, val] of Object.entries(value))
|
|
30251
|
+
out[key] = slimForReport(val, depth + 1);
|
|
30252
|
+
return out;
|
|
30253
|
+
}
|
|
30254
|
+
return value;
|
|
30255
|
+
};
|
|
30256
|
+
/** Best-effort decode of a JWT payload for the auth tab. Returns `null` for anything non-decodable. */
|
|
30257
|
+
const decodeJwtPayload = (token) => {
|
|
30258
|
+
if (!token)
|
|
30259
|
+
return null;
|
|
30260
|
+
try {
|
|
30261
|
+
const payload = token.split('.')[1];
|
|
30262
|
+
if (!payload)
|
|
30263
|
+
return null;
|
|
30264
|
+
const normalized = payload.replace(/-/g, '+').replace(/_/g, '/');
|
|
30265
|
+
const decoded = atob(normalized);
|
|
30266
|
+
const json = decodeURIComponent(decoded
|
|
30267
|
+
.split('')
|
|
30268
|
+
.map((c) => '%' + ('00' + c.charCodeAt(0).toString(16)).slice(-2))
|
|
30269
|
+
.join(''));
|
|
30270
|
+
return JSON.parse(json);
|
|
30271
|
+
}
|
|
30272
|
+
catch {
|
|
30273
|
+
return null;
|
|
30274
|
+
}
|
|
30275
|
+
};
|
|
30276
|
+
/**
|
|
30277
|
+
* A floating, dockable panel that inspects the live state of the signals-first `@ethlete/query`
|
|
30278
|
+
* system: queries, stacks, sequences, bearer auth providers, the repository cache and a rolling
|
|
30279
|
+
* event log.
|
|
30280
|
+
*
|
|
30281
|
+
* Requires `provideQueryDevtools()` in the application providers — without it the registry stays
|
|
30282
|
+
* empty and the panel shows nothing.
|
|
30283
|
+
*/
|
|
30284
|
+
class QueryDevtoolsComponent {
|
|
30285
|
+
constructor() {
|
|
30286
|
+
this.hostEl = inject(ElementRef);
|
|
30287
|
+
this.document = inject(DOCUMENT$1);
|
|
30288
|
+
this.eventIdCounter = 0;
|
|
30289
|
+
this.lastSelectionKey = '';
|
|
30290
|
+
this.persisted = readPersistedState();
|
|
30291
|
+
this.tabs = [
|
|
30292
|
+
{ id: 'queries', label: 'Queries' },
|
|
30293
|
+
{ id: 'stacks', label: 'Stacks' },
|
|
30294
|
+
{ id: 'sequences', label: 'Sequences' },
|
|
30295
|
+
{ id: 'auth', label: 'Auth' },
|
|
30296
|
+
{ id: 'ws', label: 'Sockets' },
|
|
30297
|
+
{ id: 'cache', label: 'Cache' },
|
|
30298
|
+
{ id: 'events', label: 'Events' },
|
|
30299
|
+
];
|
|
30300
|
+
this.open = signal(this.persisted.open ?? false, /* @ts-ignore */
|
|
30301
|
+
...(ngDevMode ? [{ debugName: "open" }] : /* istanbul ignore next */ []));
|
|
30302
|
+
this.panelHeight = signal(this.persisted.height ?? DEFAULT_HEIGHT, /* @ts-ignore */
|
|
30303
|
+
...(ngDevMode ? [{ debugName: "panelHeight" }] : /* istanbul ignore next */ []));
|
|
30304
|
+
this.resizing = signal(false, /* @ts-ignore */
|
|
30305
|
+
...(ngDevMode ? [{ debugName: "resizing" }] : /* istanbul ignore next */ []));
|
|
30306
|
+
this.activeTab = signal(this.persisted.activeTab ?? 'queries', /* @ts-ignore */
|
|
30307
|
+
...(ngDevMode ? [{ debugName: "activeTab" }] : /* istanbul ignore next */ []));
|
|
30308
|
+
this.selectedClientName = signal(this.persisted.selectedClientName ?? null, /* @ts-ignore */
|
|
30309
|
+
...(ngDevMode ? [{ debugName: "selectedClientName" }] : /* istanbul ignore next */ []));
|
|
30310
|
+
this.selectedQueryId = signal(this.persisted.selectedQueryId ?? null, /* @ts-ignore */
|
|
30311
|
+
...(ngDevMode ? [{ debugName: "selectedQueryId" }] : /* istanbul ignore next */ []));
|
|
30312
|
+
// Independent per-drawer selection so the Stacks / Sequences drawers don't share the Queries tab's.
|
|
30313
|
+
this.stackSelectedQueryId = signal(null, /* @ts-ignore */
|
|
30314
|
+
...(ngDevMode ? [{ debugName: "stackSelectedQueryId" }] : /* istanbul ignore next */ []));
|
|
30315
|
+
this.sequenceSelectedQueryId = signal(null, /* @ts-ignore */
|
|
30316
|
+
...(ngDevMode ? [{ debugName: "sequenceSelectedQueryId" }] : /* istanbul ignore next */ []));
|
|
30317
|
+
this.eventLog = signal([], /* @ts-ignore */
|
|
30318
|
+
...(ngDevMode ? [{ debugName: "eventLog" }] : /* istanbul ignore next */ []));
|
|
30319
|
+
/** Keys (`<entryId>:<stepIndex>`) of the sequence steps whose in/out detail is expanded. */
|
|
30320
|
+
this.expandedSteps = signal(new Set(this.persisted.expandedSteps ?? []), /* @ts-ignore */
|
|
30321
|
+
...(ngDevMode ? [{ debugName: "expandedSteps" }] : /* istanbul ignore next */ []));
|
|
30322
|
+
/** Shared value-explorer search term. */
|
|
30323
|
+
this.jsonSearch = signal(this.persisted.jsonSearch ?? '', /* @ts-ignore */
|
|
30324
|
+
...(ngDevMode ? [{ debugName: "jsonSearch" }] : /* istanbul ignore next */ []));
|
|
30325
|
+
this.jsonSearchTerm = computed(() => this.jsonSearch().trim().toLowerCase(), /* @ts-ignore */
|
|
30326
|
+
...(ngDevMode ? [{ debugName: "jsonSearchTerm" }] : /* istanbul ignore next */ []));
|
|
30327
|
+
/** Path-keyed value-explorer expansion overrides (persisted so open trees survive a reload). */
|
|
30328
|
+
this.jsonExpandedPaths = signal(new Set(this.persisted.jsonExpanded ?? []), /* @ts-ignore */
|
|
30329
|
+
...(ngDevMode ? [{ debugName: "jsonExpandedPaths" }] : /* istanbul ignore next */ []));
|
|
30330
|
+
this.jsonCollapsedPaths = signal(new Set(this.persisted.jsonCollapsed ?? []), /* @ts-ignore */
|
|
30331
|
+
...(ngDevMode ? [{ debugName: "jsonCollapsedPaths" }] : /* istanbul ignore next */ []));
|
|
30332
|
+
/** JIT editor state (response / args editing on the selected query). */
|
|
30333
|
+
this.editorMode = signal('none', /* @ts-ignore */
|
|
30334
|
+
...(ngDevMode ? [{ debugName: "editorMode" }] : /* istanbul ignore next */ []));
|
|
30335
|
+
this.responseDraft = signal('', /* @ts-ignore */
|
|
30336
|
+
...(ngDevMode ? [{ debugName: "responseDraft" }] : /* istanbul ignore next */ []));
|
|
30337
|
+
this.argsDraft = signal('', /* @ts-ignore */
|
|
30338
|
+
...(ngDevMode ? [{ debugName: "argsDraft" }] : /* istanbul ignore next */ []));
|
|
30339
|
+
this.editError = signal(null, /* @ts-ignore */
|
|
30340
|
+
...(ngDevMode ? [{ debugName: "editError" }] : /* istanbul ignore next */ []));
|
|
30341
|
+
/** Transient "Copied!" feedback for the copy-report action. */
|
|
30342
|
+
this.copiedReport = signal(false, /* @ts-ignore */
|
|
30343
|
+
...(ngDevMode ? [{ debugName: "copiedReport" }] : /* istanbul ignore next */ []));
|
|
30344
|
+
/** 1-second tick driving the cache freshness countdowns. */
|
|
30345
|
+
this.clock = toSignal(interval(1000), { initialValue: 0 });
|
|
30346
|
+
/** "Inspect" mode: hover the live UI to find the query that a component created. */
|
|
30347
|
+
this.inspectActive = signal(false, /* @ts-ignore */
|
|
30348
|
+
...(ngDevMode ? [{ debugName: "inspectActive" }] : /* istanbul ignore next */ []));
|
|
30349
|
+
this.inspectHover = signal(null, /* @ts-ignore */
|
|
30350
|
+
...(ngDevMode ? [{ debugName: "inspectHover" }] : /* istanbul ignore next */ []));
|
|
30351
|
+
/** When set (via inspect), the Queries list is filtered to exactly these entry ids. */
|
|
30352
|
+
this.inspectFilterIds = signal(this.persisted.inspectFilterIds ?? null, /* @ts-ignore */
|
|
30353
|
+
...(ngDevMode ? [{ debugName: "inspectFilterIds" }] : /* istanbul ignore next */ []));
|
|
30354
|
+
this.queryEntries = computed(() => queryDevtoolsEntries().filter((e) => e.kind === 'query'), /* @ts-ignore */
|
|
30355
|
+
...(ngDevMode ? [{ debugName: "queryEntries" }] : /* istanbul ignore next */ []));
|
|
30356
|
+
this.stackEntries = computed(() => queryDevtoolsEntries().filter((e) => e.kind === 'query-stack' || e.kind === 'paged-query-stack'), /* @ts-ignore */
|
|
30357
|
+
...(ngDevMode ? [{ debugName: "stackEntries" }] : /* istanbul ignore next */ []));
|
|
30358
|
+
this.sequenceEntries = computed(() => queryDevtoolsEntries().filter((e) => e.kind === 'query-sequence'), /* @ts-ignore */
|
|
30359
|
+
...(ngDevMode ? [{ debugName: "sequenceEntries" }] : /* istanbul ignore next */ []));
|
|
30360
|
+
this.authEntries = computed(() => queryDevtoolsEntries().filter((e) => e.kind === 'auth-provider'), /* @ts-ignore */
|
|
30361
|
+
...(ngDevMode ? [{ debugName: "authEntries" }] : /* istanbul ignore next */ []));
|
|
30362
|
+
this.wsEntries = computed(() => queryDevtoolsEntries().filter((e) => e.kind === 'ws-client'), /* @ts-ignore */
|
|
30363
|
+
...(ngDevMode ? [{ debugName: "wsEntries" }] : /* istanbul ignore next */ []));
|
|
30364
|
+
/** Unique client names present across queries and auth providers, for the Queries-tab picker. */
|
|
30365
|
+
this.clientNames = computed(() => {
|
|
30366
|
+
const names = new Set();
|
|
30367
|
+
for (const entry of queryDevtoolsEntries()) {
|
|
30368
|
+
if (entry.meta.clientName)
|
|
30369
|
+
names.add(entry.meta.clientName);
|
|
30370
|
+
}
|
|
30371
|
+
return Array.from(names).sort();
|
|
30372
|
+
}, /* @ts-ignore */
|
|
30373
|
+
...(ngDevMode ? [{ debugName: "clientNames" }] : /* istanbul ignore next */ []));
|
|
30374
|
+
/** Unique repositories (with their client name + base URL) used by the Cache and Events tabs. */
|
|
30375
|
+
this.repositories = computed(() => {
|
|
30376
|
+
const map = new Map();
|
|
30377
|
+
for (const entry of queryDevtoolsEntries()) {
|
|
30378
|
+
const repo = entry.meta.repository;
|
|
30379
|
+
if (repo && !map.has(repo)) {
|
|
30380
|
+
map.set(repo, { name: entry.meta.clientName ?? 'unknown', baseUrl: entry.meta.clientBaseUrl ?? '' });
|
|
30381
|
+
}
|
|
30382
|
+
}
|
|
30383
|
+
return Array.from(map, ([repository, info]) => ({ repository, name: info.name, baseUrl: info.baseUrl }));
|
|
30384
|
+
}, /* @ts-ignore */
|
|
30385
|
+
...(ngDevMode ? [{ debugName: "repositories" }] : /* istanbul ignore next */ []));
|
|
30386
|
+
this.filteredQueries = computed(() => {
|
|
30387
|
+
const entries = this.queryEntries();
|
|
30388
|
+
const inspectIds = this.inspectFilterIds();
|
|
30389
|
+
let filtered;
|
|
30390
|
+
if (inspectIds) {
|
|
30391
|
+
filtered = entries.filter((e) => inspectIds.includes(e.id));
|
|
30392
|
+
}
|
|
30393
|
+
else {
|
|
30394
|
+
const client = this.selectedClientName();
|
|
30395
|
+
filtered = client ? entries.filter((e) => e.meta.clientName === client) : entries;
|
|
30396
|
+
}
|
|
30397
|
+
return filtered.map((entry) => ({ entry, query: entry.handle }));
|
|
30398
|
+
}, /* @ts-ignore */
|
|
30399
|
+
...(ngDevMode ? [{ debugName: "filteredQueries" }] : /* istanbul ignore next */ []));
|
|
30400
|
+
this.selectedQuery = computed(() => this.findQuery(this.selectedQueryId()), /* @ts-ignore */
|
|
30401
|
+
...(ngDevMode ? [{ debugName: "selectedQuery" }] : /* istanbul ignore next */ []));
|
|
30402
|
+
this.stackSelectedQuery = computed(() => this.findQuery(this.stackSelectedQueryId()), /* @ts-ignore */
|
|
30403
|
+
...(ngDevMode ? [{ debugName: "stackSelectedQuery" }] : /* istanbul ignore next */ []));
|
|
30404
|
+
this.sequenceSelectedQuery = computed(() => this.findQuery(this.sequenceSelectedQueryId()), /* @ts-ignore */
|
|
30405
|
+
...(ngDevMode ? [{ debugName: "sequenceSelectedQuery" }] : /* istanbul ignore next */ []));
|
|
30406
|
+
this.cacheView = computed(() => this.repositories().map(({ repository, name, baseUrl }) => {
|
|
30407
|
+
// Read the version signal so this recomputes on every cache mutation.
|
|
30408
|
+
repository.subtle.cacheVersion();
|
|
30409
|
+
return { name, baseUrl, repository, entries: repository.subtle.cacheEntries() };
|
|
30410
|
+
}), /* @ts-ignore */
|
|
30411
|
+
...(ngDevMode ? [{ debugName: "cacheView" }] : /* istanbul ignore next */ []));
|
|
30412
|
+
/** Map of a component's host element to the query entries it created (for the inspect tool). */
|
|
30413
|
+
this.elementQueryMap = computed(() => {
|
|
30414
|
+
const map = new Map();
|
|
30415
|
+
for (const entry of this.queryEntries()) {
|
|
30416
|
+
const el = entry.meta.element;
|
|
30417
|
+
if (!el)
|
|
30418
|
+
continue;
|
|
30419
|
+
const list = map.get(el);
|
|
30420
|
+
if (list)
|
|
30421
|
+
list.push(entry);
|
|
30422
|
+
else
|
|
30423
|
+
map.set(el, [entry]);
|
|
30424
|
+
}
|
|
30425
|
+
return map;
|
|
30426
|
+
}, /* @ts-ignore */
|
|
30427
|
+
...(ngDevMode ? [{ debugName: "elementQueryMap" }] : /* istanbul ignore next */ []));
|
|
30428
|
+
// Assigned here (not as an arrow property) so `this` is bound for the value-explorer callback.
|
|
30429
|
+
this.toggleJsonPath = (path, expand) => {
|
|
30430
|
+
const expanded = new Set(this.jsonExpandedPaths());
|
|
30431
|
+
const collapsed = new Set(this.jsonCollapsedPaths());
|
|
30432
|
+
if (expand) {
|
|
30433
|
+
expanded.add(path);
|
|
30434
|
+
collapsed.delete(path);
|
|
30435
|
+
}
|
|
30436
|
+
else {
|
|
30437
|
+
collapsed.add(path);
|
|
30438
|
+
expanded.delete(path);
|
|
30439
|
+
}
|
|
30440
|
+
this.jsonExpandedPaths.set(expanded);
|
|
30441
|
+
this.jsonCollapsedPaths.set(collapsed);
|
|
30442
|
+
};
|
|
30443
|
+
// Merge every live repository's event stream into the rolling log, re-subscribing as the set of
|
|
30444
|
+
// repositories changes. Composed with RxJS (not a subscribe-in-effect) per the styleguide.
|
|
30445
|
+
toObservable(this.repositories)
|
|
30446
|
+
.pipe(switchMap((repos) => merge(...repos.map(({ repository, name, baseUrl }) => repository.events$.pipe(map((event) => ({ event, client: baseUrl || name })))))), tap(({ event, client }) => this.pushEvent(event, client)), takeUntilDestroyed())
|
|
30447
|
+
.subscribe();
|
|
30448
|
+
effect(() => {
|
|
30449
|
+
const state = {
|
|
30450
|
+
open: this.open(),
|
|
30451
|
+
height: this.panelHeight(),
|
|
30452
|
+
activeTab: this.activeTab(),
|
|
30453
|
+
selectedClientName: this.selectedClientName(),
|
|
30454
|
+
selectedQueryId: this.selectedQueryId(),
|
|
30455
|
+
inspectFilterIds: this.inspectFilterIds(),
|
|
30456
|
+
jsonSearch: this.jsonSearch(),
|
|
30457
|
+
expandedSteps: [...this.expandedSteps()],
|
|
30458
|
+
jsonExpanded: [...this.jsonExpandedPaths()],
|
|
30459
|
+
jsonCollapsed: [...this.jsonCollapsedPaths()],
|
|
30460
|
+
};
|
|
30461
|
+
try {
|
|
30462
|
+
sessionStorage.setItem(STORAGE_KEY, JSON.stringify(state));
|
|
30463
|
+
}
|
|
30464
|
+
catch {
|
|
30465
|
+
// ignore (private mode / disabled storage)
|
|
30466
|
+
}
|
|
30467
|
+
});
|
|
30468
|
+
// Close any open JIT editor on any selection / tab change, and reset the value-explorer search
|
|
30469
|
+
// when the *selected query* actually changes (but not on the initial restore, so a persisted
|
|
30470
|
+
// search survives a reload).
|
|
30471
|
+
this.lastSelectionKey = this.selectionKey();
|
|
30472
|
+
effect(() => {
|
|
30473
|
+
const key = this.selectionKey();
|
|
30474
|
+
this.activeTab();
|
|
30475
|
+
this.editorMode.set('none');
|
|
30476
|
+
this.editError.set(null);
|
|
30477
|
+
this.copiedReport.set(false);
|
|
30478
|
+
if (key !== this.lastSelectionKey) {
|
|
30479
|
+
this.lastSelectionKey = key;
|
|
30480
|
+
this.jsonSearch.set('');
|
|
30481
|
+
}
|
|
30482
|
+
});
|
|
30483
|
+
const doc = this.document;
|
|
30484
|
+
// Global toggle shortcut: Ctrl/Cmd + Alt + Q ("Q" for Query) — uncommon, no browser/OS conflict.
|
|
30485
|
+
fromEvent(doc, 'keydown')
|
|
30486
|
+
.pipe(filter((e) => (e.ctrlKey || e.metaKey) && e.altKey && e.key.toLowerCase() === 'q'), tap((e) => {
|
|
30487
|
+
e.preventDefault();
|
|
30488
|
+
this.open.update((v) => !v);
|
|
30489
|
+
}), takeUntilDestroyed())
|
|
30490
|
+
.subscribe();
|
|
30491
|
+
// Drag-to-resize: while a resize is in progress, track pointer movement on the document.
|
|
30492
|
+
toObservable(this.resizing)
|
|
30493
|
+
.pipe(switchMap((active) => active
|
|
30494
|
+
? merge(fromEvent(doc, 'pointermove').pipe(tap((e) => this.applyResize(e))), fromEvent(doc, 'pointerup').pipe(tap(() => this.resizing.set(false))))
|
|
30495
|
+
: EMPTY), takeUntilDestroyed())
|
|
30496
|
+
.subscribe();
|
|
30497
|
+
// Inspect mode: while active, listen on the document to map the hovered element to a query.
|
|
30498
|
+
const capture = { capture: true };
|
|
30499
|
+
toObservable(this.inspectActive)
|
|
30500
|
+
.pipe(tap((active) => {
|
|
30501
|
+
if (!active)
|
|
30502
|
+
this.inspectHover.set(null);
|
|
30503
|
+
}), switchMap((active) => active
|
|
30504
|
+
? merge(fromEvent(doc, 'mousemove', capture).pipe(tap((e) => this.updateInspectHover(e))), fromEvent(doc, 'click', capture).pipe(tap((e) => this.selectInspectedQuery(e))), fromEvent(doc, 'keydown', capture).pipe(tap((e) => {
|
|
30505
|
+
if (e.key === 'Escape')
|
|
30506
|
+
this.inspectActive.set(false);
|
|
30507
|
+
})))
|
|
30508
|
+
: EMPTY), takeUntilDestroyed())
|
|
30509
|
+
.subscribe();
|
|
30510
|
+
}
|
|
30511
|
+
toggleOpen() {
|
|
30512
|
+
this.open.update((v) => !v);
|
|
30513
|
+
}
|
|
30514
|
+
clearEvents() {
|
|
30515
|
+
this.eventLog.set([]);
|
|
30516
|
+
}
|
|
30517
|
+
selectClient(name) {
|
|
30518
|
+
this.selectedClientName.set(name);
|
|
30519
|
+
this.inspectFilterIds.set(null);
|
|
30520
|
+
}
|
|
30521
|
+
clearInspectFilter() {
|
|
30522
|
+
this.inspectFilterIds.set(null);
|
|
30523
|
+
}
|
|
30524
|
+
toggleInspect() {
|
|
30525
|
+
this.inspectActive.update((v) => !v);
|
|
30526
|
+
}
|
|
30527
|
+
startResize(event) {
|
|
30528
|
+
event.preventDefault();
|
|
30529
|
+
this.resizing.set(true);
|
|
30530
|
+
}
|
|
30531
|
+
inspectLabel(entries) {
|
|
30532
|
+
const first = entries[0];
|
|
30533
|
+
if (entries.length === 1 && first)
|
|
30534
|
+
return `${first.meta.method ?? ''} ${first.meta.route ?? ''}`.trim();
|
|
30535
|
+
return `${entries.length} queries`;
|
|
30536
|
+
}
|
|
30537
|
+
queryStatus(query) {
|
|
30538
|
+
const state = query.executionState();
|
|
30539
|
+
if (!state)
|
|
30540
|
+
return 'idle';
|
|
30541
|
+
if (state.type === 'loading')
|
|
30542
|
+
return 'loading';
|
|
30543
|
+
if (state.type === 'failure')
|
|
30544
|
+
return 'error';
|
|
30545
|
+
return 'success';
|
|
30546
|
+
}
|
|
30547
|
+
isStale(query) {
|
|
30548
|
+
try {
|
|
30549
|
+
return query.subtle.request()?.isStale() ?? false;
|
|
30550
|
+
}
|
|
30551
|
+
catch {
|
|
30552
|
+
return false;
|
|
30553
|
+
}
|
|
30554
|
+
}
|
|
30555
|
+
executeQuery(query, allowCache) {
|
|
30556
|
+
query.execute(allowCache ? { options: { allowCache: true } } : undefined);
|
|
30557
|
+
}
|
|
30558
|
+
resetQuery(query) {
|
|
30559
|
+
query.reset();
|
|
30560
|
+
}
|
|
30561
|
+
/**
|
|
30562
|
+
* Copies a shareable report (path, args, status, slimmed response) for handing to an API dev.
|
|
30563
|
+
* Writes both rich `text/html` (Slack applies formatting on paste — it does not parse markdown) and
|
|
30564
|
+
* a plain-text fallback.
|
|
30565
|
+
*/
|
|
30566
|
+
copyReport(entry, query) {
|
|
30567
|
+
const error = query.error();
|
|
30568
|
+
const httpStatus = error ? error.raw.status : this.responseStatus(query);
|
|
30569
|
+
const method = entry.meta.method ?? '';
|
|
30570
|
+
const route = entry.meta.route || '—';
|
|
30571
|
+
const client = entry.meta.clientBaseUrl ?? entry.meta.clientName ?? '';
|
|
30572
|
+
const statusLine = `status: ${this.queryStatus(query)}${httpStatus !== null ? ` (${httpStatus})` : ''} · ${this.formatTime(query.lastTimeExecutedAt())}`;
|
|
30573
|
+
const gqlDoc = entry.meta.gqlQuery ? this.gqlDocument(entry.meta.gqlQuery) : null;
|
|
30574
|
+
const args = query.args();
|
|
30575
|
+
const argsLabel = gqlDoc ? 'Variables' : 'Args';
|
|
30576
|
+
const argsJson = args !== null && args !== undefined ? JSON.stringify(args, null, 2) : null;
|
|
30577
|
+
const bodyLabel = error ? `Error (${error.raw.status})` : 'Response';
|
|
30578
|
+
const bodyContent = error
|
|
30579
|
+
? error.isList
|
|
30580
|
+
? error.errors.map((e) => e.message).join('\n')
|
|
30581
|
+
: error.error.message
|
|
30582
|
+
: JSON.stringify(slimForReport(query.response()), null, 2);
|
|
30583
|
+
const textParts = [`${method} ${route}${client ? ` — ${client}` : ''}`, statusLine];
|
|
30584
|
+
if (gqlDoc)
|
|
30585
|
+
textParts.push('', 'GraphQL document', gqlDoc);
|
|
30586
|
+
if (argsJson)
|
|
30587
|
+
textParts.push('', argsLabel, argsJson);
|
|
30588
|
+
textParts.push('', bodyLabel, bodyContent);
|
|
30589
|
+
const text = textParts.join('\n');
|
|
30590
|
+
const esc = (s) => s.replace(/&/g, '&').replace(/</g, '<').replace(/>/g, '>');
|
|
30591
|
+
const htmlParts = [
|
|
30592
|
+
`<b>${esc(method)}</b> <code>${esc(route)}</code>${client ? ` — <code>${esc(client)}</code>` : ''}`,
|
|
30593
|
+
esc(statusLine),
|
|
30594
|
+
];
|
|
30595
|
+
if (gqlDoc)
|
|
30596
|
+
htmlParts.push('<b>GraphQL document</b>', `<pre><code>${esc(gqlDoc)}</code></pre>`);
|
|
30597
|
+
if (argsJson)
|
|
30598
|
+
htmlParts.push(`<b>${argsLabel}</b>`, `<pre><code>${esc(argsJson)}</code></pre>`);
|
|
30599
|
+
htmlParts.push(`<b>${esc(bodyLabel)}</b>`, `<pre><code>${esc(bodyContent)}</code></pre>`);
|
|
30600
|
+
const html = htmlParts.join('<br>');
|
|
30601
|
+
this.writeToClipboard(html, text);
|
|
30602
|
+
}
|
|
30603
|
+
// --- JIT editing ---
|
|
30604
|
+
openResponseEditor(query) {
|
|
30605
|
+
this.responseDraft.set(JSON.stringify(query.response() ?? null, null, 2));
|
|
30606
|
+
this.editError.set(null);
|
|
30607
|
+
this.editorMode.set('response');
|
|
30608
|
+
}
|
|
30609
|
+
openArgsEditor(query) {
|
|
30610
|
+
this.argsDraft.set(JSON.stringify(query.args() ?? {}, null, 2));
|
|
30611
|
+
this.editError.set(null);
|
|
30612
|
+
this.editorMode.set('args');
|
|
30613
|
+
}
|
|
30614
|
+
applyResponse(query) {
|
|
30615
|
+
try {
|
|
30616
|
+
query.subtle.setResponse(JSON.parse(this.responseDraft()));
|
|
30617
|
+
this.editorMode.set('none');
|
|
30618
|
+
this.editError.set(null);
|
|
30619
|
+
}
|
|
30620
|
+
catch {
|
|
30621
|
+
this.editError.set('Invalid JSON');
|
|
30622
|
+
}
|
|
30623
|
+
}
|
|
30624
|
+
applyArgs(query) {
|
|
30625
|
+
try {
|
|
30626
|
+
query.execute({ args: JSON.parse(this.argsDraft()) });
|
|
30627
|
+
this.editorMode.set('none');
|
|
30628
|
+
this.editError.set(null);
|
|
30629
|
+
}
|
|
30630
|
+
catch {
|
|
30631
|
+
this.editError.set('Invalid JSON');
|
|
30632
|
+
}
|
|
30633
|
+
}
|
|
30634
|
+
cancelEditor() {
|
|
30635
|
+
this.editorMode.set('none');
|
|
30636
|
+
this.editError.set(null);
|
|
30637
|
+
}
|
|
30638
|
+
// --- Force states ---
|
|
30639
|
+
forceLoading(query) {
|
|
30640
|
+
// `executionState` prioritises loading > error > response, so clear the others to switch cleanly.
|
|
30641
|
+
query.subtle.setError(null);
|
|
30642
|
+
query.subtle.setLoading({ executeTime: Date.now(), progress: null });
|
|
30643
|
+
}
|
|
30644
|
+
forceError(query) {
|
|
30645
|
+
query.subtle.setLoading(null);
|
|
30646
|
+
// A real failed execution also drops the response, so mirror that for consumers bound to it.
|
|
30647
|
+
query.subtle.setResponse(null);
|
|
30648
|
+
query.subtle.setError(createQueryErrorResponse(new HttpErrorResponse({
|
|
30649
|
+
status: 500,
|
|
30650
|
+
statusText: 'Forced',
|
|
30651
|
+
error: { message: 'Forced error (devtools)' },
|
|
30652
|
+
})));
|
|
30653
|
+
}
|
|
30654
|
+
forceEmpty(query) {
|
|
30655
|
+
query.subtle.setLoading(null);
|
|
30656
|
+
query.subtle.setError(null);
|
|
30657
|
+
query.subtle.setResponse(null);
|
|
30658
|
+
}
|
|
30659
|
+
clearForced(query) {
|
|
30660
|
+
query.subtle.setLoading(null);
|
|
30661
|
+
query.subtle.setError(null);
|
|
30662
|
+
}
|
|
30663
|
+
// --- Cache actions ---
|
|
30664
|
+
refetchCacheEntry(entry) {
|
|
30665
|
+
entry.request.execute();
|
|
30666
|
+
}
|
|
30667
|
+
evictCacheEntry(repository, key) {
|
|
30668
|
+
repository.subtle.evict(key);
|
|
30669
|
+
}
|
|
30670
|
+
cacheFreshness(entry) {
|
|
30671
|
+
this.clock();
|
|
30672
|
+
if (entry.request.loading())
|
|
30673
|
+
return 'refreshing…';
|
|
30674
|
+
const expiresAt = entry.request.expiresAt();
|
|
30675
|
+
if (expiresAt === null)
|
|
30676
|
+
return 'uncacheable';
|
|
30677
|
+
const ms = expiresAt - Date.now();
|
|
30678
|
+
return ms <= 0 ? 'stale' : `${Math.ceil(ms / 1000)}s`;
|
|
30679
|
+
}
|
|
30680
|
+
/** The path + query of a request URL (origin stripped), for readable cache/event identifiers. */
|
|
30681
|
+
requestPath(url) {
|
|
30682
|
+
try {
|
|
30683
|
+
const parsed = new URL(url);
|
|
30684
|
+
return parsed.pathname + parsed.search;
|
|
30685
|
+
}
|
|
30686
|
+
catch {
|
|
30687
|
+
return url;
|
|
30688
|
+
}
|
|
30689
|
+
}
|
|
30690
|
+
// --- Typed template accessors (entry.handle is `unknown`) ---
|
|
30691
|
+
asStack(entry) {
|
|
30692
|
+
return entry.handle;
|
|
30693
|
+
}
|
|
30694
|
+
asPagedStack(entry) {
|
|
30695
|
+
return entry.handle;
|
|
30696
|
+
}
|
|
30697
|
+
asSequence(entry) {
|
|
30698
|
+
return entry.handle.current;
|
|
30699
|
+
}
|
|
30700
|
+
asAuth(entry) {
|
|
30701
|
+
return entry.handle;
|
|
30702
|
+
}
|
|
30703
|
+
asWs(entry) {
|
|
30704
|
+
return entry.handle;
|
|
30705
|
+
}
|
|
30706
|
+
/** Derives the per-step status of a sequence step from its live progress signals. */
|
|
30707
|
+
sequenceStepStatus(sequence, index) {
|
|
30708
|
+
const failedAt = sequence.failedAt();
|
|
30709
|
+
if (failedAt !== null && index === failedAt)
|
|
30710
|
+
return 'error';
|
|
30711
|
+
const current = sequence.currentStep();
|
|
30712
|
+
const running = sequence.running();
|
|
30713
|
+
if (index < current - 1)
|
|
30714
|
+
return 'success';
|
|
30715
|
+
if (index === current - 1 && running)
|
|
30716
|
+
return 'running';
|
|
30717
|
+
if (sequence.status() === 'success')
|
|
30718
|
+
return 'success';
|
|
30719
|
+
return 'idle';
|
|
30720
|
+
}
|
|
30721
|
+
authTokenPayload(auth) {
|
|
30722
|
+
return decodeJwtPayload(auth.accessToken());
|
|
30723
|
+
}
|
|
30724
|
+
queriesForStack(stack) {
|
|
30725
|
+
const inner = stack.queries();
|
|
30726
|
+
const queryEntries = this.queryEntries();
|
|
30727
|
+
return inner.map((query) => {
|
|
30728
|
+
const entry = queryEntries.find((e) => e.handle === query);
|
|
30729
|
+
return {
|
|
30730
|
+
id: entry?.id ?? '',
|
|
30731
|
+
query: query,
|
|
30732
|
+
method: entry?.meta.method ?? '',
|
|
30733
|
+
route: entry?.meta.route ?? '',
|
|
30734
|
+
clientName: entry?.meta.clientName ?? '',
|
|
30735
|
+
clientBaseUrl: entry?.meta.clientBaseUrl ?? '',
|
|
30736
|
+
};
|
|
30737
|
+
});
|
|
30738
|
+
}
|
|
30739
|
+
/** Identifying info for a stack, derived from its (uniform) inner queries. */
|
|
30740
|
+
stackIdentity(stack) {
|
|
30741
|
+
const first = this.queriesForStack(stack)[0];
|
|
30742
|
+
return { method: first?.method ?? '', route: first?.route ?? '', baseUrl: first?.clientBaseUrl ?? '' };
|
|
30743
|
+
}
|
|
30744
|
+
authFeatures(auth) {
|
|
30745
|
+
return Object.keys(auth.features ?? {});
|
|
30746
|
+
}
|
|
30747
|
+
authQueryKeys(auth) {
|
|
30748
|
+
return Object.keys(auth.queries ?? {});
|
|
30749
|
+
}
|
|
30750
|
+
/** Countdown to the access-token's `exp` (the point a refresh becomes due), or `null` if unknown. */
|
|
30751
|
+
authTokenExpiry(auth) {
|
|
30752
|
+
this.clock();
|
|
30753
|
+
const payload = decodeJwtPayload(auth.accessToken());
|
|
30754
|
+
const exp = typeof payload?.['exp'] === 'number' ? payload['exp'] : null;
|
|
30755
|
+
if (exp === null)
|
|
30756
|
+
return null;
|
|
30757
|
+
const seconds = Math.round((exp * 1000 - Date.now()) / 1000);
|
|
30758
|
+
if (seconds <= 0)
|
|
30759
|
+
return 'expired';
|
|
30760
|
+
if (seconds < 120)
|
|
30761
|
+
return `${seconds}s`;
|
|
30762
|
+
if (seconds > 86400)
|
|
30763
|
+
return `${Math.floor(seconds / 86400)}d`;
|
|
30764
|
+
return `${Math.floor(seconds / 60)}m ${seconds % 60}s`;
|
|
30765
|
+
}
|
|
30766
|
+
queriesForSequence(sequence) {
|
|
30767
|
+
const queryEntries = this.queryEntries();
|
|
30768
|
+
return sequence.queries.map((query) => {
|
|
30769
|
+
const entry = queryEntries.find((e) => e.handle === query);
|
|
30770
|
+
return {
|
|
30771
|
+
id: entry?.id ?? '',
|
|
30772
|
+
query: query,
|
|
30773
|
+
method: entry?.meta.method ?? '',
|
|
30774
|
+
route: entry?.meta.route ?? '',
|
|
30775
|
+
};
|
|
30776
|
+
});
|
|
30777
|
+
}
|
|
30778
|
+
/** The snapshot of a sequence step, once it has run (holds the args in and the response/error out). */
|
|
30779
|
+
stepSnapshot(sequence, index) {
|
|
30780
|
+
return sequence.snapshots()[index] ?? null;
|
|
30781
|
+
}
|
|
30782
|
+
isStepExpanded(entryId, index) {
|
|
30783
|
+
return this.expandedSteps().has(this.stepKey(entryId, index));
|
|
30784
|
+
}
|
|
30785
|
+
toggleStep(entryId, index) {
|
|
30786
|
+
const key = this.stepKey(entryId, index);
|
|
30787
|
+
const next = new Set(this.expandedSteps());
|
|
30788
|
+
if (next.has(key)) {
|
|
30789
|
+
next.delete(key);
|
|
30790
|
+
}
|
|
30791
|
+
else {
|
|
30792
|
+
next.add(key);
|
|
30793
|
+
}
|
|
30794
|
+
this.expandedSteps.set(next);
|
|
30795
|
+
}
|
|
30796
|
+
/** Dedents a GraphQL document (template-literal indentation) for readable display. */
|
|
30797
|
+
gqlDocument(doc) {
|
|
30798
|
+
const lines = doc.replace(/\t/g, ' ').split('\n');
|
|
30799
|
+
while (lines.length && !lines[0]?.trim())
|
|
30800
|
+
lines.shift();
|
|
30801
|
+
while (lines.length && !lines[lines.length - 1]?.trim())
|
|
30802
|
+
lines.pop();
|
|
30803
|
+
const indents = lines.filter((l) => l.trim()).map((l) => l.match(/^ */)?.[0].length ?? 0);
|
|
30804
|
+
const min = indents.length ? Math.min(...indents) : 0;
|
|
30805
|
+
return lines.map((l) => l.slice(min)).join('\n');
|
|
30806
|
+
}
|
|
30807
|
+
featureLabel(type) {
|
|
30808
|
+
return type
|
|
30809
|
+
.replace(/^WITH_/, '')
|
|
30810
|
+
.replace(/_/g, ' ')
|
|
30811
|
+
.toLowerCase();
|
|
30812
|
+
}
|
|
30813
|
+
formatTime(timestamp) {
|
|
30814
|
+
if (!timestamp)
|
|
30815
|
+
return '—';
|
|
30816
|
+
return new Date(timestamp).toLocaleTimeString(undefined, { hour12: false });
|
|
30817
|
+
}
|
|
30818
|
+
stepKey(entryId, index) {
|
|
30819
|
+
return `${entryId}:${index}`;
|
|
30820
|
+
}
|
|
30821
|
+
applyResize(event) {
|
|
30822
|
+
// The panel is docked to the bottom, so its height is the distance from the pointer to the viewport bottom.
|
|
30823
|
+
const viewport = this.document.documentElement.clientHeight;
|
|
30824
|
+
const next = viewport - event.clientY;
|
|
30825
|
+
const max = Math.round(viewport * 0.9);
|
|
30826
|
+
this.panelHeight.set(Math.min(Math.max(next, MIN_HEIGHT), max));
|
|
30827
|
+
}
|
|
30828
|
+
updateInspectHover(event) {
|
|
30829
|
+
const host = this.hostEl.nativeElement;
|
|
30830
|
+
const map = this.elementQueryMap();
|
|
30831
|
+
let node = event.target;
|
|
30832
|
+
// Ignore the devtools UI itself.
|
|
30833
|
+
if (node && host.contains(node)) {
|
|
30834
|
+
this.inspectHover.set(null);
|
|
30835
|
+
return;
|
|
30836
|
+
}
|
|
30837
|
+
while (node) {
|
|
30838
|
+
const entries = map.get(node);
|
|
30839
|
+
if (entries) {
|
|
30840
|
+
this.inspectHover.set({ rect: node.getBoundingClientRect(), entries });
|
|
30841
|
+
return;
|
|
30842
|
+
}
|
|
30843
|
+
node = node.parentElement;
|
|
30844
|
+
}
|
|
30845
|
+
this.inspectHover.set(null);
|
|
30846
|
+
}
|
|
30847
|
+
selectInspectedQuery(event) {
|
|
30848
|
+
const hover = this.inspectHover();
|
|
30849
|
+
const first = hover?.entries[0];
|
|
30850
|
+
if (!hover || !first)
|
|
30851
|
+
return;
|
|
30852
|
+
event.preventDefault();
|
|
30853
|
+
event.stopPropagation();
|
|
30854
|
+
const ids = hover.entries.map((e) => e.id);
|
|
30855
|
+
this.open.set(true);
|
|
30856
|
+
this.activeTab.set('queries');
|
|
30857
|
+
this.selectedClientName.set(null);
|
|
30858
|
+
this.inspectFilterIds.set(ids);
|
|
30859
|
+
// Auto-select when the element owns a single query, otherwise let the user pick from the filtered list.
|
|
30860
|
+
this.selectedQueryId.set(ids.length === 1 ? first.id : null);
|
|
30861
|
+
this.inspectActive.set(false);
|
|
30862
|
+
}
|
|
30863
|
+
selectionKey() {
|
|
30864
|
+
return `${this.selectedQueryId()}|${this.stackSelectedQueryId()}|${this.sequenceSelectedQueryId()}`;
|
|
30865
|
+
}
|
|
30866
|
+
writeToClipboard(html, text) {
|
|
30867
|
+
const clipboard = navigator.clipboard;
|
|
30868
|
+
if (!clipboard)
|
|
30869
|
+
return;
|
|
30870
|
+
// Prefer rich HTML (Slack keeps the formatting on paste); fall back to plain text.
|
|
30871
|
+
if ('write' in clipboard && typeof ClipboardItem !== 'undefined') {
|
|
30872
|
+
const item = new ClipboardItem({
|
|
30873
|
+
'text/html': new Blob([html], { type: 'text/html' }),
|
|
30874
|
+
'text/plain': new Blob([text], { type: 'text/plain' }),
|
|
30875
|
+
});
|
|
30876
|
+
clipboard
|
|
30877
|
+
.write([item])
|
|
30878
|
+
.then(() => this.copiedReport.set(true))
|
|
30879
|
+
.catch(() => clipboard
|
|
30880
|
+
.writeText(text)
|
|
30881
|
+
.then(() => this.copiedReport.set(true))
|
|
30882
|
+
.catch(() => undefined));
|
|
30883
|
+
return;
|
|
30884
|
+
}
|
|
30885
|
+
clipboard
|
|
30886
|
+
.writeText(text)
|
|
30887
|
+
.then(() => this.copiedReport.set(true))
|
|
30888
|
+
.catch(() => undefined);
|
|
30889
|
+
}
|
|
30890
|
+
responseStatus(query) {
|
|
30891
|
+
const event = query.latestHttpEvent();
|
|
30892
|
+
return typeof event?.status === 'number' ? event.status : null;
|
|
30893
|
+
}
|
|
30894
|
+
findQuery(id) {
|
|
30895
|
+
if (!id)
|
|
30896
|
+
return null;
|
|
30897
|
+
const entry = this.queryEntries().find((e) => e.id === id);
|
|
30898
|
+
return entry ? { entry, query: entry.handle } : null;
|
|
30899
|
+
}
|
|
30900
|
+
pushEvent(event, client) {
|
|
30901
|
+
const item = {
|
|
30902
|
+
id: this.eventIdCounter++,
|
|
30903
|
+
timestamp: Date.now(),
|
|
30904
|
+
client,
|
|
30905
|
+
type: event.type,
|
|
30906
|
+
method: event.request.method,
|
|
30907
|
+
url: event.request.url,
|
|
30908
|
+
isSecure: event.isSecure,
|
|
30909
|
+
status: event.type === 'request-error' ? event.error.status : null,
|
|
30910
|
+
};
|
|
30911
|
+
this.eventLog.update((log) => [item, ...log].slice(0, MAX_EVENTS));
|
|
30912
|
+
}
|
|
30913
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: QueryDevtoolsComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
30914
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.7", type: QueryDevtoolsComponent, isStandalone: true, selector: "et-query-devtools", host: { classAttribute: "et-query-devtools-host" }, ngImport: i0, template: "@if (open()) {\n <section\n [class.et-query-devtools-panel--resizing]=\"resizing()\"\n [style.height.px]=\"panelHeight()\"\n class=\"et-query-devtools-panel\"\n >\n <div\n (pointerdown)=\"startResize($event)\"\n class=\"et-query-devtools-resize\"\n title=\"Drag to resize\"\n aria-hidden=\"true\"\n ></div>\n <header class=\"et-query-devtools-header\">\n <nav class=\"et-query-devtools-tabs\" role=\"tablist\">\n @for (tab of tabs; track tab.id) {\n <button\n [class.et-query-devtools-tab--active]=\"activeTab() === tab.id\"\n [attr.aria-selected]=\"activeTab() === tab.id\"\n (click)=\"activeTab.set(tab.id)\"\n class=\"et-query-devtools-tab\"\n type=\"button\"\n role=\"tab\"\n >\n {{ tab.label }}\n </button>\n }\n </nav>\n\n <div class=\"et-query-devtools-header-actions\">\n <button\n [class.et-query-devtools-inspect-btn--active]=\"inspectActive()\"\n (click)=\"toggleInspect()\"\n class=\"et-query-devtools-inspect-btn\"\n type=\"button\"\n title=\"Inspect: hover the UI to find its query\"\n >\n \u2316 Inspect\n </button>\n <button (click)=\"toggleOpen()\" class=\"et-query-devtools-close\" type=\"button\" title=\"Close devtools\">\u2715</button>\n </div>\n </header>\n\n <div class=\"et-query-devtools-body\">\n @switch (activeTab()) {\n <!-- QUERIES -->\n @case ('queries') {\n <div class=\"et-query-devtools-master-detail\">\n <div class=\"et-query-devtools-list\">\n <div class=\"et-query-devtools-toolbar\">\n @if (inspectFilterIds(); as ids) {\n <span class=\"et-query-devtools-filter-chip\">\u2316 inspected \u00B7 {{ ids.length }}</span>\n <button (click)=\"clearInspectFilter()\" class=\"et-query-devtools-btn\" type=\"button\">Reset</button>\n } @else {\n <label class=\"et-query-devtools-field\">\n <span>Client</span>\n <select\n #clientSelect\n [value]=\"selectedClientName() ?? ''\"\n (change)=\"selectClient(clientSelect.value || null)\"\n class=\"et-query-devtools-select\"\n >\n <option value=\"\">All clients</option>\n @for (name of clientNames(); track name) {\n <option [value]=\"name\">{{ name }}</option>\n }\n </select>\n </label>\n }\n <span class=\"et-query-devtools-count\">{{ filteredQueries().length }}</span>\n </div>\n\n @for (item of filteredQueries(); track item.entry.id) {\n <button\n [class.et-query-devtools-row--active]=\"selectedQueryId() === item.entry.id\"\n (click)=\"selectedQueryId.set(item.entry.id)\"\n class=\"et-query-devtools-row\"\n type=\"button\"\n >\n <span\n [attr.data-status]=\"queryStatus(item.query)\"\n [title]=\"queryStatus(item.query)\"\n class=\"et-query-devtools-status\"\n ></span>\n <span class=\"et-query-devtools-method\">{{ item.entry.meta.method }}</span>\n <span class=\"et-query-devtools-route\">{{ item.entry.meta.route || '\u2014' }}</span>\n @if (isStale(item.query)) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">stale</span>\n }\n </button>\n } @empty {\n @if (inspectFilterIds()) {\n <p class=\"et-query-devtools-empty\">\n The inspected element's queries are no longer registered. Reset the filter.\n </p>\n } @else {\n <p class=\"et-query-devtools-empty\">No queries registered.</p>\n }\n }\n </div>\n\n <div class=\"et-query-devtools-detail\">\n @if (selectedQuery(); as sel) {\n <ng-container *ngTemplateOutlet=\"queryDetailTpl; context: { sel }\" />\n } @else {\n <p class=\"et-query-devtools-empty\">Select a query to inspect it.</p>\n }\n </div>\n </div>\n }\n\n <!-- STACKS -->\n @case ('stacks') {\n <div class=\"et-query-devtools-split\">\n <div class=\"et-query-devtools-scroll\">\n @for (entry of stackEntries(); track entry.id) {\n @if (entry.kind === 'paged-query-stack') {\n @let paged = asPagedStack(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-chip\">paged stack</span>\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">{{ paged.direction() }}</span>\n @if (paged.loading()) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--loading\">loading</span>\n }\n </div>\n\n @let pagedId = stackIdentity(paged);\n <div class=\"et-query-devtools-card-title\">\n <span class=\"et-query-devtools-method\">{{ pagedId.method }}</span>\n <span class=\"et-query-devtools-route\">{{ pagedId.route }}</span>\n </div>\n <div class=\"et-query-devtools-card-sub et-query-devtools-mono\">{{ pagedId.baseUrl }}</div>\n @if (entry.meta.featureTypes?.length) {\n <div class=\"et-query-devtools-chips\">\n @for (feature of entry.meta.featureTypes; track feature) {\n <span class=\"et-query-devtools-chip\">{{ featureLabel(feature) }}</span>\n }\n </div>\n }\n\n <dl class=\"et-query-devtools-meta\">\n <dt>Pages loaded</dt>\n <dd>{{ paged.queries().length }}</dd>\n <dt>Items</dt>\n <dd>{{ paged.items().length }}</dd>\n <dt>First page loaded</dt>\n <dd>{{ paged.isFirstPageLoaded() }}</dd>\n <dt>Last page loaded</dt>\n <dd>{{ paged.isLastPageLoaded() }}</dd>\n </dl>\n <ng-container *ngTemplateOutlet=\"innerQueriesTpl; context: { links: queriesForStack(paged) }\" />\n </div>\n } @else {\n @let stack = asStack(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-chip\">stack</span>\n @if (stack.anyLoading()) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--loading\">loading</span>\n }\n @if (stack.anyError()) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--error\">error</span>\n }\n </div>\n\n @let stackId = stackIdentity(stack);\n <div class=\"et-query-devtools-card-title\">\n <span class=\"et-query-devtools-method\">{{ stackId.method }}</span>\n <span class=\"et-query-devtools-route\">{{ stackId.route }}</span>\n </div>\n <div class=\"et-query-devtools-card-sub et-query-devtools-mono\">{{ stackId.baseUrl }}</div>\n @if (entry.meta.featureTypes?.length) {\n <div class=\"et-query-devtools-chips\">\n @for (feature of entry.meta.featureTypes; track feature) {\n <span class=\"et-query-devtools-chip\">{{ featureLabel(feature) }}</span>\n }\n </div>\n }\n\n <dl class=\"et-query-devtools-meta\">\n <dt>Queries</dt>\n <dd>{{ stack.queries().length }}</dd>\n <dt>Loading</dt>\n <dd>{{ stack.loadingProgress().loaded }} / {{ stack.loadingProgress().total }}</dd>\n <dt>Errors</dt>\n <dd>{{ stack.errors().length }}</dd>\n </dl>\n <ng-container *ngTemplateOutlet=\"innerQueriesTpl; context: { links: queriesForStack(stack) }\" />\n </div>\n }\n } @empty {\n <p class=\"et-query-devtools-empty\">No stacks registered.</p>\n }\n </div>\n\n @if (stackSelectedQuery(); as sel) {\n <aside class=\"et-query-devtools-drawer\">\n <div class=\"et-query-devtools-drawer-head\">\n <span>Query detail</span>\n <button\n (click)=\"stackSelectedQueryId.set(null)\"\n class=\"et-query-devtools-close\"\n type=\"button\"\n title=\"Close detail\"\n >\n \u2715\n </button>\n </div>\n <ng-container *ngTemplateOutlet=\"queryDetailTpl; context: { sel }\" />\n </aside>\n }\n </div>\n }\n\n <!-- SEQUENCES -->\n @case ('sequences') {\n <div class=\"et-query-devtools-split\">\n <div class=\"et-query-devtools-scroll\">\n @for (entry of sequenceEntries(); track entry.id) {\n @let sequence = asSequence(entry);\n @if (sequence) {\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-chip\">sequence</span>\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">{{ sequence.status() }}</span>\n <span class=\"et-query-devtools-count\"\n >step {{ sequence.currentStep() }} / {{ sequence.total }}</span\n >\n </div>\n\n <ol class=\"et-query-devtools-step-list\">\n @for (link of queriesForSequence(sequence); track $index; let i = $index) {\n <li [attr.data-status]=\"sequenceStepStatus(sequence, i)\" class=\"et-query-devtools-step-item\">\n <div class=\"et-query-devtools-step-head\">\n <button\n [class.et-query-devtools-inner-row--active]=\"sequenceSelectedQueryId() === link.id\"\n [disabled]=\"!link.id\"\n (click)=\"sequenceSelectedQueryId.set(link.id)\"\n class=\"et-query-devtools-inner-row\"\n type=\"button\"\n >\n <span\n [attr.data-status]=\"sequenceStepStatus(sequence, i)\"\n class=\"et-query-devtools-status\"\n ></span>\n <span class=\"et-query-devtools-method\">{{ i + 1 }}. {{ link.method }}</span>\n <span class=\"et-query-devtools-route\">{{ link.route || 'step ' + (i + 1) }}</span>\n </button>\n <button\n [attr.aria-expanded]=\"isStepExpanded(entry.id, i)\"\n (click)=\"toggleStep(entry.id, i)\"\n class=\"et-query-devtools-step-caret-btn\"\n type=\"button\"\n title=\"Toggle in / out\"\n >\n {{ isStepExpanded(entry.id, i) ? '\u25BE' : '\u25B8' }}\n </button>\n </div>\n\n @if (isStepExpanded(entry.id, i)) {\n @let snap = stepSnapshot(sequence, i);\n <div class=\"et-query-devtools-step-io\">\n <h5 class=\"et-query-devtools-section\">In \u00B7 args</h5>\n @if (sequence.stepArgs().length > i) {\n <et-query-devtools-json [value]=\"sequence.stepArgs()[i]\" />\n } @else {\n <p class=\"et-query-devtools-empty\">Not run yet.</p>\n }\n\n @if (snap?.error(); as error) {\n <h5 class=\"et-query-devtools-section\">Out \u00B7 error ({{ error.raw.status }})</h5>\n <et-query-devtools-json [value]=\"error.isList ? error.errors : error.error\" />\n } @else {\n <h5 class=\"et-query-devtools-section\">Out \u00B7 response</h5>\n @if (snap) {\n <et-query-devtools-json [value]=\"snap.response()\" />\n } @else {\n <p class=\"et-query-devtools-empty\">Not run yet.</p>\n }\n }\n </div>\n }\n </li>\n }\n </ol>\n </div>\n }\n } @empty {\n <p class=\"et-query-devtools-empty\">No sequences registered.</p>\n }\n </div>\n\n @if (sequenceSelectedQuery(); as sel) {\n <aside class=\"et-query-devtools-drawer\">\n <div class=\"et-query-devtools-drawer-head\">\n <span>Query detail</span>\n <button\n (click)=\"sequenceSelectedQueryId.set(null)\"\n class=\"et-query-devtools-close\"\n type=\"button\"\n title=\"Close detail\"\n >\n \u2715\n </button>\n </div>\n <ng-container *ngTemplateOutlet=\"queryDetailTpl; context: { sel }\" />\n </aside>\n }\n </div>\n }\n\n <!-- AUTH -->\n @case ('auth') {\n <div class=\"et-query-devtools-scroll\">\n @for (entry of authEntries(); track entry.id) {\n @let auth = asAuth(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <strong>{{ entry.meta.name || 'auth provider' }}</strong>\n <span\n [class.et-query-devtools-chip--success]=\"auth.isAuthenticated()\"\n [class.et-query-devtools-chip--muted]=\"!auth.isAuthenticated()\"\n class=\"et-query-devtools-chip\"\n >\n {{ auth.isAuthenticated() ? 'authenticated' : 'anonymous' }}\n </span>\n </div>\n <dl class=\"et-query-devtools-meta\">\n <dt>Base URL</dt>\n <dd class=\"et-query-devtools-mono\">{{ entry.meta.clientBaseUrl || entry.meta.clientName || '\u2014' }}</dd>\n <dt>Access token</dt>\n <dd>{{ auth.accessToken() ? 'present' : 'none' }}</dd>\n <dt>Refresh token</dt>\n <dd>{{ auth.refreshToken() ? 'present' : 'none' }}</dd>\n @if (authTokenExpiry(auth); as expiry) {\n <dt>Token expires in</dt>\n <dd>{{ expiry }}</dd>\n }\n @if (auth.executionState(); as state) {\n <dt>Execution state</dt>\n <dd>{{ state.type }} \u00B7 {{ state.state }}</dd>\n }\n @if (authQueryKeys(auth).length) {\n <dt>Queries</dt>\n <dd>\n <div class=\"et-query-devtools-chips\">\n @for (key of authQueryKeys(auth); track key) {\n <span class=\"et-query-devtools-chip\">{{ key }}</span>\n }\n </div>\n </dd>\n }\n @if (authFeatures(auth).length) {\n <dt>Features</dt>\n <dd>\n <div class=\"et-query-devtools-chips\">\n @for (feature of authFeatures(auth); track feature) {\n <span class=\"et-query-devtools-chip\">{{ feature }}</span>\n }\n </div>\n </dd>\n }\n </dl>\n\n @if (authTokenPayload(auth); as payload) {\n <h4 class=\"et-query-devtools-section\">Access token payload</h4>\n <et-query-devtools-json [value]=\"payload\" />\n }\n\n @if (auth.latestNonInternalQuery(); as latest) {\n <h4 class=\"et-query-devtools-section\">Latest auth query \u00B7 {{ latest.key }}</h4>\n <et-query-devtools-json [value]=\"latest.snapshot.response()\" />\n }\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No auth providers registered.</p>\n }\n </div>\n }\n\n <!-- SOCKETS -->\n @case ('ws') {\n <div class=\"et-query-devtools-scroll\">\n @for (entry of wsEntries(); track entry.id) {\n @let ws = asWs(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <strong>{{ entry.meta.name || 'socket' }}</strong>\n <span\n [class.et-query-devtools-chip--success]=\"ws.connected()\"\n [class.et-query-devtools-chip--muted]=\"!ws.connected()\"\n class=\"et-query-devtools-chip\"\n >\n {{ ws.connected() ? 'connected' : 'disconnected' }}\n </span>\n </div>\n <dl class=\"et-query-devtools-meta\">\n <dt>URL</dt>\n <dd class=\"et-query-devtools-mono\">{{ entry.meta.url }}</dd>\n <dt>Rooms</dt>\n <dd>\n @if (ws.rooms().length) {\n <div class=\"et-query-devtools-chips\">\n @for (room of ws.rooms(); track room) {\n <span class=\"et-query-devtools-chip\">{{ room }}</span>\n }\n </div>\n } @else {\n none\n }\n </dd>\n </dl>\n\n <h5 class=\"et-query-devtools-section\">Messages ({{ ws.messages().length }})</h5>\n @for (message of ws.messages(); track message.id) {\n <div class=\"et-query-devtools-ws-message\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-count\">{{ formatTime(message.timestamp) }}</span>\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">{{ message.room }}</span>\n <span class=\"et-query-devtools-method\">{{ message.event }}</span>\n </div>\n <et-query-devtools-json [value]=\"message.data\" />\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No messages received yet.</p>\n }\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No web socket clients registered.</p>\n }\n </div>\n }\n\n <!-- CACHE -->\n @case ('cache') {\n <div class=\"et-query-devtools-scroll\">\n @for (client of cacheView(); track client.name) {\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <strong class=\"et-query-devtools-mono\">{{ client.baseUrl || client.name }}</strong>\n <span class=\"et-query-devtools-count\">{{ client.entries.length }} entries</span>\n </div>\n <table class=\"et-query-devtools-table\">\n <thead>\n <tr>\n <th>Request</th>\n <th>Consumers</th>\n <th>Secure</th>\n <th>Freshness</th>\n <th>Actions</th>\n </tr>\n </thead>\n <tbody>\n @for (cacheEntry of client.entries; track cacheEntry.key) {\n <tr>\n <td [title]=\"cacheEntry.request.method + ' ' + cacheEntry.request.url\">\n <span class=\"et-query-devtools-method\">{{ cacheEntry.request.method }}</span>\n <span class=\"et-query-devtools-url\">{{ requestPath(cacheEntry.request.url) }}</span>\n </td>\n <td>{{ cacheEntry.consumerCount }}</td>\n <td>{{ cacheEntry.isSecure ? 'yes' : 'no' }}</td>\n <td>{{ cacheFreshness(cacheEntry) }}</td>\n <td class=\"et-query-devtools-cell-actions\">\n <button (click)=\"refetchCacheEntry(cacheEntry)\" class=\"et-query-devtools-btn\" type=\"button\">\n Refetch\n </button>\n <button\n (click)=\"evictCacheEntry(client.repository, cacheEntry.key)\"\n class=\"et-query-devtools-btn\"\n type=\"button\"\n >\n Evict\n </button>\n </td>\n </tr>\n } @empty {\n <tr>\n <td class=\"et-query-devtools-empty\" colspan=\"5\">Cache empty.</td>\n </tr>\n }\n </tbody>\n </table>\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No clients with a cache yet.</p>\n }\n </div>\n }\n\n <!-- EVENTS -->\n @case ('events') {\n <div class=\"et-query-devtools-scroll\">\n <div class=\"et-query-devtools-toolbar\">\n <span class=\"et-query-devtools-count\">{{ eventLog().length }} events</span>\n <button (click)=\"clearEvents()\" class=\"et-query-devtools-btn\" type=\"button\">Clear</button>\n </div>\n <table class=\"et-query-devtools-table\">\n <thead>\n <tr>\n <th>Time</th>\n <th>Base URL</th>\n <th>Type</th>\n <th>Request</th>\n </tr>\n </thead>\n <tbody>\n @for (event of eventLog(); track event.id) {\n <tr [attr.data-status]=\"event.type === 'request-error' ? 'error' : 'success'\">\n <td>{{ formatTime(event.timestamp) }}</td>\n <td class=\"et-query-devtools-mono\">{{ event.client }}</td>\n <td>\n {{ event.type === 'request-error' ? 'error ' + event.status : 'success' }}\n @if (event.isSecure) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">secure</span>\n }\n </td>\n <td [title]=\"event.method + ' ' + event.url\">\n <span class=\"et-query-devtools-method\">{{ event.method }}</span>\n <span class=\"et-query-devtools-url\">{{ requestPath(event.url) }}</span>\n </td>\n </tr>\n } @empty {\n <tr>\n <td class=\"et-query-devtools-empty\" colspan=\"4\">No events captured yet.</td>\n </tr>\n }\n </tbody>\n </table>\n </div>\n }\n }\n </div>\n\n <!-- Reusable inner-query list (stacks) \u2014 clicking opens the split-view drawer, not a tab switch. -->\n <ng-template #innerQueriesTpl let-links=\"links\">\n <div class=\"et-query-devtools-inner-queries\">\n @for (link of links; track $index) {\n <button\n [class.et-query-devtools-inner-row--active]=\"stackSelectedQueryId() === link.id\"\n [disabled]=\"!link.id\"\n (click)=\"stackSelectedQueryId.set(link.id)\"\n class=\"et-query-devtools-inner-row\"\n type=\"button\"\n >\n <span [attr.data-status]=\"queryStatus(link.query)\" class=\"et-query-devtools-status\"></span>\n <span class=\"et-query-devtools-method\">{{ link.method }}</span>\n <span class=\"et-query-devtools-route\">{{ link.route || link.query.id() || 'query ' + ($index + 1) }}</span>\n </button>\n }\n </div>\n </ng-template>\n\n <!-- Reusable query detail \u2014 used by the Queries tab and the stacks split-view drawer. -->\n <ng-template #queryDetailTpl let-sel=\"sel\">\n <div class=\"et-query-devtools-detail-head\">\n <span class=\"et-query-devtools-method\">{{ sel.entry.meta.method }}</span>\n <span class=\"et-query-devtools-route\">{{ sel.entry.meta.route || '\u2014' }}</span>\n </div>\n\n <div class=\"et-query-devtools-actions\">\n <span class=\"et-query-devtools-actions-label\">Run</span>\n <button (click)=\"executeQuery(sel.query, false)\" class=\"et-query-devtools-btn\" type=\"button\">Execute</button>\n <button (click)=\"executeQuery(sel.query, true)\" class=\"et-query-devtools-btn\" type=\"button\">Cached</button>\n <button (click)=\"resetQuery(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Reset</button>\n <button (click)=\"copyReport(sel.entry, sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">\n {{ copiedReport() ? '\u2713 Copied' : 'Copy report' }}\n </button>\n <span class=\"et-query-devtools-actions-label\">Edit</span>\n <button (click)=\"openResponseEditor(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Response</button>\n <button (click)=\"openArgsEditor(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Replay args</button>\n <span class=\"et-query-devtools-actions-label\">Force</span>\n <button (click)=\"forceLoading(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Loading</button>\n <button (click)=\"forceError(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Error</button>\n <button (click)=\"forceEmpty(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Empty</button>\n <button (click)=\"clearForced(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Clear</button>\n </div>\n\n @if (editorMode() !== 'none') {\n <div class=\"et-query-devtools-editor\">\n @if (editorMode() === 'response') {\n <h4 class=\"et-query-devtools-section\">Edit response \u2192 setResponse()</h4>\n <textarea\n #respArea\n [value]=\"responseDraft()\"\n (input)=\"responseDraft.set(respArea.value)\"\n class=\"et-query-devtools-textarea\"\n spellcheck=\"false\"\n ></textarea>\n <div class=\"et-query-devtools-actions\">\n <button (click)=\"applyResponse(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Apply</button>\n <button (click)=\"cancelEditor()\" class=\"et-query-devtools-btn\" type=\"button\">Cancel</button>\n </div>\n } @else {\n <h4 class=\"et-query-devtools-section\">Replay with edited args \u2192 execute()</h4>\n <textarea\n #argsArea\n [value]=\"argsDraft()\"\n (input)=\"argsDraft.set(argsArea.value)\"\n class=\"et-query-devtools-textarea\"\n spellcheck=\"false\"\n ></textarea>\n <div class=\"et-query-devtools-actions\">\n <button (click)=\"applyArgs(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Execute</button>\n <button (click)=\"cancelEditor()\" class=\"et-query-devtools-btn\" type=\"button\">Cancel</button>\n </div>\n }\n @if (editError(); as err) {\n <p class=\"et-query-devtools-editor-error\">{{ err }}</p>\n }\n </div>\n }\n\n <dl class=\"et-query-devtools-meta\">\n <dt>Base URL</dt>\n <dd class=\"et-query-devtools-mono\">{{ sel.entry.meta.clientBaseUrl || sel.entry.meta.clientName || '\u2014' }}</dd>\n <dt>Status</dt>\n <dd>{{ queryStatus(sel.query) }}</dd>\n <dt>Cache key</dt>\n <dd class=\"et-query-devtools-mono\">{{ sel.query.id() || '\u2014' }}</dd>\n <dt>Last executed</dt>\n <dd>{{ formatTime(sel.query.lastTimeExecutedAt()) }}</dd>\n <dt>Triggered by</dt>\n <dd>{{ sel.query.triggeredBy() || 'user' }}</dd>\n @if (sel.entry.meta.featureTypes?.length) {\n <dt>Features</dt>\n <dd>\n <div class=\"et-query-devtools-chips\">\n @for (feature of sel.entry.meta.featureTypes; track feature) {\n <span class=\"et-query-devtools-chip\">{{ featureLabel(feature) }}</span>\n }\n </div>\n </dd>\n }\n </dl>\n\n @if (sel.entry.meta.gqlQuery; as gqlQuery) {\n <h5 class=\"et-query-devtools-section\">GraphQL document</h5>\n <pre class=\"et-query-devtools-code\">{{ gqlDocument(gqlQuery) }}</pre>\n }\n\n <div class=\"et-query-devtools-section-row\">\n <h4 class=\"et-query-devtools-section\">Value explorer</h4>\n <input\n #jsonSearchInput\n [value]=\"jsonSearch()\"\n (input)=\"jsonSearch.set(jsonSearchInput.value)\"\n class=\"et-query-devtools-search\"\n type=\"search\"\n placeholder=\"filter keys / values\u2026\"\n />\n </div>\n\n <h5 class=\"et-query-devtools-section\">Args</h5>\n <et-query-devtools-json\n [value]=\"sel.query.args()\"\n [search]=\"jsonSearchTerm()\"\n [expandedPaths]=\"jsonExpandedPaths()\"\n [collapsedPaths]=\"jsonCollapsedPaths()\"\n [toggleFn]=\"toggleJsonPath\"\n path=\"args\"\n />\n\n @if (sel.query.error(); as error) {\n <h5 class=\"et-query-devtools-section\">Error ({{ error.raw.status }})</h5>\n <et-query-devtools-json\n [value]=\"error.isList ? error.errors : error.error\"\n [search]=\"jsonSearchTerm()\"\n [expandedPaths]=\"jsonExpandedPaths()\"\n [collapsedPaths]=\"jsonCollapsedPaths()\"\n [toggleFn]=\"toggleJsonPath\"\n path=\"error\"\n />\n } @else {\n <h5 class=\"et-query-devtools-section\">Response</h5>\n <et-query-devtools-json\n [value]=\"sel.query.response()\"\n [search]=\"jsonSearchTerm()\"\n [expandedPaths]=\"jsonExpandedPaths()\"\n [collapsedPaths]=\"jsonCollapsedPaths()\"\n [toggleFn]=\"toggleJsonPath\"\n path=\"response\"\n />\n }\n </ng-template>\n </section>\n}\n\n@if (!open()) {\n <et-query-devtools-toggle (openChange)=\"toggleOpen()\" />\n}\n\n@if (inspectActive() && inspectHover(); as hover) {\n <div\n [style.left.px]=\"hover.rect.left\"\n [style.top.px]=\"hover.rect.top\"\n [style.width.px]=\"hover.rect.width\"\n [style.height.px]=\"hover.rect.height\"\n class=\"et-query-devtools-inspect-box\"\n >\n <span class=\"et-query-devtools-inspect-tag\">{{ inspectLabel(hover.entries) }}</span>\n </div>\n}\n", styles: ["@layer components{.et-query-devtools-host{--_et-qdt-bg: var(--et-surface-background-solid, rgb(24 24 27));--_et-qdt-fg: var(--et-surface-color-solid, rgb(244 244 245));--_et-qdt-muted: var(--et-surface-color-muted-solid, rgb(161 161 170));--_et-qdt-subtle: var(--et-surface-color-subtle-solid, rgb(113 113 122));--_et-qdt-border: var(--et-surface-border-solid, rgb(255 255 255 / .12));--_et-qdt-interaction: var(--et-surface-interaction-solid, rgb(255 255 255));--_et-qdt-accent: var(--et-theme-color-primary-solid, rgb(96 165 250));--_et-qdt-hover: color-mix(in srgb, var(--_et-qdt-interaction) 10%, transparent);--_et-qdt-active: color-mix(in srgb, var(--_et-qdt-interaction) 18%, transparent);--_et-qdt-success: rgb(34 197 94);--_et-qdt-error: rgb(239 68 68);--_et-qdt-loading: rgb(234 179 8);position:fixed;inset-inline:0;inset-block-end:0;z-index:2147483000;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,Liberation Mono,monospace;font-size:1.2rem;line-height:1.4;pointer-events:none}.et-query-devtools-host>*{pointer-events:auto}.et-query-devtools-panel{position:relative;display:flex;flex-direction:column;inline-size:100%;min-block-size:20rem;max-block-size:90vh;background:var(--_et-qdt-bg);color:var(--_et-qdt-fg);border-block-start:1px solid var(--_et-qdt-border);box-shadow:0 -.4rem 2rem #00000059}.et-query-devtools-panel--resizing{-webkit-user-select:none;user-select:none}.et-query-devtools-resize{position:absolute;inset-inline:0;inset-block-start:0;block-size:.6rem;cursor:ns-resize;z-index:1}.et-query-devtools-resize:after{content:\"\";position:absolute;inset-inline:50%;inset-block-start:.2rem;inline-size:4rem;margin-inline-start:-2rem;block-size:.2rem;border-radius:999px;background:var(--_et-qdt-border)}.et-query-devtools-resize:hover:after{background:var(--_et-qdt-accent)}.et-query-devtools-header{display:flex;align-items:center;justify-content:space-between;gap:.8rem;padding-inline:.8rem;border-block-end:1px solid var(--_et-qdt-border);flex:0 0 auto}.et-query-devtools-tabs{display:flex;flex-wrap:wrap;gap:.2rem}.et-query-devtools-tab{appearance:none;border:none;background:transparent;color:var(--_et-qdt-muted);padding:.9rem 1rem;cursor:pointer;border-block-end:2px solid transparent;font:inherit}.et-query-devtools-tab:hover{color:var(--_et-qdt-fg)}.et-query-devtools-tab--active{color:var(--_et-qdt-fg);border-block-end-color:var(--_et-qdt-accent)}.et-query-devtools-header-actions{display:flex;align-items:center;gap:.4rem;flex:0 0 auto}.et-query-devtools-inspect-btn{appearance:none;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:transparent;color:var(--_et-qdt-muted);cursor:pointer;padding:.4rem .8rem;font:inherit}.et-query-devtools-inspect-btn:hover{color:var(--_et-qdt-fg)}.et-query-devtools-inspect-btn--active{color:#09090b;background:var(--_et-qdt-accent);border-color:var(--_et-qdt-accent)}.et-query-devtools-close{appearance:none;border:none;background:transparent;color:var(--_et-qdt-muted);cursor:pointer;padding:.6rem;font:inherit}.et-query-devtools-inspect-box{position:fixed;z-index:2147483002;pointer-events:none;border:2px solid var(--_et-qdt-accent);background:color-mix(in srgb,var(--_et-qdt-accent) 15%,transparent);border-radius:.2rem}.et-query-devtools-inspect-tag{position:absolute;inset-block-start:100%;inset-inline-start:0;margin-block-start:.2rem;padding:.2rem .5rem;border-radius:.3rem;background:var(--_et-qdt-accent);color:#09090b;font-family:ui-monospace,monospace;font-size:1.1rem;font-weight:600;white-space:nowrap}.et-query-devtools-close:hover{color:var(--_et-qdt-fg)}.et-query-devtools-body{flex:1 1 auto;min-block-size:0;overflow:hidden}.et-query-devtools-master-detail{display:flex;block-size:100%;min-block-size:0}.et-query-devtools-list{flex:0 0 34%;min-inline-size:22rem;max-inline-size:40rem;overflow-y:auto;border-inline-end:1px solid var(--_et-qdt-border)}.et-query-devtools-detail{flex:1 1 auto;min-inline-size:0;overflow-y:auto;padding:1rem}.et-query-devtools-detail .et-query-devtools-detail-head,.et-query-devtools-drawer .et-query-devtools-detail-head{padding-block-end:.8rem;border-block-end:1px solid var(--_et-qdt-border)}.et-query-devtools-detail .et-query-devtools-meta,.et-query-devtools-drawer .et-query-devtools-meta{padding:.8rem;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:color-mix(in srgb,var(--_et-qdt-interaction) 3%,transparent)}.et-query-devtools-detail .et-query-devtools-section-row,.et-query-devtools-drawer .et-query-devtools-section-row{padding-block-start:.8rem;border-block-start:1px solid var(--_et-qdt-border)}.et-query-devtools-filter-chip{display:inline-flex;align-items:center;padding:.3rem .7rem;border-radius:999px;background:var(--_et-qdt-accent);color:#09090b;font-size:1.1rem;font-weight:600}.et-query-devtools-scroll{block-size:100%;overflow:auto;padding:1rem;display:flex;flex-direction:column;gap:1rem}.et-query-devtools-split{display:flex;block-size:100%;min-block-size:0}.et-query-devtools-split .et-query-devtools-scroll{flex:1 1 auto;min-inline-size:0}.et-query-devtools-drawer{flex:0 0 42%;min-inline-size:26rem;max-inline-size:48rem;overflow-y:auto;padding:0 1rem 1rem;border-inline-start:1px solid var(--_et-qdt-border)}.et-query-devtools-drawer-head{display:flex;align-items:center;justify-content:space-between;gap:.8rem;padding:.8rem 0;position:sticky;inset-block-start:0;background:var(--_et-qdt-bg);color:var(--_et-qdt-muted);border-block-end:1px solid var(--_et-qdt-border);margin-block-end:.8rem}.et-query-devtools-toolbar{display:flex;align-items:center;justify-content:space-between;gap:.8rem;padding:.8rem;position:sticky;inset-block-start:0;background:var(--_et-qdt-bg)}.et-query-devtools-field{display:inline-flex;align-items:center;gap:.6rem;color:var(--_et-qdt-muted)}.et-query-devtools-select{background:var(--_et-qdt-bg);color:var(--_et-qdt-fg);border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.4rem .6rem;font:inherit}.et-query-devtools-count{color:var(--_et-qdt-subtle)}.et-query-devtools-row{display:flex;align-items:center;gap:.8rem;inline-size:100%;text-align:start;appearance:none;border:none;border-block-end:1px solid var(--_et-qdt-border);background:transparent;color:var(--_et-qdt-fg);padding:.8rem;cursor:pointer;font:inherit}.et-query-devtools-row:hover{background:var(--_et-qdt-hover)}.et-query-devtools-row--active{background:var(--_et-qdt-active)}.et-query-devtools-method{font-weight:700;font-size:1.1rem;color:var(--_et-qdt-muted);white-space:nowrap}.et-query-devtools-route{overflow:hidden;text-overflow:ellipsis;white-space:nowrap;flex:1 1 auto;min-inline-size:0}.et-query-devtools-status{inline-size:.8rem;block-size:.8rem;border-radius:999px;flex:0 0 auto;background:var(--_et-qdt-subtle)}.et-query-devtools-status[data-status=success]{background:var(--_et-qdt-success)}.et-query-devtools-status[data-status=error]{background:var(--_et-qdt-error)}.et-query-devtools-status[data-status=loading],.et-query-devtools-status[data-status=running]{background:var(--_et-qdt-loading)}.et-query-devtools-detail-head{display:flex;align-items:center;gap:.8rem;margin-block-end:.8rem}.et-query-devtools-actions{display:flex;flex-wrap:wrap;align-items:center;gap:.35rem;margin-block-end:.8rem}.et-query-devtools-btn{appearance:none;border:1px solid var(--_et-qdt-border);border-radius:.3rem;background:transparent;color:var(--_et-qdt-fg);padding:.25rem .55rem;font-size:1.15rem;line-height:1.4;cursor:pointer}.et-query-devtools-btn:hover{background:var(--_et-qdt-hover)}.et-query-devtools-meta{display:grid;grid-template-columns:auto 1fr;gap:.3rem 1rem;margin:0 0 1rem}.et-query-devtools-meta dt{color:var(--_et-qdt-muted)}.et-query-devtools-meta dd{margin:0;overflow-wrap:anywhere}.et-query-devtools-section{margin:1rem 0 .4rem;font-size:1.1rem;text-transform:uppercase;letter-spacing:.05em;color:var(--_et-qdt-muted)}.et-query-devtools-json{margin:0;padding:.8rem;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:color-mix(in srgb,var(--_et-qdt-interaction) 4%,transparent);overflow-x:auto;white-space:pre-wrap;overflow-wrap:anywhere;max-block-size:24rem;overflow-y:auto}.et-query-devtools-json--error{border-color:color-mix(in srgb,var(--_et-qdt-error) 50%,transparent)}.et-query-devtools-mono{font-variant-numeric:tabular-nums;overflow-wrap:anywhere}.et-query-devtools-code{margin:0 0 .8rem;padding:.8rem;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:color-mix(in srgb,var(--_et-qdt-interaction) 4%,transparent);overflow:auto;white-space:pre;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;font-size:1.15rem;max-block-size:20rem}.et-query-devtools-ws-message{border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.6rem;margin-block-end:.4rem}.et-query-devtools-url{display:inline-block;max-inline-size:32rem;margin-inline-start:.6rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;vertical-align:bottom;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace}.et-query-devtools-chips,.et-query-devtools-chip-row{display:flex;flex-wrap:wrap;gap:.4rem;margin-block-end:.8rem}.et-query-devtools-chip{display:inline-flex;align-items:center;gap:.3rem;padding:.2rem .6rem;border-radius:999px;border:1px solid var(--_et-qdt-border);font-size:1.1rem;color:var(--_et-qdt-fg);background:color-mix(in srgb,var(--_et-qdt-interaction) 6%,transparent)}.et-query-devtools-chip--muted{color:var(--_et-qdt-muted)}.et-query-devtools-chip--loading{color:var(--_et-qdt-loading);border-color:color-mix(in srgb,var(--_et-qdt-loading) 50%,transparent)}.et-query-devtools-chip--error{color:var(--_et-qdt-error);border-color:color-mix(in srgb,var(--_et-qdt-error) 50%,transparent)}.et-query-devtools-chip--success{color:var(--_et-qdt-success);border-color:color-mix(in srgb,var(--_et-qdt-success) 50%,transparent)}.et-query-devtools-card{border:1px solid var(--_et-qdt-border);border-radius:.6rem;padding:1rem}.et-query-devtools-card-head{display:flex;align-items:center;gap:.6rem;margin-block-end:.8rem}.et-query-devtools-card-title{display:flex;align-items:baseline;gap:.5rem;margin-block-end:.2rem}.et-query-devtools-card-sub{color:var(--_et-qdt-subtle);font-size:1.1rem;margin-block-end:.6rem;overflow-wrap:anywhere}.et-query-devtools-inner-queries{display:flex;flex-direction:column;gap:.3rem}.et-query-devtools-inner-row{display:flex;align-items:center;gap:.6rem;inline-size:100%;text-align:start;appearance:none;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:transparent;color:var(--_et-qdt-fg);padding:.4rem .6rem;cursor:pointer;font:inherit}.et-query-devtools-inner-row:hover:not([disabled]){background:var(--_et-qdt-hover)}.et-query-devtools-inner-row--active{background:var(--_et-qdt-active);border-color:var(--_et-qdt-accent)}.et-query-devtools-inner-row[disabled]{cursor:default;opacity:.6}.et-query-devtools-step-list{display:flex;flex-direction:column;gap:.4rem;margin:0;padding:0;list-style:none}.et-query-devtools-step-item{border:1px solid var(--_et-qdt-border);border-radius:.4rem;overflow:hidden}.et-query-devtools-step-item[data-status=error]{border-color:color-mix(in srgb,var(--_et-qdt-error) 50%,transparent)}.et-query-devtools-step-head{display:flex;align-items:stretch}.et-query-devtools-step-head .et-query-devtools-inner-row{border:none;border-radius:0;flex:1 1 auto}.et-query-devtools-step-caret-btn{appearance:none;border:none;border-inline-start:1px solid var(--_et-qdt-border);background:transparent;color:var(--_et-qdt-muted);cursor:pointer;padding:0 .7rem;font:inherit}.et-query-devtools-step-caret-btn:hover{background:var(--_et-qdt-hover);color:var(--_et-qdt-fg)}.et-query-devtools-step-toggle{display:flex;align-items:center;gap:.6rem;inline-size:100%;text-align:start;appearance:none;border:none;background:transparent;color:var(--_et-qdt-fg);padding:.6rem;cursor:pointer;font:inherit}.et-query-devtools-step-toggle:hover{background:var(--_et-qdt-hover)}.et-query-devtools-step-index{flex:1 1 auto;min-inline-size:0}.et-query-devtools-step-caret{color:var(--_et-qdt-muted)}.et-query-devtools-step-io{padding:0 .8rem .8rem;border-block-start:1px solid var(--_et-qdt-border)}.et-query-devtools-table{inline-size:100%;border-collapse:collapse}.et-query-devtools-table th,.et-query-devtools-table td{text-align:start;padding:.5rem .6rem;border-block-end:1px solid var(--_et-qdt-border);vertical-align:top}.et-query-devtools-table th{color:var(--_et-qdt-muted);font-weight:600;position:sticky;inset-block-start:0;background:var(--_et-qdt-bg)}.et-query-devtools-table tr[data-status=error] td{color:var(--_et-qdt-error)}.et-query-devtools-empty{color:var(--_et-qdt-subtle);padding:1.2rem;text-align:center}.et-query-devtools-actions-label{color:var(--_et-qdt-subtle);align-self:center;text-transform:uppercase;font-size:1rem;letter-spacing:.05em}.et-query-devtools-actions-label:not(:first-child){margin-inline-start:.7rem}.et-query-devtools-cell-actions{display:flex;gap:.4rem;white-space:nowrap}.et-query-devtools-section-row{display:flex;align-items:center;justify-content:space-between;gap:.8rem;margin-block-start:1rem}.et-query-devtools-search{flex:0 1 20rem;background:var(--_et-qdt-bg);color:var(--_et-qdt-fg);border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.4rem .6rem;font:inherit}.et-query-devtools-editor{border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.8rem;margin-block-end:1rem}.et-query-devtools-textarea{inline-size:100%;min-block-size:12rem;resize:vertical;background:color-mix(in srgb,var(--_et-qdt-interaction) 4%,transparent);color:var(--_et-qdt-fg);border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.6rem;font-family:inherit;font-size:1.2rem}.et-query-devtools-editor-error{color:var(--_et-qdt-error);margin:.4rem 0 0}.et-query-devtools-json-node,.et-query-devtools-json-children{display:flex;flex-direction:column}.et-query-devtools-json-children{padding-inline-start:1.4rem;border-inline-start:1px solid var(--_et-qdt-border);margin-inline-start:.4rem}.et-query-devtools-json-row{display:flex;align-items:baseline;gap:.4rem;padding:.1rem 0;font-family:inherit;line-height:1.5}.et-query-devtools-json-toggle{appearance:none;border:none;background:transparent;color:var(--_et-qdt-fg);cursor:pointer;text-align:start;font:inherit;padding:.1rem 0}.et-query-devtools-json-toggle:hover{background:var(--_et-qdt-hover)}.et-query-devtools-json-caret{color:var(--_et-qdt-subtle);inline-size:1rem;flex:0 0 auto}.et-query-devtools-json-key{color:var(--_et-qdt-accent)}.et-query-devtools-json-colon,.et-query-devtools-json-preview{color:var(--_et-qdt-subtle)}.et-query-devtools-json-value{overflow-wrap:anywhere}.et-query-devtools-json-leaf[data-kind=string] .et-query-devtools-json-value{color:var(--_et-qdt-success)}.et-query-devtools-json-leaf[data-kind=number] .et-query-devtools-json-value,.et-query-devtools-json-leaf[data-kind=boolean] .et-query-devtools-json-value{color:var(--_et-qdt-loading)}.et-query-devtools-json-leaf[data-kind=null] .et-query-devtools-json-value,.et-query-devtools-json-leaf[data-kind=undefined] .et-query-devtools-json-value{color:var(--_et-qdt-subtle)}.et-query-devtools-json-hit{background:color-mix(in srgb,var(--_et-qdt-loading) 40%,transparent);border-radius:.2rem}.et-query-devtools-json-copy{appearance:none;border:none;background:transparent;color:var(--_et-qdt-subtle);cursor:pointer;opacity:0;font:inherit}.et-query-devtools-json-row:hover .et-query-devtools-json-copy{opacity:1}}\n"], dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: QueryDevtoolsJsonComponent, selector: "et-query-devtools-json", inputs: ["value", "nodeKey", "depth", "search", "path", "expandedPaths", "collapsedPaths", "toggleFn"] }, { kind: "component", type: QueryDevtoolsToggleComponent, selector: "et-query-devtools-toggle", outputs: ["openChange"] }], encapsulation: i0.ViewEncapsulation.None }); }
|
|
30915
|
+
}
|
|
30916
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.7", ngImport: i0, type: QueryDevtoolsComponent, decorators: [{
|
|
30917
|
+
type: Component,
|
|
30918
|
+
args: [{ selector: 'et-query-devtools', encapsulation: ViewEncapsulation.None, imports: [NgTemplateOutlet, QueryDevtoolsJsonComponent, QueryDevtoolsToggleComponent], host: {
|
|
30919
|
+
class: 'et-query-devtools-host',
|
|
30920
|
+
}, template: "@if (open()) {\n <section\n [class.et-query-devtools-panel--resizing]=\"resizing()\"\n [style.height.px]=\"panelHeight()\"\n class=\"et-query-devtools-panel\"\n >\n <div\n (pointerdown)=\"startResize($event)\"\n class=\"et-query-devtools-resize\"\n title=\"Drag to resize\"\n aria-hidden=\"true\"\n ></div>\n <header class=\"et-query-devtools-header\">\n <nav class=\"et-query-devtools-tabs\" role=\"tablist\">\n @for (tab of tabs; track tab.id) {\n <button\n [class.et-query-devtools-tab--active]=\"activeTab() === tab.id\"\n [attr.aria-selected]=\"activeTab() === tab.id\"\n (click)=\"activeTab.set(tab.id)\"\n class=\"et-query-devtools-tab\"\n type=\"button\"\n role=\"tab\"\n >\n {{ tab.label }}\n </button>\n }\n </nav>\n\n <div class=\"et-query-devtools-header-actions\">\n <button\n [class.et-query-devtools-inspect-btn--active]=\"inspectActive()\"\n (click)=\"toggleInspect()\"\n class=\"et-query-devtools-inspect-btn\"\n type=\"button\"\n title=\"Inspect: hover the UI to find its query\"\n >\n \u2316 Inspect\n </button>\n <button (click)=\"toggleOpen()\" class=\"et-query-devtools-close\" type=\"button\" title=\"Close devtools\">\u2715</button>\n </div>\n </header>\n\n <div class=\"et-query-devtools-body\">\n @switch (activeTab()) {\n <!-- QUERIES -->\n @case ('queries') {\n <div class=\"et-query-devtools-master-detail\">\n <div class=\"et-query-devtools-list\">\n <div class=\"et-query-devtools-toolbar\">\n @if (inspectFilterIds(); as ids) {\n <span class=\"et-query-devtools-filter-chip\">\u2316 inspected \u00B7 {{ ids.length }}</span>\n <button (click)=\"clearInspectFilter()\" class=\"et-query-devtools-btn\" type=\"button\">Reset</button>\n } @else {\n <label class=\"et-query-devtools-field\">\n <span>Client</span>\n <select\n #clientSelect\n [value]=\"selectedClientName() ?? ''\"\n (change)=\"selectClient(clientSelect.value || null)\"\n class=\"et-query-devtools-select\"\n >\n <option value=\"\">All clients</option>\n @for (name of clientNames(); track name) {\n <option [value]=\"name\">{{ name }}</option>\n }\n </select>\n </label>\n }\n <span class=\"et-query-devtools-count\">{{ filteredQueries().length }}</span>\n </div>\n\n @for (item of filteredQueries(); track item.entry.id) {\n <button\n [class.et-query-devtools-row--active]=\"selectedQueryId() === item.entry.id\"\n (click)=\"selectedQueryId.set(item.entry.id)\"\n class=\"et-query-devtools-row\"\n type=\"button\"\n >\n <span\n [attr.data-status]=\"queryStatus(item.query)\"\n [title]=\"queryStatus(item.query)\"\n class=\"et-query-devtools-status\"\n ></span>\n <span class=\"et-query-devtools-method\">{{ item.entry.meta.method }}</span>\n <span class=\"et-query-devtools-route\">{{ item.entry.meta.route || '\u2014' }}</span>\n @if (isStale(item.query)) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">stale</span>\n }\n </button>\n } @empty {\n @if (inspectFilterIds()) {\n <p class=\"et-query-devtools-empty\">\n The inspected element's queries are no longer registered. Reset the filter.\n </p>\n } @else {\n <p class=\"et-query-devtools-empty\">No queries registered.</p>\n }\n }\n </div>\n\n <div class=\"et-query-devtools-detail\">\n @if (selectedQuery(); as sel) {\n <ng-container *ngTemplateOutlet=\"queryDetailTpl; context: { sel }\" />\n } @else {\n <p class=\"et-query-devtools-empty\">Select a query to inspect it.</p>\n }\n </div>\n </div>\n }\n\n <!-- STACKS -->\n @case ('stacks') {\n <div class=\"et-query-devtools-split\">\n <div class=\"et-query-devtools-scroll\">\n @for (entry of stackEntries(); track entry.id) {\n @if (entry.kind === 'paged-query-stack') {\n @let paged = asPagedStack(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-chip\">paged stack</span>\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">{{ paged.direction() }}</span>\n @if (paged.loading()) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--loading\">loading</span>\n }\n </div>\n\n @let pagedId = stackIdentity(paged);\n <div class=\"et-query-devtools-card-title\">\n <span class=\"et-query-devtools-method\">{{ pagedId.method }}</span>\n <span class=\"et-query-devtools-route\">{{ pagedId.route }}</span>\n </div>\n <div class=\"et-query-devtools-card-sub et-query-devtools-mono\">{{ pagedId.baseUrl }}</div>\n @if (entry.meta.featureTypes?.length) {\n <div class=\"et-query-devtools-chips\">\n @for (feature of entry.meta.featureTypes; track feature) {\n <span class=\"et-query-devtools-chip\">{{ featureLabel(feature) }}</span>\n }\n </div>\n }\n\n <dl class=\"et-query-devtools-meta\">\n <dt>Pages loaded</dt>\n <dd>{{ paged.queries().length }}</dd>\n <dt>Items</dt>\n <dd>{{ paged.items().length }}</dd>\n <dt>First page loaded</dt>\n <dd>{{ paged.isFirstPageLoaded() }}</dd>\n <dt>Last page loaded</dt>\n <dd>{{ paged.isLastPageLoaded() }}</dd>\n </dl>\n <ng-container *ngTemplateOutlet=\"innerQueriesTpl; context: { links: queriesForStack(paged) }\" />\n </div>\n } @else {\n @let stack = asStack(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-chip\">stack</span>\n @if (stack.anyLoading()) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--loading\">loading</span>\n }\n @if (stack.anyError()) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--error\">error</span>\n }\n </div>\n\n @let stackId = stackIdentity(stack);\n <div class=\"et-query-devtools-card-title\">\n <span class=\"et-query-devtools-method\">{{ stackId.method }}</span>\n <span class=\"et-query-devtools-route\">{{ stackId.route }}</span>\n </div>\n <div class=\"et-query-devtools-card-sub et-query-devtools-mono\">{{ stackId.baseUrl }}</div>\n @if (entry.meta.featureTypes?.length) {\n <div class=\"et-query-devtools-chips\">\n @for (feature of entry.meta.featureTypes; track feature) {\n <span class=\"et-query-devtools-chip\">{{ featureLabel(feature) }}</span>\n }\n </div>\n }\n\n <dl class=\"et-query-devtools-meta\">\n <dt>Queries</dt>\n <dd>{{ stack.queries().length }}</dd>\n <dt>Loading</dt>\n <dd>{{ stack.loadingProgress().loaded }} / {{ stack.loadingProgress().total }}</dd>\n <dt>Errors</dt>\n <dd>{{ stack.errors().length }}</dd>\n </dl>\n <ng-container *ngTemplateOutlet=\"innerQueriesTpl; context: { links: queriesForStack(stack) }\" />\n </div>\n }\n } @empty {\n <p class=\"et-query-devtools-empty\">No stacks registered.</p>\n }\n </div>\n\n @if (stackSelectedQuery(); as sel) {\n <aside class=\"et-query-devtools-drawer\">\n <div class=\"et-query-devtools-drawer-head\">\n <span>Query detail</span>\n <button\n (click)=\"stackSelectedQueryId.set(null)\"\n class=\"et-query-devtools-close\"\n type=\"button\"\n title=\"Close detail\"\n >\n \u2715\n </button>\n </div>\n <ng-container *ngTemplateOutlet=\"queryDetailTpl; context: { sel }\" />\n </aside>\n }\n </div>\n }\n\n <!-- SEQUENCES -->\n @case ('sequences') {\n <div class=\"et-query-devtools-split\">\n <div class=\"et-query-devtools-scroll\">\n @for (entry of sequenceEntries(); track entry.id) {\n @let sequence = asSequence(entry);\n @if (sequence) {\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-chip\">sequence</span>\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">{{ sequence.status() }}</span>\n <span class=\"et-query-devtools-count\"\n >step {{ sequence.currentStep() }} / {{ sequence.total }}</span\n >\n </div>\n\n <ol class=\"et-query-devtools-step-list\">\n @for (link of queriesForSequence(sequence); track $index; let i = $index) {\n <li [attr.data-status]=\"sequenceStepStatus(sequence, i)\" class=\"et-query-devtools-step-item\">\n <div class=\"et-query-devtools-step-head\">\n <button\n [class.et-query-devtools-inner-row--active]=\"sequenceSelectedQueryId() === link.id\"\n [disabled]=\"!link.id\"\n (click)=\"sequenceSelectedQueryId.set(link.id)\"\n class=\"et-query-devtools-inner-row\"\n type=\"button\"\n >\n <span\n [attr.data-status]=\"sequenceStepStatus(sequence, i)\"\n class=\"et-query-devtools-status\"\n ></span>\n <span class=\"et-query-devtools-method\">{{ i + 1 }}. {{ link.method }}</span>\n <span class=\"et-query-devtools-route\">{{ link.route || 'step ' + (i + 1) }}</span>\n </button>\n <button\n [attr.aria-expanded]=\"isStepExpanded(entry.id, i)\"\n (click)=\"toggleStep(entry.id, i)\"\n class=\"et-query-devtools-step-caret-btn\"\n type=\"button\"\n title=\"Toggle in / out\"\n >\n {{ isStepExpanded(entry.id, i) ? '\u25BE' : '\u25B8' }}\n </button>\n </div>\n\n @if (isStepExpanded(entry.id, i)) {\n @let snap = stepSnapshot(sequence, i);\n <div class=\"et-query-devtools-step-io\">\n <h5 class=\"et-query-devtools-section\">In \u00B7 args</h5>\n @if (sequence.stepArgs().length > i) {\n <et-query-devtools-json [value]=\"sequence.stepArgs()[i]\" />\n } @else {\n <p class=\"et-query-devtools-empty\">Not run yet.</p>\n }\n\n @if (snap?.error(); as error) {\n <h5 class=\"et-query-devtools-section\">Out \u00B7 error ({{ error.raw.status }})</h5>\n <et-query-devtools-json [value]=\"error.isList ? error.errors : error.error\" />\n } @else {\n <h5 class=\"et-query-devtools-section\">Out \u00B7 response</h5>\n @if (snap) {\n <et-query-devtools-json [value]=\"snap.response()\" />\n } @else {\n <p class=\"et-query-devtools-empty\">Not run yet.</p>\n }\n }\n </div>\n }\n </li>\n }\n </ol>\n </div>\n }\n } @empty {\n <p class=\"et-query-devtools-empty\">No sequences registered.</p>\n }\n </div>\n\n @if (sequenceSelectedQuery(); as sel) {\n <aside class=\"et-query-devtools-drawer\">\n <div class=\"et-query-devtools-drawer-head\">\n <span>Query detail</span>\n <button\n (click)=\"sequenceSelectedQueryId.set(null)\"\n class=\"et-query-devtools-close\"\n type=\"button\"\n title=\"Close detail\"\n >\n \u2715\n </button>\n </div>\n <ng-container *ngTemplateOutlet=\"queryDetailTpl; context: { sel }\" />\n </aside>\n }\n </div>\n }\n\n <!-- AUTH -->\n @case ('auth') {\n <div class=\"et-query-devtools-scroll\">\n @for (entry of authEntries(); track entry.id) {\n @let auth = asAuth(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <strong>{{ entry.meta.name || 'auth provider' }}</strong>\n <span\n [class.et-query-devtools-chip--success]=\"auth.isAuthenticated()\"\n [class.et-query-devtools-chip--muted]=\"!auth.isAuthenticated()\"\n class=\"et-query-devtools-chip\"\n >\n {{ auth.isAuthenticated() ? 'authenticated' : 'anonymous' }}\n </span>\n </div>\n <dl class=\"et-query-devtools-meta\">\n <dt>Base URL</dt>\n <dd class=\"et-query-devtools-mono\">{{ entry.meta.clientBaseUrl || entry.meta.clientName || '\u2014' }}</dd>\n <dt>Access token</dt>\n <dd>{{ auth.accessToken() ? 'present' : 'none' }}</dd>\n <dt>Refresh token</dt>\n <dd>{{ auth.refreshToken() ? 'present' : 'none' }}</dd>\n @if (authTokenExpiry(auth); as expiry) {\n <dt>Token expires in</dt>\n <dd>{{ expiry }}</dd>\n }\n @if (auth.executionState(); as state) {\n <dt>Execution state</dt>\n <dd>{{ state.type }} \u00B7 {{ state.state }}</dd>\n }\n @if (authQueryKeys(auth).length) {\n <dt>Queries</dt>\n <dd>\n <div class=\"et-query-devtools-chips\">\n @for (key of authQueryKeys(auth); track key) {\n <span class=\"et-query-devtools-chip\">{{ key }}</span>\n }\n </div>\n </dd>\n }\n @if (authFeatures(auth).length) {\n <dt>Features</dt>\n <dd>\n <div class=\"et-query-devtools-chips\">\n @for (feature of authFeatures(auth); track feature) {\n <span class=\"et-query-devtools-chip\">{{ feature }}</span>\n }\n </div>\n </dd>\n }\n </dl>\n\n @if (authTokenPayload(auth); as payload) {\n <h4 class=\"et-query-devtools-section\">Access token payload</h4>\n <et-query-devtools-json [value]=\"payload\" />\n }\n\n @if (auth.latestNonInternalQuery(); as latest) {\n <h4 class=\"et-query-devtools-section\">Latest auth query \u00B7 {{ latest.key }}</h4>\n <et-query-devtools-json [value]=\"latest.snapshot.response()\" />\n }\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No auth providers registered.</p>\n }\n </div>\n }\n\n <!-- SOCKETS -->\n @case ('ws') {\n <div class=\"et-query-devtools-scroll\">\n @for (entry of wsEntries(); track entry.id) {\n @let ws = asWs(entry);\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <strong>{{ entry.meta.name || 'socket' }}</strong>\n <span\n [class.et-query-devtools-chip--success]=\"ws.connected()\"\n [class.et-query-devtools-chip--muted]=\"!ws.connected()\"\n class=\"et-query-devtools-chip\"\n >\n {{ ws.connected() ? 'connected' : 'disconnected' }}\n </span>\n </div>\n <dl class=\"et-query-devtools-meta\">\n <dt>URL</dt>\n <dd class=\"et-query-devtools-mono\">{{ entry.meta.url }}</dd>\n <dt>Rooms</dt>\n <dd>\n @if (ws.rooms().length) {\n <div class=\"et-query-devtools-chips\">\n @for (room of ws.rooms(); track room) {\n <span class=\"et-query-devtools-chip\">{{ room }}</span>\n }\n </div>\n } @else {\n none\n }\n </dd>\n </dl>\n\n <h5 class=\"et-query-devtools-section\">Messages ({{ ws.messages().length }})</h5>\n @for (message of ws.messages(); track message.id) {\n <div class=\"et-query-devtools-ws-message\">\n <div class=\"et-query-devtools-card-head\">\n <span class=\"et-query-devtools-count\">{{ formatTime(message.timestamp) }}</span>\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">{{ message.room }}</span>\n <span class=\"et-query-devtools-method\">{{ message.event }}</span>\n </div>\n <et-query-devtools-json [value]=\"message.data\" />\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No messages received yet.</p>\n }\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No web socket clients registered.</p>\n }\n </div>\n }\n\n <!-- CACHE -->\n @case ('cache') {\n <div class=\"et-query-devtools-scroll\">\n @for (client of cacheView(); track client.name) {\n <div class=\"et-query-devtools-card\">\n <div class=\"et-query-devtools-card-head\">\n <strong class=\"et-query-devtools-mono\">{{ client.baseUrl || client.name }}</strong>\n <span class=\"et-query-devtools-count\">{{ client.entries.length }} entries</span>\n </div>\n <table class=\"et-query-devtools-table\">\n <thead>\n <tr>\n <th>Request</th>\n <th>Consumers</th>\n <th>Secure</th>\n <th>Freshness</th>\n <th>Actions</th>\n </tr>\n </thead>\n <tbody>\n @for (cacheEntry of client.entries; track cacheEntry.key) {\n <tr>\n <td [title]=\"cacheEntry.request.method + ' ' + cacheEntry.request.url\">\n <span class=\"et-query-devtools-method\">{{ cacheEntry.request.method }}</span>\n <span class=\"et-query-devtools-url\">{{ requestPath(cacheEntry.request.url) }}</span>\n </td>\n <td>{{ cacheEntry.consumerCount }}</td>\n <td>{{ cacheEntry.isSecure ? 'yes' : 'no' }}</td>\n <td>{{ cacheFreshness(cacheEntry) }}</td>\n <td class=\"et-query-devtools-cell-actions\">\n <button (click)=\"refetchCacheEntry(cacheEntry)\" class=\"et-query-devtools-btn\" type=\"button\">\n Refetch\n </button>\n <button\n (click)=\"evictCacheEntry(client.repository, cacheEntry.key)\"\n class=\"et-query-devtools-btn\"\n type=\"button\"\n >\n Evict\n </button>\n </td>\n </tr>\n } @empty {\n <tr>\n <td class=\"et-query-devtools-empty\" colspan=\"5\">Cache empty.</td>\n </tr>\n }\n </tbody>\n </table>\n </div>\n } @empty {\n <p class=\"et-query-devtools-empty\">No clients with a cache yet.</p>\n }\n </div>\n }\n\n <!-- EVENTS -->\n @case ('events') {\n <div class=\"et-query-devtools-scroll\">\n <div class=\"et-query-devtools-toolbar\">\n <span class=\"et-query-devtools-count\">{{ eventLog().length }} events</span>\n <button (click)=\"clearEvents()\" class=\"et-query-devtools-btn\" type=\"button\">Clear</button>\n </div>\n <table class=\"et-query-devtools-table\">\n <thead>\n <tr>\n <th>Time</th>\n <th>Base URL</th>\n <th>Type</th>\n <th>Request</th>\n </tr>\n </thead>\n <tbody>\n @for (event of eventLog(); track event.id) {\n <tr [attr.data-status]=\"event.type === 'request-error' ? 'error' : 'success'\">\n <td>{{ formatTime(event.timestamp) }}</td>\n <td class=\"et-query-devtools-mono\">{{ event.client }}</td>\n <td>\n {{ event.type === 'request-error' ? 'error ' + event.status : 'success' }}\n @if (event.isSecure) {\n <span class=\"et-query-devtools-chip et-query-devtools-chip--muted\">secure</span>\n }\n </td>\n <td [title]=\"event.method + ' ' + event.url\">\n <span class=\"et-query-devtools-method\">{{ event.method }}</span>\n <span class=\"et-query-devtools-url\">{{ requestPath(event.url) }}</span>\n </td>\n </tr>\n } @empty {\n <tr>\n <td class=\"et-query-devtools-empty\" colspan=\"4\">No events captured yet.</td>\n </tr>\n }\n </tbody>\n </table>\n </div>\n }\n }\n </div>\n\n <!-- Reusable inner-query list (stacks) \u2014 clicking opens the split-view drawer, not a tab switch. -->\n <ng-template #innerQueriesTpl let-links=\"links\">\n <div class=\"et-query-devtools-inner-queries\">\n @for (link of links; track $index) {\n <button\n [class.et-query-devtools-inner-row--active]=\"stackSelectedQueryId() === link.id\"\n [disabled]=\"!link.id\"\n (click)=\"stackSelectedQueryId.set(link.id)\"\n class=\"et-query-devtools-inner-row\"\n type=\"button\"\n >\n <span [attr.data-status]=\"queryStatus(link.query)\" class=\"et-query-devtools-status\"></span>\n <span class=\"et-query-devtools-method\">{{ link.method }}</span>\n <span class=\"et-query-devtools-route\">{{ link.route || link.query.id() || 'query ' + ($index + 1) }}</span>\n </button>\n }\n </div>\n </ng-template>\n\n <!-- Reusable query detail \u2014 used by the Queries tab and the stacks split-view drawer. -->\n <ng-template #queryDetailTpl let-sel=\"sel\">\n <div class=\"et-query-devtools-detail-head\">\n <span class=\"et-query-devtools-method\">{{ sel.entry.meta.method }}</span>\n <span class=\"et-query-devtools-route\">{{ sel.entry.meta.route || '\u2014' }}</span>\n </div>\n\n <div class=\"et-query-devtools-actions\">\n <span class=\"et-query-devtools-actions-label\">Run</span>\n <button (click)=\"executeQuery(sel.query, false)\" class=\"et-query-devtools-btn\" type=\"button\">Execute</button>\n <button (click)=\"executeQuery(sel.query, true)\" class=\"et-query-devtools-btn\" type=\"button\">Cached</button>\n <button (click)=\"resetQuery(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Reset</button>\n <button (click)=\"copyReport(sel.entry, sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">\n {{ copiedReport() ? '\u2713 Copied' : 'Copy report' }}\n </button>\n <span class=\"et-query-devtools-actions-label\">Edit</span>\n <button (click)=\"openResponseEditor(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Response</button>\n <button (click)=\"openArgsEditor(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Replay args</button>\n <span class=\"et-query-devtools-actions-label\">Force</span>\n <button (click)=\"forceLoading(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Loading</button>\n <button (click)=\"forceError(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Error</button>\n <button (click)=\"forceEmpty(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Empty</button>\n <button (click)=\"clearForced(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Clear</button>\n </div>\n\n @if (editorMode() !== 'none') {\n <div class=\"et-query-devtools-editor\">\n @if (editorMode() === 'response') {\n <h4 class=\"et-query-devtools-section\">Edit response \u2192 setResponse()</h4>\n <textarea\n #respArea\n [value]=\"responseDraft()\"\n (input)=\"responseDraft.set(respArea.value)\"\n class=\"et-query-devtools-textarea\"\n spellcheck=\"false\"\n ></textarea>\n <div class=\"et-query-devtools-actions\">\n <button (click)=\"applyResponse(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Apply</button>\n <button (click)=\"cancelEditor()\" class=\"et-query-devtools-btn\" type=\"button\">Cancel</button>\n </div>\n } @else {\n <h4 class=\"et-query-devtools-section\">Replay with edited args \u2192 execute()</h4>\n <textarea\n #argsArea\n [value]=\"argsDraft()\"\n (input)=\"argsDraft.set(argsArea.value)\"\n class=\"et-query-devtools-textarea\"\n spellcheck=\"false\"\n ></textarea>\n <div class=\"et-query-devtools-actions\">\n <button (click)=\"applyArgs(sel.query)\" class=\"et-query-devtools-btn\" type=\"button\">Execute</button>\n <button (click)=\"cancelEditor()\" class=\"et-query-devtools-btn\" type=\"button\">Cancel</button>\n </div>\n }\n @if (editError(); as err) {\n <p class=\"et-query-devtools-editor-error\">{{ err }}</p>\n }\n </div>\n }\n\n <dl class=\"et-query-devtools-meta\">\n <dt>Base URL</dt>\n <dd class=\"et-query-devtools-mono\">{{ sel.entry.meta.clientBaseUrl || sel.entry.meta.clientName || '\u2014' }}</dd>\n <dt>Status</dt>\n <dd>{{ queryStatus(sel.query) }}</dd>\n <dt>Cache key</dt>\n <dd class=\"et-query-devtools-mono\">{{ sel.query.id() || '\u2014' }}</dd>\n <dt>Last executed</dt>\n <dd>{{ formatTime(sel.query.lastTimeExecutedAt()) }}</dd>\n <dt>Triggered by</dt>\n <dd>{{ sel.query.triggeredBy() || 'user' }}</dd>\n @if (sel.entry.meta.featureTypes?.length) {\n <dt>Features</dt>\n <dd>\n <div class=\"et-query-devtools-chips\">\n @for (feature of sel.entry.meta.featureTypes; track feature) {\n <span class=\"et-query-devtools-chip\">{{ featureLabel(feature) }}</span>\n }\n </div>\n </dd>\n }\n </dl>\n\n @if (sel.entry.meta.gqlQuery; as gqlQuery) {\n <h5 class=\"et-query-devtools-section\">GraphQL document</h5>\n <pre class=\"et-query-devtools-code\">{{ gqlDocument(gqlQuery) }}</pre>\n }\n\n <div class=\"et-query-devtools-section-row\">\n <h4 class=\"et-query-devtools-section\">Value explorer</h4>\n <input\n #jsonSearchInput\n [value]=\"jsonSearch()\"\n (input)=\"jsonSearch.set(jsonSearchInput.value)\"\n class=\"et-query-devtools-search\"\n type=\"search\"\n placeholder=\"filter keys / values\u2026\"\n />\n </div>\n\n <h5 class=\"et-query-devtools-section\">Args</h5>\n <et-query-devtools-json\n [value]=\"sel.query.args()\"\n [search]=\"jsonSearchTerm()\"\n [expandedPaths]=\"jsonExpandedPaths()\"\n [collapsedPaths]=\"jsonCollapsedPaths()\"\n [toggleFn]=\"toggleJsonPath\"\n path=\"args\"\n />\n\n @if (sel.query.error(); as error) {\n <h5 class=\"et-query-devtools-section\">Error ({{ error.raw.status }})</h5>\n <et-query-devtools-json\n [value]=\"error.isList ? error.errors : error.error\"\n [search]=\"jsonSearchTerm()\"\n [expandedPaths]=\"jsonExpandedPaths()\"\n [collapsedPaths]=\"jsonCollapsedPaths()\"\n [toggleFn]=\"toggleJsonPath\"\n path=\"error\"\n />\n } @else {\n <h5 class=\"et-query-devtools-section\">Response</h5>\n <et-query-devtools-json\n [value]=\"sel.query.response()\"\n [search]=\"jsonSearchTerm()\"\n [expandedPaths]=\"jsonExpandedPaths()\"\n [collapsedPaths]=\"jsonCollapsedPaths()\"\n [toggleFn]=\"toggleJsonPath\"\n path=\"response\"\n />\n }\n </ng-template>\n </section>\n}\n\n@if (!open()) {\n <et-query-devtools-toggle (openChange)=\"toggleOpen()\" />\n}\n\n@if (inspectActive() && inspectHover(); as hover) {\n <div\n [style.left.px]=\"hover.rect.left\"\n [style.top.px]=\"hover.rect.top\"\n [style.width.px]=\"hover.rect.width\"\n [style.height.px]=\"hover.rect.height\"\n class=\"et-query-devtools-inspect-box\"\n >\n <span class=\"et-query-devtools-inspect-tag\">{{ inspectLabel(hover.entries) }}</span>\n </div>\n}\n", styles: ["@layer components{.et-query-devtools-host{--_et-qdt-bg: var(--et-surface-background-solid, rgb(24 24 27));--_et-qdt-fg: var(--et-surface-color-solid, rgb(244 244 245));--_et-qdt-muted: var(--et-surface-color-muted-solid, rgb(161 161 170));--_et-qdt-subtle: var(--et-surface-color-subtle-solid, rgb(113 113 122));--_et-qdt-border: var(--et-surface-border-solid, rgb(255 255 255 / .12));--_et-qdt-interaction: var(--et-surface-interaction-solid, rgb(255 255 255));--_et-qdt-accent: var(--et-theme-color-primary-solid, rgb(96 165 250));--_et-qdt-hover: color-mix(in srgb, var(--_et-qdt-interaction) 10%, transparent);--_et-qdt-active: color-mix(in srgb, var(--_et-qdt-interaction) 18%, transparent);--_et-qdt-success: rgb(34 197 94);--_et-qdt-error: rgb(239 68 68);--_et-qdt-loading: rgb(234 179 8);position:fixed;inset-inline:0;inset-block-end:0;z-index:2147483000;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,Liberation Mono,monospace;font-size:1.2rem;line-height:1.4;pointer-events:none}.et-query-devtools-host>*{pointer-events:auto}.et-query-devtools-panel{position:relative;display:flex;flex-direction:column;inline-size:100%;min-block-size:20rem;max-block-size:90vh;background:var(--_et-qdt-bg);color:var(--_et-qdt-fg);border-block-start:1px solid var(--_et-qdt-border);box-shadow:0 -.4rem 2rem #00000059}.et-query-devtools-panel--resizing{-webkit-user-select:none;user-select:none}.et-query-devtools-resize{position:absolute;inset-inline:0;inset-block-start:0;block-size:.6rem;cursor:ns-resize;z-index:1}.et-query-devtools-resize:after{content:\"\";position:absolute;inset-inline:50%;inset-block-start:.2rem;inline-size:4rem;margin-inline-start:-2rem;block-size:.2rem;border-radius:999px;background:var(--_et-qdt-border)}.et-query-devtools-resize:hover:after{background:var(--_et-qdt-accent)}.et-query-devtools-header{display:flex;align-items:center;justify-content:space-between;gap:.8rem;padding-inline:.8rem;border-block-end:1px solid var(--_et-qdt-border);flex:0 0 auto}.et-query-devtools-tabs{display:flex;flex-wrap:wrap;gap:.2rem}.et-query-devtools-tab{appearance:none;border:none;background:transparent;color:var(--_et-qdt-muted);padding:.9rem 1rem;cursor:pointer;border-block-end:2px solid transparent;font:inherit}.et-query-devtools-tab:hover{color:var(--_et-qdt-fg)}.et-query-devtools-tab--active{color:var(--_et-qdt-fg);border-block-end-color:var(--_et-qdt-accent)}.et-query-devtools-header-actions{display:flex;align-items:center;gap:.4rem;flex:0 0 auto}.et-query-devtools-inspect-btn{appearance:none;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:transparent;color:var(--_et-qdt-muted);cursor:pointer;padding:.4rem .8rem;font:inherit}.et-query-devtools-inspect-btn:hover{color:var(--_et-qdt-fg)}.et-query-devtools-inspect-btn--active{color:#09090b;background:var(--_et-qdt-accent);border-color:var(--_et-qdt-accent)}.et-query-devtools-close{appearance:none;border:none;background:transparent;color:var(--_et-qdt-muted);cursor:pointer;padding:.6rem;font:inherit}.et-query-devtools-inspect-box{position:fixed;z-index:2147483002;pointer-events:none;border:2px solid var(--_et-qdt-accent);background:color-mix(in srgb,var(--_et-qdt-accent) 15%,transparent);border-radius:.2rem}.et-query-devtools-inspect-tag{position:absolute;inset-block-start:100%;inset-inline-start:0;margin-block-start:.2rem;padding:.2rem .5rem;border-radius:.3rem;background:var(--_et-qdt-accent);color:#09090b;font-family:ui-monospace,monospace;font-size:1.1rem;font-weight:600;white-space:nowrap}.et-query-devtools-close:hover{color:var(--_et-qdt-fg)}.et-query-devtools-body{flex:1 1 auto;min-block-size:0;overflow:hidden}.et-query-devtools-master-detail{display:flex;block-size:100%;min-block-size:0}.et-query-devtools-list{flex:0 0 34%;min-inline-size:22rem;max-inline-size:40rem;overflow-y:auto;border-inline-end:1px solid var(--_et-qdt-border)}.et-query-devtools-detail{flex:1 1 auto;min-inline-size:0;overflow-y:auto;padding:1rem}.et-query-devtools-detail .et-query-devtools-detail-head,.et-query-devtools-drawer .et-query-devtools-detail-head{padding-block-end:.8rem;border-block-end:1px solid var(--_et-qdt-border)}.et-query-devtools-detail .et-query-devtools-meta,.et-query-devtools-drawer .et-query-devtools-meta{padding:.8rem;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:color-mix(in srgb,var(--_et-qdt-interaction) 3%,transparent)}.et-query-devtools-detail .et-query-devtools-section-row,.et-query-devtools-drawer .et-query-devtools-section-row{padding-block-start:.8rem;border-block-start:1px solid var(--_et-qdt-border)}.et-query-devtools-filter-chip{display:inline-flex;align-items:center;padding:.3rem .7rem;border-radius:999px;background:var(--_et-qdt-accent);color:#09090b;font-size:1.1rem;font-weight:600}.et-query-devtools-scroll{block-size:100%;overflow:auto;padding:1rem;display:flex;flex-direction:column;gap:1rem}.et-query-devtools-split{display:flex;block-size:100%;min-block-size:0}.et-query-devtools-split .et-query-devtools-scroll{flex:1 1 auto;min-inline-size:0}.et-query-devtools-drawer{flex:0 0 42%;min-inline-size:26rem;max-inline-size:48rem;overflow-y:auto;padding:0 1rem 1rem;border-inline-start:1px solid var(--_et-qdt-border)}.et-query-devtools-drawer-head{display:flex;align-items:center;justify-content:space-between;gap:.8rem;padding:.8rem 0;position:sticky;inset-block-start:0;background:var(--_et-qdt-bg);color:var(--_et-qdt-muted);border-block-end:1px solid var(--_et-qdt-border);margin-block-end:.8rem}.et-query-devtools-toolbar{display:flex;align-items:center;justify-content:space-between;gap:.8rem;padding:.8rem;position:sticky;inset-block-start:0;background:var(--_et-qdt-bg)}.et-query-devtools-field{display:inline-flex;align-items:center;gap:.6rem;color:var(--_et-qdt-muted)}.et-query-devtools-select{background:var(--_et-qdt-bg);color:var(--_et-qdt-fg);border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.4rem .6rem;font:inherit}.et-query-devtools-count{color:var(--_et-qdt-subtle)}.et-query-devtools-row{display:flex;align-items:center;gap:.8rem;inline-size:100%;text-align:start;appearance:none;border:none;border-block-end:1px solid var(--_et-qdt-border);background:transparent;color:var(--_et-qdt-fg);padding:.8rem;cursor:pointer;font:inherit}.et-query-devtools-row:hover{background:var(--_et-qdt-hover)}.et-query-devtools-row--active{background:var(--_et-qdt-active)}.et-query-devtools-method{font-weight:700;font-size:1.1rem;color:var(--_et-qdt-muted);white-space:nowrap}.et-query-devtools-route{overflow:hidden;text-overflow:ellipsis;white-space:nowrap;flex:1 1 auto;min-inline-size:0}.et-query-devtools-status{inline-size:.8rem;block-size:.8rem;border-radius:999px;flex:0 0 auto;background:var(--_et-qdt-subtle)}.et-query-devtools-status[data-status=success]{background:var(--_et-qdt-success)}.et-query-devtools-status[data-status=error]{background:var(--_et-qdt-error)}.et-query-devtools-status[data-status=loading],.et-query-devtools-status[data-status=running]{background:var(--_et-qdt-loading)}.et-query-devtools-detail-head{display:flex;align-items:center;gap:.8rem;margin-block-end:.8rem}.et-query-devtools-actions{display:flex;flex-wrap:wrap;align-items:center;gap:.35rem;margin-block-end:.8rem}.et-query-devtools-btn{appearance:none;border:1px solid var(--_et-qdt-border);border-radius:.3rem;background:transparent;color:var(--_et-qdt-fg);padding:.25rem .55rem;font-size:1.15rem;line-height:1.4;cursor:pointer}.et-query-devtools-btn:hover{background:var(--_et-qdt-hover)}.et-query-devtools-meta{display:grid;grid-template-columns:auto 1fr;gap:.3rem 1rem;margin:0 0 1rem}.et-query-devtools-meta dt{color:var(--_et-qdt-muted)}.et-query-devtools-meta dd{margin:0;overflow-wrap:anywhere}.et-query-devtools-section{margin:1rem 0 .4rem;font-size:1.1rem;text-transform:uppercase;letter-spacing:.05em;color:var(--_et-qdt-muted)}.et-query-devtools-json{margin:0;padding:.8rem;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:color-mix(in srgb,var(--_et-qdt-interaction) 4%,transparent);overflow-x:auto;white-space:pre-wrap;overflow-wrap:anywhere;max-block-size:24rem;overflow-y:auto}.et-query-devtools-json--error{border-color:color-mix(in srgb,var(--_et-qdt-error) 50%,transparent)}.et-query-devtools-mono{font-variant-numeric:tabular-nums;overflow-wrap:anywhere}.et-query-devtools-code{margin:0 0 .8rem;padding:.8rem;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:color-mix(in srgb,var(--_et-qdt-interaction) 4%,transparent);overflow:auto;white-space:pre;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;font-size:1.15rem;max-block-size:20rem}.et-query-devtools-ws-message{border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.6rem;margin-block-end:.4rem}.et-query-devtools-url{display:inline-block;max-inline-size:32rem;margin-inline-start:.6rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;vertical-align:bottom;font-family:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace}.et-query-devtools-chips,.et-query-devtools-chip-row{display:flex;flex-wrap:wrap;gap:.4rem;margin-block-end:.8rem}.et-query-devtools-chip{display:inline-flex;align-items:center;gap:.3rem;padding:.2rem .6rem;border-radius:999px;border:1px solid var(--_et-qdt-border);font-size:1.1rem;color:var(--_et-qdt-fg);background:color-mix(in srgb,var(--_et-qdt-interaction) 6%,transparent)}.et-query-devtools-chip--muted{color:var(--_et-qdt-muted)}.et-query-devtools-chip--loading{color:var(--_et-qdt-loading);border-color:color-mix(in srgb,var(--_et-qdt-loading) 50%,transparent)}.et-query-devtools-chip--error{color:var(--_et-qdt-error);border-color:color-mix(in srgb,var(--_et-qdt-error) 50%,transparent)}.et-query-devtools-chip--success{color:var(--_et-qdt-success);border-color:color-mix(in srgb,var(--_et-qdt-success) 50%,transparent)}.et-query-devtools-card{border:1px solid var(--_et-qdt-border);border-radius:.6rem;padding:1rem}.et-query-devtools-card-head{display:flex;align-items:center;gap:.6rem;margin-block-end:.8rem}.et-query-devtools-card-title{display:flex;align-items:baseline;gap:.5rem;margin-block-end:.2rem}.et-query-devtools-card-sub{color:var(--_et-qdt-subtle);font-size:1.1rem;margin-block-end:.6rem;overflow-wrap:anywhere}.et-query-devtools-inner-queries{display:flex;flex-direction:column;gap:.3rem}.et-query-devtools-inner-row{display:flex;align-items:center;gap:.6rem;inline-size:100%;text-align:start;appearance:none;border:1px solid var(--_et-qdt-border);border-radius:.4rem;background:transparent;color:var(--_et-qdt-fg);padding:.4rem .6rem;cursor:pointer;font:inherit}.et-query-devtools-inner-row:hover:not([disabled]){background:var(--_et-qdt-hover)}.et-query-devtools-inner-row--active{background:var(--_et-qdt-active);border-color:var(--_et-qdt-accent)}.et-query-devtools-inner-row[disabled]{cursor:default;opacity:.6}.et-query-devtools-step-list{display:flex;flex-direction:column;gap:.4rem;margin:0;padding:0;list-style:none}.et-query-devtools-step-item{border:1px solid var(--_et-qdt-border);border-radius:.4rem;overflow:hidden}.et-query-devtools-step-item[data-status=error]{border-color:color-mix(in srgb,var(--_et-qdt-error) 50%,transparent)}.et-query-devtools-step-head{display:flex;align-items:stretch}.et-query-devtools-step-head .et-query-devtools-inner-row{border:none;border-radius:0;flex:1 1 auto}.et-query-devtools-step-caret-btn{appearance:none;border:none;border-inline-start:1px solid var(--_et-qdt-border);background:transparent;color:var(--_et-qdt-muted);cursor:pointer;padding:0 .7rem;font:inherit}.et-query-devtools-step-caret-btn:hover{background:var(--_et-qdt-hover);color:var(--_et-qdt-fg)}.et-query-devtools-step-toggle{display:flex;align-items:center;gap:.6rem;inline-size:100%;text-align:start;appearance:none;border:none;background:transparent;color:var(--_et-qdt-fg);padding:.6rem;cursor:pointer;font:inherit}.et-query-devtools-step-toggle:hover{background:var(--_et-qdt-hover)}.et-query-devtools-step-index{flex:1 1 auto;min-inline-size:0}.et-query-devtools-step-caret{color:var(--_et-qdt-muted)}.et-query-devtools-step-io{padding:0 .8rem .8rem;border-block-start:1px solid var(--_et-qdt-border)}.et-query-devtools-table{inline-size:100%;border-collapse:collapse}.et-query-devtools-table th,.et-query-devtools-table td{text-align:start;padding:.5rem .6rem;border-block-end:1px solid var(--_et-qdt-border);vertical-align:top}.et-query-devtools-table th{color:var(--_et-qdt-muted);font-weight:600;position:sticky;inset-block-start:0;background:var(--_et-qdt-bg)}.et-query-devtools-table tr[data-status=error] td{color:var(--_et-qdt-error)}.et-query-devtools-empty{color:var(--_et-qdt-subtle);padding:1.2rem;text-align:center}.et-query-devtools-actions-label{color:var(--_et-qdt-subtle);align-self:center;text-transform:uppercase;font-size:1rem;letter-spacing:.05em}.et-query-devtools-actions-label:not(:first-child){margin-inline-start:.7rem}.et-query-devtools-cell-actions{display:flex;gap:.4rem;white-space:nowrap}.et-query-devtools-section-row{display:flex;align-items:center;justify-content:space-between;gap:.8rem;margin-block-start:1rem}.et-query-devtools-search{flex:0 1 20rem;background:var(--_et-qdt-bg);color:var(--_et-qdt-fg);border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.4rem .6rem;font:inherit}.et-query-devtools-editor{border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.8rem;margin-block-end:1rem}.et-query-devtools-textarea{inline-size:100%;min-block-size:12rem;resize:vertical;background:color-mix(in srgb,var(--_et-qdt-interaction) 4%,transparent);color:var(--_et-qdt-fg);border:1px solid var(--_et-qdt-border);border-radius:.4rem;padding:.6rem;font-family:inherit;font-size:1.2rem}.et-query-devtools-editor-error{color:var(--_et-qdt-error);margin:.4rem 0 0}.et-query-devtools-json-node,.et-query-devtools-json-children{display:flex;flex-direction:column}.et-query-devtools-json-children{padding-inline-start:1.4rem;border-inline-start:1px solid var(--_et-qdt-border);margin-inline-start:.4rem}.et-query-devtools-json-row{display:flex;align-items:baseline;gap:.4rem;padding:.1rem 0;font-family:inherit;line-height:1.5}.et-query-devtools-json-toggle{appearance:none;border:none;background:transparent;color:var(--_et-qdt-fg);cursor:pointer;text-align:start;font:inherit;padding:.1rem 0}.et-query-devtools-json-toggle:hover{background:var(--_et-qdt-hover)}.et-query-devtools-json-caret{color:var(--_et-qdt-subtle);inline-size:1rem;flex:0 0 auto}.et-query-devtools-json-key{color:var(--_et-qdt-accent)}.et-query-devtools-json-colon,.et-query-devtools-json-preview{color:var(--_et-qdt-subtle)}.et-query-devtools-json-value{overflow-wrap:anywhere}.et-query-devtools-json-leaf[data-kind=string] .et-query-devtools-json-value{color:var(--_et-qdt-success)}.et-query-devtools-json-leaf[data-kind=number] .et-query-devtools-json-value,.et-query-devtools-json-leaf[data-kind=boolean] .et-query-devtools-json-value{color:var(--_et-qdt-loading)}.et-query-devtools-json-leaf[data-kind=null] .et-query-devtools-json-value,.et-query-devtools-json-leaf[data-kind=undefined] .et-query-devtools-json-value{color:var(--_et-qdt-subtle)}.et-query-devtools-json-hit{background:color-mix(in srgb,var(--_et-qdt-loading) 40%,transparent);border-radius:.2rem}.et-query-devtools-json-copy{appearance:none;border:none;background:transparent;color:var(--_et-qdt-subtle);cursor:pointer;opacity:0;font:inherit}.et-query-devtools-json-row:hover .et-query-devtools-json-copy{opacity:1}}\n"] }]
|
|
30921
|
+
}], ctorParameters: () => [] });
|
|
30922
|
+
|
|
30923
|
+
const QUERY_DEVTOOLS_IMPORTS = [QueryDevtoolsComponent];
|
|
30924
|
+
|
|
29940
30925
|
// codes 2100-2199
|
|
29941
30926
|
const SCROLLABLE_ERROR_CODES = {
|
|
29942
30927
|
MISSING_SCROLL_CONTAINER: 2100,
|
|
@@ -36757,5 +37742,5 @@ const TOOLTIP_IMPORTS = [TooltipDirective, TooltipComponent];
|
|
|
36757
37742
|
* Generated bundle index. Do not edit.
|
|
36758
37743
|
*/
|
|
36759
37744
|
|
|
36760
|
-
export { ALIGN_CENTER_ICON, ALIGN_JUSTIFY_ICON, ALIGN_LEFT_ICON, ALIGN_RIGHT_ICON, ARROW_OUT_UP_RIGHT_ICON, ARROW_RIGHT_ICON, BOLD_ICON, BUTTON_ICON_ALIGNMENTS, BUTTON_IMPORTS, BUTTON_SIZES, BUTTON_SPINNER_CONFIG, BUTTON_TYPES, BUTTON_VARIANTS, BrandLoaderComponent, ButtonComponent, ButtonDirective, ButtonStylesDirective, CALENDAR_ERROR_CODES, CALENDAR_ICON, CALENDAR_IMPORTS, CASCADER_ERROR_CODES, CASCADER_IMPORTS, CASCADER_SELECTABLE_LEVELS, CHECKBOX_IMPORTS, CHECK_ICON, CHEVRON_ICON, CHIP_ERROR_CODES, CHIP_IMPORTS, CHOICE_FIELD_IMPORTS, CLIPBOARD_CHECK_ICON, CLOCK_ICON, CODE_ICON, COLOR_INPUT_IMPORTS, CalendarCellDirective, CalendarComponent, CalendarDirective, CalendarGridDirective, CascaderColumnDirective, CascaderComponent, CascaderDirective, CascaderNodeDirective, CascaderPanelComponent, CascaderSearchDirective, CascaderSearchOptionDirective, CascaderSurfaceDirective, CascaderTriggerDirective, CheckboxComponent, CheckboxDirective, CheckboxGroupComponent, CheckboxOptionComponent, ChipComponent, ChipDirective, ChipRemoveDirective, ChoiceFieldComponent, ColorInputComponent, ColorInputDirective, DAILYMOTION_PLAYER_TOKEN, DATE_FORMAT, DATE_INPUT_ERROR_CODES, DATE_INPUT_IMPORTS, DATE_LOCALE, DATE_PICKER_HOST, DATE_RANGE_INPUT_ERROR_CODES, DATE_RANGE_INPUT_IMPORTS, DATE_TIME_INPUT_ERROR_CODES, DATE_TIME_INPUT_IMPORTS, DEFAULT_BREAKPOINTS, DEFAULT_ICON_VARIANT, DEFAULT_NOTIFICATION_MANAGER_CONFIG, DEFAULT_PIP_WINDOW_CONFIG, DEFAULT_RICH_TEXT_EDITOR_TOOLS, DEFAULT_STREAM_PLAYER_STATE, DROPZONE_ENTRY_STATUSES, DROPZONE_ERROR_CODES, DROPZONE_FILES_ERROR_KIND, DROPZONE_FILE_CONSTRAINTS, DROPZONE_FILE_REJECTION_REASONS, DROPZONE_IMPORTS, DURATION_INPUT_ERROR_CODES, DURATION_INPUT_IMPORTS, DailymotionPlayerComponent, DailymotionPlayerDirective, DailymotionPlayerParamsDirective, DailymotionPlayerSlotComponent, DateInputComponent, DateInputDirective, DateInputFieldDirective, DatePickerPanelComponent, DatePickerSurfaceDirective, DatePickerTriggerDirective, DateRangeInputComponent, DateRangeInputDirective, DateRangeInputFieldDirective, DateTimeInputComponent, DateTimeInputDirective, DateTimeInputFieldDirective, DescriptionComponent, DropzoneComponent, DropzoneDirective, DurationInputComponent, DurationInputDirective, DurationInputFieldDirective, ET_BUILT_IN_ICON_NAMES, EYE_ICON, EYE_SLASH_ICON, FACEBOOK_PLAYER_TOKEN, FILE_ICON, FLOPPY_DISK_ICON, FOCUS_FRAME_ICON, FORM_ERROR_MESSAGE_RESOLVER, FORM_FIELD_APPEARANCES, FORM_FIELD_CONTROL_TYPES, FORM_FIELD_ERROR_CODES, FORM_FIELD_FILLS, FORM_FIELD_IMPORTS, FORM_FIELD_LABEL_MODES, FORM_FIELD_SIZES, FORM_FIELD_TOKEN, FabComponent, FacebookPlayerComponent, FacebookPlayerDirective, FacebookPlayerParamsDirective, FacebookPlayerSlotComponent, FocusRingDirective, FormErrorComponent, FormFieldComponent, FormFieldDirective, GRID_2X2_ICON, GRID_ERROR_CODES, GRID_IMPORTS, GRID_TOKEN, GridComponent, GridDebugComponent, GridDirective, GridDragDirective, GridItemComponent, GridItemDefaultActionsComponent, GridItemDirective, GridItemRef, GridItemToolbarComponent, GridResizeDirective, HEADING_1_ICON, HEADING_2_ICON, HEADING_3_ICON, HintComponent, ICONS_TOKEN, ICON_DIRECTIVE_TOKEN, ICON_ERROR_CODES, ICON_IMPORTS, ICON_OVERRIDES_TOKEN, INITIAL_SUPPORT_PRESENTATION_STATE, INPUT_IMPORTS, INPUT_MASK_HOST, INPUT_TEXT_ALIGNMENTS, INPUT_TYPES, INTERACTIVE_TAGS, ITALIC_ICON, IconButtonComponent, IconDirective, InputComponent, InputDirective, InputMaskDirective, InputPrefixDirective, InputSuffixDirective, KICK_PLAYER_TOKEN, KickPlayerComponent, KickPlayerDirective, KickPlayerParamsDirective, KickPlayerSlotComponent, LINK_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LOCK_ICON, LabelDirective, MASKED_INPUT_ERROR_CODES, MASKED_INPUT_IMPORTS, MASK_VALUE_MODES, MENU_ERROR_CODES, MENU_IMPORTS, MENU_ITEM_VARIANTS, MENU_SELECTION_GROUP_MULTIPLE, MENU_SELECTION_GROUP_TOKEN, MENU_SELECTION_ITEM_KIND, MINUS_ICON, MULTI_LANGUAGE_RICH_TEXT_EDITOR_ERROR_CODES, MULTI_LANGUAGE_RICH_TEXT_EDITOR_IMPORTS, MenuCheckboxGroupComponent, MenuCheckboxItemComponent, MenuComponent, MenuContextTriggerDirective, MenuDirective, MenuGroupLabelComponent, MenuItemComponent, MenuItemDirective, MenuItemShortcutComponent, MenuPanelDirective, MenuRadioGroupComponent, MenuRadioItemComponent, MenuSearchDirective, MenuSelectionGroupDirective, MenuSelectionItemDirective, MenuSeparatorComponent, MenuSurfaceDirective, MenuTriggerDirective, MultiLanguageRichTextEditorComponent, MultiLanguageRichTextEditorDirective, MultiLanguageRichTextEditorLanguageToolComponent, NAV_TABS_TOKEN, NAV_TAB_IMPORTS, NOTIFICATION_ERROR_CODES, NOTIFICATION_IMPORTS, NOTIFICATION_STACK_CONTEXT_TOKEN, NOTIFICATION_STATUS, NUMBER_INPUT_IMPORTS, NavTabLinkComponent, NavTabLinkDirective, NavTabsComponent, NavTabsDirective, NavTabsOutletComponent, NavTabsOutletDirective, NotificationActionDirective, NotificationComponent, NotificationDirective, NotificationDismissDirective, NotificationItemDirective, NotificationStackDirective, NumberInputComponent, NumberInputDirective, OTP_INPUT_IMPORTS, OVERLAY_BACK_OR_CLOSE_TOKEN, OVERLAY_BODY_TOKEN, OVERLAY_CONFIG_CLASS_KEYS, OVERLAY_CONTENT_IMPORTS, OVERLAY_ERROR_CODES, OVERLAY_FOOTER_TOKEN, OVERLAY_HEADER_TEMPLATE_TOKEN, OVERLAY_HEADER_TOKEN, OVERLAY_IMPORTS, OVERLAY_MAIN_TOKEN, OVERLAY_QUERY_PARAM_INPUT_NAME, OVERLAY_REF, OVERLAY_ROUTER_CONFIG_TOKEN, OVERLAY_ROUTER_LINK_TOKEN, OVERLAY_ROUTER_OUTLET_DISABLED_TEMPLATE_TOKEN, OVERLAY_ROUTER_OUTLET_TOKEN, OVERLAY_ROUTER_TOKEN, OVERLAY_SHARED_ROUTE_TEMPLATE_TOKEN, OtpInputComponent, OtpInputDirective, OverlayAnchorDirective, OverlayBackOrCloseDirective, OverlayBodyComponent, OverlayCloseDirective, OverlayContainerComponent, OverlayDirective, OverlayFooterDirective, OverlayHeaderDirective, OverlayHeaderTemplateDirective, OverlayMainDirective, OverlayOriginCloneComponent, OverlayRouteHeaderTemplateOutletComponent, OverlayRouterLinkDirective, OverlayRouterOutletComponent, OverlayRouterOutletDisabledTemplateDirective, OverlaySharedRouteTemplateDirective, OverlaySharedRouteTemplateOutletComponent, OverlaySidebarComponent, OverlaySidebarPageComponent, OverlaySurfaceDirective, OverlayTitleDirective, OverlayTriggerDirective, PARAGRAPH_ICON, PASSWORD_INPUT_IMPORTS, PENCIL_ICON, PHONE_COUNTRIES, PHONE_INPUT_ERROR_CODES, PHONE_INPUT_IMPORTS, PIP_CHROME_REF_TOKEN, PIP_ENTRY_TOKEN, PIP_WINDOW_ASPECT_RATIO_TOKEN, PLUS_ICON, PasswordInputComponent, PasswordInputDirective, PhoneInputComponent, PhoneInputDirective, PhoneInputFieldDirective, PhoneInputFlagDirective, PipBackDirective, PipBringBackDirective, PipCellDirective, PipCloseDirective, PipCollapseOverlayDirective, PipGridToggleDirective, PipPlayerComponent, PipSlotPlaceholderComponent, PipStageDirective, PipTitleBarDirective, PipTitleBarTemplateDirective, PipWindowComponent, PipWindowParamsDirective, ProgressBarComponent, QueryParamOverlayLinkDirective, RATING_IMPORTS, RICH_TEXT_EDITOR_HEADING_OPTIONS, RICH_TEXT_EDITOR_IMPORTS, RICH_TEXT_EDITOR_INLINE_TOOLS, RICH_TEXT_EDITOR_LANGUAGE_TOOL, RICH_TEXT_EDITOR_TOKEN_CODEC, RICH_TEXT_EDITOR_TOKEN_PALETTE_IMPORTS, RICH_TEXT_EDITOR_TOOL, RICH_TEXT_EDITOR_TOOLS, RICH_TEXT_EDITOR_TOOL_BUTTONS, RICH_TEXT_EDITOR_TRIGGERS_IMPORTS, ROTATE_RIGHT_ICON, RadioComponent, RadioGroupComponent, RangeSliderComponent, RangeSliderDirective, RatingComponent, RatingDirective, RatingIconDirective, RichTextEditorAlignToolComponent, RichTextEditorComponent, RichTextEditorDirective, RichTextEditorFloatingToolbarComponent, RichTextEditorFloatingToolbarDirective, RichTextEditorLinkEditorComponent, RichTextEditorLinkEditorDirective, RichTextEditorTableToolComponent, RichTextEditorTokenPaletteComponent, RichTextEditorTokenPopupComponent, RichTextEditorTriggersDirective, SCROLLABLE_ERROR_CODES, SCROLLABLE_IMPORTS, SELECTION_LIST_MULTIPLE, SELECTION_LIST_TOKEN, SELECT_ERROR_CODES, SELECT_FILTER_MODES, SELECT_IMPORTS, SIDEBAR_OVERLAY_CONFIG, SIDEBAR_OVERLAY_TOKEN, SLIDER_ERROR_CODES, SLIDER_IMPORTS, SLIDER_TOKEN, SNAP_HYSTERESIS, SOOP_PLAYER_TOKEN, SPLIT_BUTTON_ERROR_CODES, STAR_ICON, STREAM_CONSENT_TOKEN, STREAM_IMPORTS, STREAM_PLAYER_COMPONENT_TOKEN, STREAM_PLAYER_ERROR_CONTEXT_TOKEN, STREAM_PLAYER_ERROR_TOKEN, STREAM_PLAYER_PARAMS_TOKEN, STREAM_PLAYER_SLOT_TOKEN, STREAM_PLAYER_TOKEN, STREAM_SLOT_PLAYER_ID_TOKEN, STREAM_USER_CONSENT_PROVIDER_TOKEN, STRIKETHROUGH_ICON, SUPPORT_CONTENT_STATE, SUPPORT_TRANSITION_DIRECTION, SWITCH_IMPORTS, ScrollableActiveChildDirective, ScrollableButtonsDirective, ScrollableComponent, ScrollableDarkenDirective, ScrollableDirective, ScrollableDragDirective, ScrollableIgnoreChildDirective, ScrollableLoadingTemplateDirective, ScrollableMasksDirective, ScrollableNavigationDirective, ScrollableSnapDirective, SegmentedButtonComponent, SegmentedButtonGroupComponent, SelectComponent, SelectDirective, SelectEmptyDirective, SelectErrorDirective, SelectListboxDirective, SelectLoadingDirective, SelectOptionComponent, SelectOptionDirective, SelectOptionGroupComponent, SelectOptionGroupDirective, SelectOptionTemplateDirective, SelectOptionsDirective, SelectPanelComponent, SelectSearchDirective, SelectSurfaceDirective, SelectTriggerDirective, SelectValueDirective, SelectViewportDirective, SelectVirtualOptionComponent, SelectVirtualOptionDirective, SelectionListControlDirective, SelectionListDirective, SelectionOptionDirective, SliderComponent, SliderDirective, SliderThumbDirective, SliderThumbLabelDirective, SliderTrackDirective, SoopPlayerComponent, SoopPlayerDirective, SoopPlayerParamsDirective, SoopPlayerSlotComponent, SpinnerComponent, SplitButtonActionDirective, SplitButtonComponent, SplitButtonDirective, SplitButtonTriggerDirective, StreamConsentAcceptDirective, StreamConsentComponent, StreamConsentDirective, StreamPipChromeComponent, StreamPlayerErrorComponent, StreamPlayerErrorDirective, StreamPlayerLoadingComponent, StreamPlayerSlotDirective, SwitchComponent, SwitchDirective, TABLE_ICON, TAB_BAR_FITS, TAB_BAR_ORIENTATIONS, TAB_BAR_TOKEN, TAB_BAR_TRIGGER_TOKEN, TAB_BAR_VARIANTS, TAB_ERROR_CODES, TAB_GROUP_TOKEN, TAB_IMPORTS, TAB_PANEL_TOKEN, TAB_SIZES, TAG_INPUT_ERROR_CODES, TAG_INPUT_IMPORTS, TEXTAREA_IMPORTS, TEXTAREA_RESIZE_MODES, TEXT_ALIGNS, TIKTOK_PLAYER_TOKEN, TIMES_ICON, TIME_FORMAT, TIME_INPUT_ERROR_CODES, TIME_INPUT_IMPORTS, TIME_PICKER_ERROR_CODES, TIME_PICKER_IMPORTS, TOGGLETIP_ERROR_CODES, TOGGLETIP_IMPORTS, TOOLTIP_ERROR_CODES, TOOLTIP_IMPORTS, TRIANGLE_EXCLAMATION_ICON, TWITCH_PLAYER_TOKEN, TabBarDirective, TabBarTriggerDirective, TabBarUnderlineDirective, TabComponent, TabGroupComponent, TabGroupDirective, TabLabelDirective, TabPanelDirective, TabTriggerDirective, TagInputComponent, TagInputDirective, TagInputFieldDirective, TextButtonComponent, TextFieldControlDirective, TextareaComponent, TextareaDirective, TikTokPlayerComponent, TikTokPlayerDirective, TikTokPlayerParamsDirective, TikTokPlayerSlotComponent, TimeInputComponent, TimeInputDirective, TimeInputFieldDirective, TimePickerColumnDirective, TimePickerComponent, TimePickerDirective, TimePickerOptionDirective, ToggletipCloseDirective, ToggletipComponent, ToggletipDirective, ToggletipTriggerDirective, TooltipComponent, TooltipDirective, TwitchPlayerComponent, TwitchPlayerDirective, TwitchPlayerParamsDirective, TwitchPlayerSlotComponent, UNDERLINE_ICON, UNIT_MS, UPLOAD_ICON, VIMEO_PLAYER_TOKEN, VimeoPlayerComponent, VimeoPlayerDirective, VimeoPlayerParamsDirective, VimeoPlayerSlotComponent, WINDOW_CONTROL_BUTTON_KINDS, WINDOW_CONTROL_BUTTON_SIZES, WindowControlButtonComponent, YOUTUBE_PLAYER_SLOT_TOKEN, YOUTUBE_PLAYER_TOKEN, YoutubePlayerComponent, YoutubePlayerDirective, YoutubePlayerParamsDirective, YoutubePlayerSlotComponent, YoutubePlayerSlotDirective, abortFullscreenAnimation, anchoredDialogOverlayStrategy, anchoredOverlayStrategy, autoPlace, bottomSheetOverlayStrategy, buildAnchoredRuntimePositionStrategy, canHaveChildren, cascaderFromQuery, centeredOverlayStrategy, clampPosition, clampResizeRect, cleanupFullscreenAnimation, cleanupFullscreenAnimationStyles, compactLayout, computeGeometry, computeGridHeight, createAnchoredPanelController, createAutoScroller, createCardMask, createCurrencyMask, createDefaultDropzoneArgs, createDropzoneUpload, createExistingDropzoneEntry, createFileDropzoneEntry, createGridAdapter, createIbanMask, createNotificationRef, createOverlayOpener, createOverlayRef, createOverlayStrategyController, createOverlayUnsavedChangesGuard, createPipChromeAnimations, createPipChromeState, createRichTextEditorTrigger, createRichTextEditorTriggerWithQuery, createStreamConfig, createStreamPlayerSlot, createV2DropzoneUpload, defaultCompareWith, defaultDropzoneRejectionMessage, defineOverlay, defineQueryParamOverlay, deriveDurationFormatSpec, deserializeGridLayout, dialogOverlayStrategy, disposeDropzoneEntry, dropzoneFiles, enableDragToDismiss, findCollision, findNextRelevantHtmlElement, findScrollableAncestor, formatDuration, formatFileSize, fromGridPosition, fullScreenDialogOverlayStrategy, getClosestOverlay, getOriginCoordinatesAndDimensions, hysteresisRound, iconRegistryKey, indexOfNode, injectAnchoredDialogStrategy, injectAnchoredDialogStrategyDefaults, injectBottomSheetStrategy, injectBottomSheetStrategyDefaults, injectDateFormat, injectDateLocale, injectDialogStrategy, injectDialogStrategyDefaults, injectFormSupport, injectFullscreenDialogStrategy, injectFullscreenDialogStrategyDefaults, injectGridConfig, injectLeftSheetStrategy, injectLeftSheetStrategyDefaults, injectNotificationManager, injectNotificationManagerConfig, injectOverlayManager, injectOverlayRouter, injectOverlayScrollBlocker, injectOverlaySurfaceContext, injectPipChromeManager, injectPipManager, injectPipSlotPlaceholderConfig, injectRichTextEditorTools, injectRightSheetStrategy, injectRightSheetStrategyDefaults, injectSidebarOverlay, injectStreamConfig, injectStreamConsentConfig, injectStreamManager, injectStreamPlayerErrorConfig, injectStreamPlayerLoadingConfig, injectStreamScriptLoader, injectStreamUserConsentProvider, injectTimeFormat, injectTopSheetStrategy, injectTopSheetStrategyDefaults, isFileAccepted, isHtmlElement, isInteractiveElement, isPointerEvent, isTargetInsideOverlayTree, isTouchEvent, itemsCollide, leftSheetOverlayStrategy, mapLayoutToBreakpoint, matchCountryByDialCode, mergeOverlayBreakpointConfigs, mergeOverlayConfigs, nodesEqual, parseDuration, phoneCountryFlag, phoneCountryName, pixelRectsEqual, positionToPixelRect, positionsEqual, projectDragCell, provideAnchoredDialogStrategy, provideAnchoredDialogStrategyDefaults, provideBottomSheetStrategy, provideBottomSheetStrategyDefaults, provideDateFormat, provideDateLocale, provideDialogStrategy, provideDialogStrategyDefaults, provideFormErrorMessageResolver, provideFormSupport, provideFullscreenDialogStrategy, provideFullscreenDialogStrategyDefaults, provideGridConfig, provideIconOverrides, provideIcons, provideLeftSheetStrategy, provideLeftSheetStrategyDefaults, provideNotificationManager, provideNotificationManagerConfig, provideNotificationManagerInstance, provideOverlay, provideOverlayManager, provideOverlayRouter, provideOverlayRouterConfig, provideOverlayRouterService, provideOverlayScrollBlocker, providePipChromeManager, providePipManager, providePipSlotPlaceholderConfig, provideRichTextEditorAlignmentTool, provideRichTextEditorLanguageTool, provideRichTextEditorTableTool, provideRichTextEditorTokenRendering, provideRichTextEditorTools, provideRightSheetStrategy, provideRightSheetStrategyDefaults, provideSidebarOverlay, provideSidebarOverlayConfig, provideSidebarOverlayService, provideStreamConfig, provideStreamConsentConfig, provideStreamManager, provideStreamPlayerErrorConfig, provideStreamPlayerLoadingConfig, provideTimeFormat, provideTopSheetStrategy, provideTopSheetStrategyDefaults, reduceSupportPresentation, registerSingleton, requiredLanguages, resizeSpanBounds, resolveBreakpoint, resolveClosestOverlay, resolveCollisions, rightSheetOverlayStrategy, rowsToPixelHeight, selectOptionsFromQuery, selectOptionsFromV2Query, serializeGridLayout, snapResizeSpan, spanHeight, spanWidth, startFullscreenEnterAnimation, startFullscreenLeaveAnimation, stripTrunkZero, supportPresentationIncludesState, toChildrenObservable, toGridPosition, toPathObservable, toSearchObservable, topSheetOverlayStrategy, transformingBottomSheetToDialogOverlayStrategy, transformingFullScreenDialogToDialogOverlayStrategy, transformingFullScreenDialogToRightSheetOverlayStrategy, wireFormSupport };
|
|
37745
|
+
export { ALIGN_CENTER_ICON, ALIGN_JUSTIFY_ICON, ALIGN_LEFT_ICON, ALIGN_RIGHT_ICON, ARROW_OUT_UP_RIGHT_ICON, ARROW_RIGHT_ICON, BOLD_ICON, BUTTON_ICON_ALIGNMENTS, BUTTON_IMPORTS, BUTTON_SIZES, BUTTON_SPINNER_CONFIG, BUTTON_TYPES, BUTTON_VARIANTS, BrandLoaderComponent, ButtonComponent, ButtonDirective, ButtonStylesDirective, CALENDAR_ERROR_CODES, CALENDAR_ICON, CALENDAR_IMPORTS, CASCADER_ERROR_CODES, CASCADER_IMPORTS, CASCADER_SELECTABLE_LEVELS, CHECKBOX_IMPORTS, CHECK_ICON, CHEVRON_ICON, CHIP_ERROR_CODES, CHIP_IMPORTS, CHOICE_FIELD_IMPORTS, CLIPBOARD_CHECK_ICON, CLOCK_ICON, CODE_ICON, COLOR_INPUT_IMPORTS, CalendarCellDirective, CalendarComponent, CalendarDirective, CalendarGridDirective, CascaderColumnDirective, CascaderComponent, CascaderDirective, CascaderNodeDirective, CascaderPanelComponent, CascaderSearchDirective, CascaderSearchOptionDirective, CascaderSurfaceDirective, CascaderTriggerDirective, CheckboxComponent, CheckboxDirective, CheckboxGroupComponent, CheckboxOptionComponent, ChipComponent, ChipDirective, ChipRemoveDirective, ChoiceFieldComponent, ColorInputComponent, ColorInputDirective, DAILYMOTION_PLAYER_TOKEN, DATE_FORMAT, DATE_INPUT_ERROR_CODES, DATE_INPUT_IMPORTS, DATE_LOCALE, DATE_PICKER_HOST, DATE_RANGE_INPUT_ERROR_CODES, DATE_RANGE_INPUT_IMPORTS, DATE_TIME_INPUT_ERROR_CODES, DATE_TIME_INPUT_IMPORTS, DEFAULT_BREAKPOINTS, DEFAULT_ICON_VARIANT, DEFAULT_NOTIFICATION_MANAGER_CONFIG, DEFAULT_PIP_WINDOW_CONFIG, DEFAULT_RICH_TEXT_EDITOR_TOOLS, DEFAULT_STREAM_PLAYER_STATE, DROPZONE_ENTRY_STATUSES, DROPZONE_ERROR_CODES, DROPZONE_FILES_ERROR_KIND, DROPZONE_FILE_CONSTRAINTS, DROPZONE_FILE_REJECTION_REASONS, DROPZONE_IMPORTS, DURATION_INPUT_ERROR_CODES, DURATION_INPUT_IMPORTS, DailymotionPlayerComponent, DailymotionPlayerDirective, DailymotionPlayerParamsDirective, DailymotionPlayerSlotComponent, DateInputComponent, DateInputDirective, DateInputFieldDirective, DatePickerPanelComponent, DatePickerSurfaceDirective, DatePickerTriggerDirective, DateRangeInputComponent, DateRangeInputDirective, DateRangeInputFieldDirective, DateTimeInputComponent, DateTimeInputDirective, DateTimeInputFieldDirective, DescriptionComponent, DropzoneComponent, DropzoneDirective, DurationInputComponent, DurationInputDirective, DurationInputFieldDirective, ET_BUILT_IN_ICON_NAMES, EYE_ICON, EYE_SLASH_ICON, FACEBOOK_PLAYER_TOKEN, FILE_ICON, FLOPPY_DISK_ICON, FOCUS_FRAME_ICON, FORM_ERROR_MESSAGE_RESOLVER, FORM_FIELD_APPEARANCES, FORM_FIELD_CONTROL_TYPES, FORM_FIELD_ERROR_CODES, FORM_FIELD_FILLS, FORM_FIELD_IMPORTS, FORM_FIELD_LABEL_MODES, FORM_FIELD_SIZES, FORM_FIELD_TOKEN, FabComponent, FacebookPlayerComponent, FacebookPlayerDirective, FacebookPlayerParamsDirective, FacebookPlayerSlotComponent, FocusRingDirective, FormErrorComponent, FormFieldComponent, FormFieldDirective, GRID_2X2_ICON, GRID_ERROR_CODES, GRID_IMPORTS, GRID_TOKEN, GridComponent, GridDebugComponent, GridDirective, GridDragDirective, GridItemComponent, GridItemDefaultActionsComponent, GridItemDirective, GridItemRef, GridItemToolbarComponent, GridResizeDirective, HEADING_1_ICON, HEADING_2_ICON, HEADING_3_ICON, HintComponent, ICONS_TOKEN, ICON_DIRECTIVE_TOKEN, ICON_ERROR_CODES, ICON_IMPORTS, ICON_OVERRIDES_TOKEN, INITIAL_SUPPORT_PRESENTATION_STATE, INPUT_IMPORTS, INPUT_MASK_HOST, INPUT_TEXT_ALIGNMENTS, INPUT_TYPES, INTERACTIVE_TAGS, ITALIC_ICON, IconButtonComponent, IconDirective, InputComponent, InputDirective, InputMaskDirective, InputPrefixDirective, InputSuffixDirective, KICK_PLAYER_TOKEN, KickPlayerComponent, KickPlayerDirective, KickPlayerParamsDirective, KickPlayerSlotComponent, LINK_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LOCK_ICON, LabelDirective, MASKED_INPUT_ERROR_CODES, MASKED_INPUT_IMPORTS, MASK_VALUE_MODES, MENU_ERROR_CODES, MENU_IMPORTS, MENU_ITEM_VARIANTS, MENU_SELECTION_GROUP_MULTIPLE, MENU_SELECTION_GROUP_TOKEN, MENU_SELECTION_ITEM_KIND, MINUS_ICON, MULTI_LANGUAGE_RICH_TEXT_EDITOR_ERROR_CODES, MULTI_LANGUAGE_RICH_TEXT_EDITOR_IMPORTS, MenuCheckboxGroupComponent, MenuCheckboxItemComponent, MenuComponent, MenuContextTriggerDirective, MenuDirective, MenuGroupLabelComponent, MenuItemComponent, MenuItemDirective, MenuItemShortcutComponent, MenuPanelDirective, MenuRadioGroupComponent, MenuRadioItemComponent, MenuSearchDirective, MenuSelectionGroupDirective, MenuSelectionItemDirective, MenuSeparatorComponent, MenuSurfaceDirective, MenuTriggerDirective, MultiLanguageRichTextEditorComponent, MultiLanguageRichTextEditorDirective, MultiLanguageRichTextEditorLanguageToolComponent, NAV_TABS_TOKEN, NAV_TAB_IMPORTS, NOTIFICATION_ERROR_CODES, NOTIFICATION_IMPORTS, NOTIFICATION_STACK_CONTEXT_TOKEN, NOTIFICATION_STATUS, NUMBER_INPUT_IMPORTS, NavTabLinkComponent, NavTabLinkDirective, NavTabsComponent, NavTabsDirective, NavTabsOutletComponent, NavTabsOutletDirective, NotificationActionDirective, NotificationComponent, NotificationDirective, NotificationDismissDirective, NotificationItemDirective, NotificationStackDirective, NumberInputComponent, NumberInputDirective, OTP_INPUT_IMPORTS, OVERLAY_BACK_OR_CLOSE_TOKEN, OVERLAY_BODY_TOKEN, OVERLAY_CONFIG_CLASS_KEYS, OVERLAY_CONTENT_IMPORTS, OVERLAY_ERROR_CODES, OVERLAY_FOOTER_TOKEN, OVERLAY_HEADER_TEMPLATE_TOKEN, OVERLAY_HEADER_TOKEN, OVERLAY_IMPORTS, OVERLAY_MAIN_TOKEN, OVERLAY_QUERY_PARAM_INPUT_NAME, OVERLAY_REF, OVERLAY_ROUTER_CONFIG_TOKEN, OVERLAY_ROUTER_LINK_TOKEN, OVERLAY_ROUTER_OUTLET_DISABLED_TEMPLATE_TOKEN, OVERLAY_ROUTER_OUTLET_TOKEN, OVERLAY_ROUTER_TOKEN, OVERLAY_SHARED_ROUTE_TEMPLATE_TOKEN, OtpInputComponent, OtpInputDirective, OverlayAnchorDirective, OverlayBackOrCloseDirective, OverlayBodyComponent, OverlayCloseDirective, OverlayContainerComponent, OverlayDirective, OverlayFooterDirective, OverlayHeaderDirective, OverlayHeaderTemplateDirective, OverlayMainDirective, OverlayOriginCloneComponent, OverlayRouteHeaderTemplateOutletComponent, OverlayRouterLinkDirective, OverlayRouterOutletComponent, OverlayRouterOutletDisabledTemplateDirective, OverlaySharedRouteTemplateDirective, OverlaySharedRouteTemplateOutletComponent, OverlaySidebarComponent, OverlaySidebarPageComponent, OverlaySurfaceDirective, OverlayTitleDirective, OverlayTriggerDirective, PARAGRAPH_ICON, PASSWORD_INPUT_IMPORTS, PENCIL_ICON, PHONE_COUNTRIES, PHONE_INPUT_ERROR_CODES, PHONE_INPUT_IMPORTS, PIP_CHROME_REF_TOKEN, PIP_ENTRY_TOKEN, PIP_WINDOW_ASPECT_RATIO_TOKEN, PLUS_ICON, PasswordInputComponent, PasswordInputDirective, PhoneInputComponent, PhoneInputDirective, PhoneInputFieldDirective, PhoneInputFlagDirective, PipBackDirective, PipBringBackDirective, PipCellDirective, PipCloseDirective, PipCollapseOverlayDirective, PipGridToggleDirective, PipPlayerComponent, PipSlotPlaceholderComponent, PipStageDirective, PipTitleBarDirective, PipTitleBarTemplateDirective, PipWindowComponent, PipWindowParamsDirective, ProgressBarComponent, QUERY_DEVTOOLS_IMPORTS, QueryDevtoolsComponent, QueryDevtoolsJsonComponent, QueryDevtoolsToggleComponent, QueryParamOverlayLinkDirective, RATING_IMPORTS, RICH_TEXT_EDITOR_HEADING_OPTIONS, RICH_TEXT_EDITOR_IMPORTS, RICH_TEXT_EDITOR_INLINE_TOOLS, RICH_TEXT_EDITOR_LANGUAGE_TOOL, RICH_TEXT_EDITOR_TOKEN_CODEC, RICH_TEXT_EDITOR_TOKEN_PALETTE_IMPORTS, RICH_TEXT_EDITOR_TOOL, RICH_TEXT_EDITOR_TOOLS, RICH_TEXT_EDITOR_TOOL_BUTTONS, RICH_TEXT_EDITOR_TRIGGERS_IMPORTS, ROTATE_RIGHT_ICON, RadioComponent, RadioGroupComponent, RangeSliderComponent, RangeSliderDirective, RatingComponent, RatingDirective, RatingIconDirective, RichTextEditorAlignToolComponent, RichTextEditorComponent, RichTextEditorDirective, RichTextEditorFloatingToolbarComponent, RichTextEditorFloatingToolbarDirective, RichTextEditorLinkEditorComponent, RichTextEditorLinkEditorDirective, RichTextEditorTableToolComponent, RichTextEditorTokenPaletteComponent, RichTextEditorTokenPopupComponent, RichTextEditorTriggersDirective, SCROLLABLE_ERROR_CODES, SCROLLABLE_IMPORTS, SELECTION_LIST_MULTIPLE, SELECTION_LIST_TOKEN, SELECT_ERROR_CODES, SELECT_FILTER_MODES, SELECT_IMPORTS, SIDEBAR_OVERLAY_CONFIG, SIDEBAR_OVERLAY_TOKEN, SLIDER_ERROR_CODES, SLIDER_IMPORTS, SLIDER_TOKEN, SNAP_HYSTERESIS, SOOP_PLAYER_TOKEN, SPLIT_BUTTON_ERROR_CODES, STAR_ICON, STREAM_CONSENT_TOKEN, STREAM_IMPORTS, STREAM_PLAYER_COMPONENT_TOKEN, STREAM_PLAYER_ERROR_CONTEXT_TOKEN, STREAM_PLAYER_ERROR_TOKEN, STREAM_PLAYER_PARAMS_TOKEN, STREAM_PLAYER_SLOT_TOKEN, STREAM_PLAYER_TOKEN, STREAM_SLOT_PLAYER_ID_TOKEN, STREAM_USER_CONSENT_PROVIDER_TOKEN, STRIKETHROUGH_ICON, SUPPORT_CONTENT_STATE, SUPPORT_TRANSITION_DIRECTION, SWITCH_IMPORTS, ScrollableActiveChildDirective, ScrollableButtonsDirective, ScrollableComponent, ScrollableDarkenDirective, ScrollableDirective, ScrollableDragDirective, ScrollableIgnoreChildDirective, ScrollableLoadingTemplateDirective, ScrollableMasksDirective, ScrollableNavigationDirective, ScrollableSnapDirective, SegmentedButtonComponent, SegmentedButtonGroupComponent, SelectComponent, SelectDirective, SelectEmptyDirective, SelectErrorDirective, SelectListboxDirective, SelectLoadingDirective, SelectOptionComponent, SelectOptionDirective, SelectOptionGroupComponent, SelectOptionGroupDirective, SelectOptionTemplateDirective, SelectOptionsDirective, SelectPanelComponent, SelectSearchDirective, SelectSurfaceDirective, SelectTriggerDirective, SelectValueDirective, SelectViewportDirective, SelectVirtualOptionComponent, SelectVirtualOptionDirective, SelectionListControlDirective, SelectionListDirective, SelectionOptionDirective, SliderComponent, SliderDirective, SliderThumbDirective, SliderThumbLabelDirective, SliderTrackDirective, SoopPlayerComponent, SoopPlayerDirective, SoopPlayerParamsDirective, SoopPlayerSlotComponent, SpinnerComponent, SplitButtonActionDirective, SplitButtonComponent, SplitButtonDirective, SplitButtonTriggerDirective, StreamConsentAcceptDirective, StreamConsentComponent, StreamConsentDirective, StreamPipChromeComponent, StreamPlayerErrorComponent, StreamPlayerErrorDirective, StreamPlayerLoadingComponent, StreamPlayerSlotDirective, SwitchComponent, SwitchDirective, TABLE_ICON, TAB_BAR_FITS, TAB_BAR_ORIENTATIONS, TAB_BAR_TOKEN, TAB_BAR_TRIGGER_TOKEN, TAB_BAR_VARIANTS, TAB_ERROR_CODES, TAB_GROUP_TOKEN, TAB_IMPORTS, TAB_PANEL_TOKEN, TAB_SIZES, TAG_INPUT_ERROR_CODES, TAG_INPUT_IMPORTS, TEXTAREA_IMPORTS, TEXTAREA_RESIZE_MODES, TEXT_ALIGNS, TIKTOK_PLAYER_TOKEN, TIMES_ICON, TIME_FORMAT, TIME_INPUT_ERROR_CODES, TIME_INPUT_IMPORTS, TIME_PICKER_ERROR_CODES, TIME_PICKER_IMPORTS, TOGGLETIP_ERROR_CODES, TOGGLETIP_IMPORTS, TOOLTIP_ERROR_CODES, TOOLTIP_IMPORTS, TRIANGLE_EXCLAMATION_ICON, TWITCH_PLAYER_TOKEN, TabBarDirective, TabBarTriggerDirective, TabBarUnderlineDirective, TabComponent, TabGroupComponent, TabGroupDirective, TabLabelDirective, TabPanelDirective, TabTriggerDirective, TagInputComponent, TagInputDirective, TagInputFieldDirective, TextButtonComponent, TextFieldControlDirective, TextareaComponent, TextareaDirective, TikTokPlayerComponent, TikTokPlayerDirective, TikTokPlayerParamsDirective, TikTokPlayerSlotComponent, TimeInputComponent, TimeInputDirective, TimeInputFieldDirective, TimePickerColumnDirective, TimePickerComponent, TimePickerDirective, TimePickerOptionDirective, ToggletipCloseDirective, ToggletipComponent, ToggletipDirective, ToggletipTriggerDirective, TooltipComponent, TooltipDirective, TwitchPlayerComponent, TwitchPlayerDirective, TwitchPlayerParamsDirective, TwitchPlayerSlotComponent, UNDERLINE_ICON, UNIT_MS, UPLOAD_ICON, VIMEO_PLAYER_TOKEN, VimeoPlayerComponent, VimeoPlayerDirective, VimeoPlayerParamsDirective, VimeoPlayerSlotComponent, WINDOW_CONTROL_BUTTON_KINDS, WINDOW_CONTROL_BUTTON_SIZES, WindowControlButtonComponent, YOUTUBE_PLAYER_SLOT_TOKEN, YOUTUBE_PLAYER_TOKEN, YoutubePlayerComponent, YoutubePlayerDirective, YoutubePlayerParamsDirective, YoutubePlayerSlotComponent, YoutubePlayerSlotDirective, abortFullscreenAnimation, anchoredDialogOverlayStrategy, anchoredOverlayStrategy, autoPlace, bottomSheetOverlayStrategy, buildAnchoredRuntimePositionStrategy, canHaveChildren, cascaderFromQuery, centeredOverlayStrategy, clampPosition, clampResizeRect, cleanupFullscreenAnimation, cleanupFullscreenAnimationStyles, compactLayout, computeGeometry, computeGridHeight, createAnchoredPanelController, createAutoScroller, createCardMask, createCurrencyMask, createDefaultDropzoneArgs, createDropzoneUpload, createExistingDropzoneEntry, createFileDropzoneEntry, createGridAdapter, createIbanMask, createNotificationRef, createOverlayOpener, createOverlayRef, createOverlayStrategyController, createOverlayUnsavedChangesGuard, createPipChromeAnimations, createPipChromeState, createRichTextEditorTrigger, createRichTextEditorTriggerWithQuery, createStreamConfig, createStreamPlayerSlot, createV2DropzoneUpload, defaultCompareWith, defaultDropzoneRejectionMessage, defineOverlay, defineQueryParamOverlay, deriveDurationFormatSpec, deserializeGridLayout, dialogOverlayStrategy, disposeDropzoneEntry, dropzoneFiles, enableDragToDismiss, findCollision, findNextRelevantHtmlElement, findScrollableAncestor, formatDuration, formatFileSize, fromGridPosition, fullScreenDialogOverlayStrategy, getClosestOverlay, getOriginCoordinatesAndDimensions, hysteresisRound, iconRegistryKey, indexOfNode, injectAnchoredDialogStrategy, injectAnchoredDialogStrategyDefaults, injectBottomSheetStrategy, injectBottomSheetStrategyDefaults, injectDateFormat, injectDateLocale, injectDialogStrategy, injectDialogStrategyDefaults, injectFormSupport, injectFullscreenDialogStrategy, injectFullscreenDialogStrategyDefaults, injectGridConfig, injectLeftSheetStrategy, injectLeftSheetStrategyDefaults, injectNotificationManager, injectNotificationManagerConfig, injectOverlayManager, injectOverlayRouter, injectOverlayScrollBlocker, injectOverlaySurfaceContext, injectPipChromeManager, injectPipManager, injectPipSlotPlaceholderConfig, injectRichTextEditorTools, injectRightSheetStrategy, injectRightSheetStrategyDefaults, injectSidebarOverlay, injectStreamConfig, injectStreamConsentConfig, injectStreamManager, injectStreamPlayerErrorConfig, injectStreamPlayerLoadingConfig, injectStreamScriptLoader, injectStreamUserConsentProvider, injectTimeFormat, injectTopSheetStrategy, injectTopSheetStrategyDefaults, isFileAccepted, isHtmlElement, isInteractiveElement, isPointerEvent, isTargetInsideOverlayTree, isTouchEvent, itemsCollide, leftSheetOverlayStrategy, mapLayoutToBreakpoint, matchCountryByDialCode, mergeOverlayBreakpointConfigs, mergeOverlayConfigs, nodesEqual, parseDuration, phoneCountryFlag, phoneCountryName, pixelRectsEqual, positionToPixelRect, positionsEqual, projectDragCell, provideAnchoredDialogStrategy, provideAnchoredDialogStrategyDefaults, provideBottomSheetStrategy, provideBottomSheetStrategyDefaults, provideDateFormat, provideDateLocale, provideDialogStrategy, provideDialogStrategyDefaults, provideFormErrorMessageResolver, provideFormSupport, provideFullscreenDialogStrategy, provideFullscreenDialogStrategyDefaults, provideGridConfig, provideIconOverrides, provideIcons, provideLeftSheetStrategy, provideLeftSheetStrategyDefaults, provideNotificationManager, provideNotificationManagerConfig, provideNotificationManagerInstance, provideOverlay, provideOverlayManager, provideOverlayRouter, provideOverlayRouterConfig, provideOverlayRouterService, provideOverlayScrollBlocker, providePipChromeManager, providePipManager, providePipSlotPlaceholderConfig, provideRichTextEditorAlignmentTool, provideRichTextEditorLanguageTool, provideRichTextEditorTableTool, provideRichTextEditorTokenRendering, provideRichTextEditorTools, provideRightSheetStrategy, provideRightSheetStrategyDefaults, provideSidebarOverlay, provideSidebarOverlayConfig, provideSidebarOverlayService, provideStreamConfig, provideStreamConsentConfig, provideStreamManager, provideStreamPlayerErrorConfig, provideStreamPlayerLoadingConfig, provideTimeFormat, provideTopSheetStrategy, provideTopSheetStrategyDefaults, reduceSupportPresentation, registerSingleton, requiredLanguages, resizeSpanBounds, resolveBreakpoint, resolveClosestOverlay, resolveCollisions, rightSheetOverlayStrategy, rowsToPixelHeight, selectOptionsFromQuery, selectOptionsFromV2Query, serializeGridLayout, snapResizeSpan, spanHeight, spanWidth, startFullscreenEnterAnimation, startFullscreenLeaveAnimation, stripTrunkZero, supportPresentationIncludesState, toChildrenObservable, toGridPosition, toPathObservable, toSearchObservable, topSheetOverlayStrategy, transformingBottomSheetToDialogOverlayStrategy, transformingFullScreenDialogToDialogOverlayStrategy, transformingFullScreenDialogToRightSheetOverlayStrategy, wireFormSupport };
|
|
36761
37746
|
//# sourceMappingURL=ethlete-components.mjs.map
|