@firestitch/report 18.0.12 → 18.0.13

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.
@@ -23,12 +23,15 @@ export function dateBoundString(value) {
23
23
  // the group-keyed path for charts/KPIs and the report bar.)
24
24
  // The query key fs-filter uses for a group's item(s).
25
25
  const itemName = (group) => `g${group.id}`;
26
- // A select group's distinct options, as { name, value } pairs. Options come from
27
- // the first member filter that declares them — members are the same data point,
28
- // so any member's list serves the group. The list is fetched once (the server
29
- // caps it) and replayed (shareReplay), so repeated reads never refetch. Shared
30
- // by the report-bar select control and the report-settings default picker so the
31
- // two never drift. Returns an empty list when no member provides options.
26
+ // A select group's distinct options, as { name, value } pairs. The server sends
27
+ // { value, label }: the value is what the filter matches on (an entity's stable
28
+ // id) and the label is what the viewer reads — so a renamed entity keeps its id
29
+ // and simply shows its new name here. Options come from the first member filter
30
+ // that declares them — members are the same data point, so any member's list
31
+ // serves the group. The list is fetched once (the server caps it) and replayed
32
+ // (shareReplay), so repeated reads never refetch. Shared by the report-bar
33
+ // select control and the report-settings default picker so the two never drift.
34
+ // Returns an empty list when no member provides options.
32
35
  export function loadGroupOptions(group, reportData, reportId) {
33
36
  const optionFilter = (group.filters ?? []).find((member) => member.hasOptions);
34
37
  if (!optionFilter) {
@@ -36,7 +39,19 @@ export function loadGroupOptions(group, reportData, reportId) {
36
39
  }
37
40
  return reportData.filterOptions(reportId, optionFilter.id)
38
41
  .pipe(map((options) => (options ?? [])
39
- .map((option) => ({ name: String(option), value: option }))), shareReplay({ bufferSize: 1, refCount: false }));
42
+ .map((option) => ({ name: option.label, value: option.value }))), shareReplay({ bufferSize: 1, refCount: false }));
43
+ }
44
+ // Stored filter values (ids) paired back with the labels to show for them.
45
+ // A saved default holds only values, so the names have to be read back off the
46
+ // option list — that indirection is exactly what survives a rename. A value with
47
+ // no matching option (its entity was deleted, so it is no longer listed) falls
48
+ // back to showing the raw value rather than dropping the chip, which would
49
+ // silently widen the filter.
50
+ export function resolveOptionValues(options$, values) {
51
+ return options$.pipe(map((options) => values.map((value) => {
52
+ const option = options.find((candidate) => String(candidate.value) === String(value));
53
+ return { name: option?.name ?? String(value), value };
54
+ })));
40
55
  }
41
56
  // Case-insensitive name filter applied to a loaded option list — the typed
42
57
  // keyword has to be matched here because fs-autocomplete renders what we return
@@ -65,14 +80,17 @@ export function filterItemForGroup(group, reportData, reportId, initial) {
65
80
  case 'select': {
66
81
  // One shared, replayed option stream so typing never refetches.
67
82
  const options$ = loadGroupOptions(group, reportData, reportId);
83
+ const values = initial?.values;
68
84
  return {
69
85
  name,
70
86
  type: ItemType.AutoCompleteChips,
71
87
  label,
72
88
  fetchOnFocus: true,
73
89
  values: (keyword) => matchOptions(options$, keyword),
74
- default: initial?.values?.length
75
- ? initial.values.map((value) => ({ name: String(value), value }))
90
+ // Stored values are ids, so the chips can only be named once the option
91
+ // list has loaded — hence the observable form of `default`.
92
+ default: values?.length
93
+ ? () => resolveOptionValues(options$, values)
76
94
  : undefined,
77
95
  };
78
96
  }
@@ -122,4 +140,4 @@ function selectQueryValues(raw) {
122
140
  }
123
141
  return String(raw).split(',');
124
142
  }
125
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWZpbHRlci1pdGVtcy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9hcHAvcmVwb3J0cy9yZXBvcnQtZmlsdGVyLWl0ZW1zLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBcUIsUUFBUSxFQUFFLE1BQU0sb0JBQW9CLENBQUM7QUFFakUsT0FBTyxFQUFFLE1BQU0sRUFBRSxNQUFNLFVBQVUsQ0FBQztBQUVsQyxPQUFPLEVBQWMsRUFBRSxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBQ3RDLE9BQU8sRUFBRSxHQUFHLEVBQUUsV0FBVyxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFNbEQsMkVBQTJFO0FBQzNFLDRFQUE0RTtBQUM1RSx5RUFBeUU7QUFDekUsTUFBTSxVQUFVLGVBQWUsQ0FBQyxLQUF1QztJQUNyRSxJQUFJLEtBQUssWUFBWSxJQUFJLEVBQUUsQ0FBQztRQUMxQixPQUFPLE1BQU0sQ0FBQyxLQUFLLEVBQUUsWUFBWSxDQUFDLENBQUM7SUFDckMsQ0FBQztJQUVELHNFQUFzRTtJQUN0RSw4QkFBOEI7SUFDOUIsT0FBTyxLQUFLLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsQ0FBQyxLQUFLLENBQUMsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUM7QUFDeEQsQ0FBQztBQUdELDhFQUE4RTtBQUM5RSwrRUFBK0U7QUFDL0UsNEVBQTRFO0FBQzVFLCtFQUErRTtBQUMvRSxpRUFBaUU7QUFDakUsRUFBRTtBQUNGLGdGQUFnRjtBQUNoRiw0REFBNEQ7QUFFNUQsc0RBQXNEO0FBQ3RELE1BQU0sUUFBUSxHQUFHLENBQUMsS0FBd0IsRUFBVSxFQUFFLENBQUMsSUFBSSxLQUFLLENBQUMsRUFBRSxFQUFFLENBQUM7QUFFdEUsaUZBQWlGO0FBQ2pGLGdGQUFnRjtBQUNoRiw4RUFBOEU7QUFDOUUsK0VBQStFO0FBQy9FLGlGQUFpRjtBQUNqRiww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QUVELE9BQU8sTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDLEtBQUssQ0FBQyxHQUFHLENBQUMsQ0FBQztBQUNoQyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSUZpbHRlckNvbmZpZ0l0ZW0sIEl0ZW1UeXBlIH0gZnJvbSAnQGZpcmVzdGl0Y2gvZmlsdGVyJztcblxuaW1wb3J0IHsgZm9ybWF0IH0gZnJvbSAnZGF0ZS1mbnMnO1xuXG5pbXBvcnQgeyBPYnNlcnZhYmxlLCBvZiB9IGZyb20gJ3J4anMnO1xuaW1wb3J0IHsgbWFwLCBzaGFyZVJlcGxheSB9IGZyb20gJ3J4anMvb3BlcmF0b3JzJztcblxuaW1wb3J0IHsgUmVwb3J0RGF0YSB9IGZyb20gJy4vZGF0YS9yZXBvcnQuZGF0YSc7XG5pbXBvcnQgeyBGaWx0ZXJHcm91cFZhbHVlLCBSZXBvcnRGaWx0ZXJHcm91cCB9IGZyb20gJy4vaW50ZXJmYWNlcy9yZXBvcnQuaW50ZXJmYWNlJztcblxuXG4vLyBBIGRhdGUtcmFuZ2UgYm91bmRhcnkgYXMgdGhlIHBpY2tlZCBMT0NBTCBjYWxlbmRhciBkYXkgKG5vIHRpbWUsIG5vIHR6KS5cbi8vIERhdGUtcmFuZ2UgZmlsdGVycyBhcmUgY2FsZW5kYXItZGF5IHNlbWFudGljcywgc28gdGhlIGJvdW5kYXJ5IG11c3QgY2Fycnlcbi8vIG9ubHkgWS1NLUQg4oCUIG5ldmVyIGEgdGltZXpvbmUtYmVhcmluZyBpbnN0YW50IHRoZSBiYWNrZW5kIHdvdWxkIHNoaWZ0LlxuZXhwb3J0IGZ1bmN0aW9uIGRhdGVCb3VuZFN0cmluZyh2YWx1ZTogRGF0ZSB8IHN0cmluZyB8IG51bGwgfCB1bmRlZmluZWQpOiBzdHJpbmcgfCB1bmRlZmluZWQge1xuICBpZiAodmFsdWUgaW5zdGFuY2VvZiBEYXRlKSB7XG4gICAgcmV0dXJuIGZvcm1hdCh2YWx1ZSwgJ3l5eXktTU0tZGQnKTtcbiAgfVxuXG4gIC8vIEF1dGhvcmVkL3JlbGF0aXZlIGRlZmF1bHRzIGFycml2ZSBhcyBzdHJpbmdzIGFscmVhZHkgaW4gWS1NLUQgZm9ybTtcbiAgLy8ga2VlcCBqdXN0IHRoZSBkYXRlIHBvcnRpb24uXG4gIHJldHVybiB2YWx1ZSA/IFN0cmluZyh2YWx1ZSkuc2xpY2UoMCwgMTApIDogdW5kZWZpbmVkO1xufVxuXG5cbi8vIE1hcHMgYSByZXBvcnQgZmlsdGVyIEdST1VQIHRvIGFuIGZzLWZpbHRlciBjb25maWcgaXRlbSwgYW5kIHJlYWRzIGZzLWZpbHRlclxuLy8gcXVlcnkgdmFsdWVzIGJhY2sgaW50byBwZXItZ3JvdXAgRmlsdGVyR3JvdXBWYWx1ZXMuIFNoYXJlZCBieSB0aGUgcmVwb3J0LWJhclxuLy8gZnMtZmlsdGVyIGFuZCB0aGUgcGVyLWNvbXBvbmVudCBmcy1maWx0ZXIgc28gYm90aCByZW5kZXIgdGhyb3VnaCB0aGUgc2FtZVxuLy8gbGlicmFyeSBhbmQgd3JpdGUgaW50byBSZXBvcnRGaWx0ZXJTdGF0ZVNlcnZpY2UgaWRlbnRpY2FsbHkuIEl0ZW1zIGFyZSBuYW1lZFxuLy8gYGc8Z3JvdXBJZD5gIHNvIHRoZSBxdWVyeSBrZXlzIG1hcCBzdHJhaWdodCBiYWNrIHRvIHRoZSBncm91cC5cbi8vXG4vLyAoTGlzdHMga2VlcCB0aGVpciBvd24gZmlsdGVycyBpbiBGc0xpc3QgYW5kIG5hbWUgaXRlbXMgYGY8ZmlsdGVySWQ+YDsgdGhpcyBpc1xuLy8gdGhlIGdyb3VwLWtleWVkIHBhdGggZm9yIGNoYXJ0cy9LUElzIGFuZCB0aGUgcmVwb3J0IGJhci4pXG5cbi8vIFRoZSBxdWVyeSBrZXkgZnMtZmlsdGVyIHVzZXMgZm9yIGEgZ3JvdXAncyBpdGVtKHMpLlxuY29uc3QgaXRlbU5hbWUgPSAoZ3JvdXA6IFJlcG9ydEZpbHRlckdyb3VwKTogc3RyaW5nID0+IGBnJHtncm91cC5pZH1gO1xuXG4vLyBBIHNlbGVjdCBncm91cCdzIGRpc3RpbmN0IG9wdGlvbnMsIGFzIHsgbmFtZSwgdmFsdWUgfSBwYWlycy4gT3B0aW9ucyBjb21lIGZyb21cbi8vIHRoZSBmaXJzdCBtZW1iZXIgZmlsdGVyIHRoYXQgZGVjbGFyZXMgdGhlbSDigJQgbWVtYmVycyBhcmUgdGhlIHNhbWUgZGF0YSBwb2ludCxcbi8vIHNvIGFueSBtZW1iZXIncyBsaXN0IHNlcnZlcyB0aGUgZ3JvdXAuIFRoZSBsaXN0IGlzIGZldGNoZWQgb25jZSAodGhlIHNlcnZlclxuLy8gY2FwcyBpdCkgYW5kIHJlcGxheWVkIChzaGFyZVJlcGxheSksIHNvIHJlcGVhdGVkIHJlYWRzIG5ldmVyIHJlZmV0Y2guIFNoYXJlZFxuLy8gYnkgdGhlIHJlcG9ydC1iYXIgc2VsZWN0IGNvbnRyb2wgYW5kIHRoZSByZXBvcnQtc2V0dGluZ3MgZGVmYXVsdCBwaWNrZXIgc28gdGhlXG4vLyB0d28gbmV2ZXIgZHJpZnQuIFJldHVybnMgYW4gZW1wdHkgbGlzdCB3aGVuIG5vIG1lbWJlciBwcm92aWRlcyBvcHRpb25zLlxuZXhwb3J0IGZ1bmN0aW9uIGxvYWRHcm91cE9wdGlvbnMoXG4gIGdyb3VwOiBSZXBvcnRGaWx0ZXJHcm91cCxcbiAgcmVwb3J0RGF0YTogUmVwb3J0RGF0YSxcbiAgcmVwb3J0SWQ6IG51bWJlcixcbik6IE9ic2VydmFibGU8eyBuYW1lOiBzdHJpbmc7IHZhbHVlOiB1bmtub3duIH1bXT4ge1xuICBjb25zdCBvcHRpb25GaWx0ZXIgPSAoZ3JvdXAuZmlsdGVycyA/PyBbXSkuZmluZCgobWVtYmVyKSA9PiBtZW1iZXIuaGFzT3B0aW9ucyk7XG4gIGlmICghb3B0aW9uRmlsdGVyKSB7XG4gICAgcmV0dXJuIG9mKFtdKTtcbiAgfVxuXG4gIHJldHVybiByZXBvcnREYXRhLmZpbHRlck9wdGlvbnMocmVwb3J0SWQsIG9wdGlvbkZpbHRlci5pZClcbiAgICAucGlwZShcbiAgICAgIG1hcCgob3B0aW9uczogdW5rbm93bltdKSA9PiAob3B0aW9ucyA/PyBbXSlcbiAgICAgICAgLm1hcCgob3B0aW9uKSA9PiAoeyBuYW1lOiBTdHJpbmcob3B0aW9uKSwgdmFsdWU6IG9wdGlvbiB9KSkpLFxuICAgICAgc2hhcmVSZXBsYXkoeyBidWZmZXJTaXplOiAxLCByZWZDb3VudDogZmFsc2UgfSksXG4gICAgKTtcbn1cblxuLy8gQ2FzZS1pbnNlbnNpdGl2ZSBuYW1lIGZpbHRlciBhcHBsaWVkIHRvIGEgbG9hZGVkIG9wdGlvbiBsaXN0IOKAlCB0aGUgdHlwZWRcbi8vIGtleXdvcmQgaGFzIHRvIGJlIG1hdGNoZWQgaGVyZSBiZWNhdXNlIGZzLWF1dG9jb21wbGV0ZSByZW5kZXJzIHdoYXQgd2UgcmV0dXJuXG4vLyB2ZXJiYXRpbS5cbmV4cG9ydCBmdW5jdGlvbiBtYXRjaE9wdGlvbnMoXG4gIG9wdGlvbnMkOiBPYnNlcnZhYmxlPHsgbmFtZTogc3RyaW5nOyB2YWx1ZTogdW5rbm93biB9W10+LFxuICBrZXl3b3JkPzogc3RyaW5nLFxuKTogT2JzZXJ2YWJsZTx7IG5hbWU6IHN0cmluZzsgdmFsdWU6IHVua25vd24gfVtdPiB7XG4gIGNvbnN0IHRlcm0gPSAoa2V5d29yZCA/PyAnJykudHJpbSgpLnRvTG93ZXJDYXNlKCk7XG5cbiAgcmV0dXJuIG9wdGlvbnMkLnBpcGUobWFwKChvcHRpb25zKSA9PiB0ZXJtXG4gICAgPyBvcHRpb25zLmZpbHRlcigob3B0aW9uKSA9PiBvcHRpb24ubmFtZS50b0xvd2VyQ2FzZSgpLmluY2x1ZGVzKHRlcm0pKVxuICAgIDogb3B0aW9ucykpO1xufVxuXG4vLyBCdWlsZCB0aGUgZnMtZmlsdGVyIGNvbmZpZyBpdGVtIGZvciBhIGdyb3VwLCBzZWVkaW5nIGl0cyBkZWZhdWx0IGZyb20gdGhlXG4vLyBjdXJyZW50IHNlc3Npb24gdmFsdWUgc28gYXV0aG9yZWQvcmVsYXRpdmUgZGVmYXVsdHMgc2hvdyBzZWxlY3RlZCBvbiBvcGVuLlxuZXhwb3J0IGZ1bmN0aW9uIGZpbHRlckl0ZW1Gb3JHcm91cChcbiAgZ3JvdXA6IFJlcG9ydEZpbHRlckdyb3VwLFxuICByZXBvcnREYXRhOiBSZXBvcnREYXRhLFxuICByZXBvcnRJZDogbnVtYmVyLFxuICBpbml0aWFsPzogRmlsdGVyR3JvdXBWYWx1ZSxcbik6IElGaWx0ZXJDb25maWdJdGVtIHtcbiAgY29uc3QgbmFtZSA9IGl0ZW1OYW1lKGdyb3VwKTtcbiAgY29uc3QgbGFiZWwgPSBncm91cC5sYWJlbCB8fCBncm91cC5maWx0ZXJzPy5bMF0/LmZpbHRlckNvbHVtbiB8fCAnJztcblxuICBzd2l0Y2ggKGdyb3VwLnR5cGUpIHtcbiAgICBjYXNlICdkYXRlUmFuZ2UnOlxuICAgICAgcmV0dXJuIHtcbiAgICAgICAgbmFtZSxcbiAgICAgICAgdHlwZTogSXRlbVR5cGUuRGF0ZVJhbmdlLFxuICAgICAgICBsYWJlbDogeyBmcm9tOiBgJHtsYWJlbH0gRnJvbWAsIHRvOiBgJHtsYWJlbH0gVG9gIH0sXG4gICAgICAgIGRlZmF1bHQ6IChpbml0aWFsPy5zdGFydCB8fCBpbml0aWFsPy5lbmQpXG4gICAgICAgICAgPyB7IGZyb206IGluaXRpYWwuc3RhcnQgPz8gdW5kZWZpbmVkLCB0bzogaW5pdGlhbC5lbmQgPz8gdW5kZWZpbmVkIH1cbiAgICAgICAgICA6IHVuZGVmaW5lZCxcbiAgICAgIH07XG5cbiAgICBjYXNlICdzZWxlY3QnOiB7XG4gICAgICAvLyBPbmUgc2hhcmVkLCByZXBsYXllZCBvcHRpb24gc3RyZWFtIHNvIHR5cGluZyBuZXZlciByZWZldGNoZXMuXG4gICAgICBjb25zdCBvcHRpb25zJCA9IGxvYWRHcm91cE9wdGlvbnMoZ3JvdXAsIHJlcG9ydERhdGEsIHJlcG9ydElkKTtcblxuICAgICAgcmV0dXJuIHtcbiAgICAgICAgbmFtZSxcbiAgICAgICAgdHlwZTogSXRlbVR5cGUuQXV0b0NvbXBsZXRlQ2hpcHMsXG4gICAgICAgIGxhYmVsLFxuICAgICAgICBmZXRjaE9uRm9jdXM6IHRydWUsXG4gICAgICAgIHZhbHVlczogKGtleXdvcmQ/OiBzdHJpbmcpID0+IG1hdGNoT3B0aW9ucyhvcHRpb25zJCwga2V5d29yZCksXG4gICAgICAgIGRlZmF1bHQ6IGluaXRpYWw/LnZhbHVlcz8ubGVuZ3RoXG4gICAgICAgICAgPyBpbml0aWFsLnZhbHVlcy5tYXAoKHZhbHVlKSA9PiAoeyBuYW1lOiBTdHJpbmcodmFsdWUpLCB2YWx1ZSB9KSlcbiAgICAgICAgICA6IHVuZGVmaW5lZCxcbiAgICAgIH07XG4gICAgfVxuXG4gICAgY2FzZSAna2V5d29yZCc6XG4gICAgZGVmYXVsdDpcbiAgICAgIHJldHVybiB7XG4gICAgICAgIG5hbWUsXG4gICAgICAgIHR5cGU6IEl0ZW1UeXBlLktleXdvcmQsXG4gICAgICAgIGxhYmVsLFxuICAgICAgICBkZWZhdWx0OiBpbml0aWFsPy52YWx1ZSxcbiAgICAgIH07XG4gIH1cbn1cblxuLy8gUmVhZCBhbiBmcy1maWx0ZXIgY2hhbmdlIHF1ZXJ5IGludG8gcGVyLWdyb3VwIHZhbHVlcy4gUmV0dXJucyBvbmUgZW50cnkgcGVyXG4vLyBncm91cCB3aXRoIHRoZSB2YWx1ZSB0byBzdG9yZSAob3IgbnVsbCB0byBjbGVhcikg4oCUIGNhbGxlcnMgZmVlZCB0aGVzZSB0b1xuLy8gUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlLnNldFZhbHVlLlxuZXhwb3J0IGZ1bmN0aW9uIGdyb3VwVmFsdWVzRnJvbVF1ZXJ5KFxuICBxdWVyeTogUmVjb3JkPHN0cmluZywgYW55PixcbiAgZ3JvdXBzOiBSZXBvcnRGaWx0ZXJHcm91cFtdLFxuKTogeyBncm91cElkOiBudW1iZXI7IHZhbHVlOiBGaWx0ZXJHcm91cFZhbHVlIHwgbnVsbCB9W10ge1xuICByZXR1cm4gZ3JvdXBzLm1hcCgoZ3JvdXApID0+IHtcbiAgICBjb25zdCBuYW1lID0gaXRlbU5hbWUoZ3JvdXApO1xuXG4gICAgaWYgKGdyb3VwLnR5cGUgPT09ICdkYXRlUmFuZ2UnKSB7XG4gICAgICBjb25zdCBzdGFydCA9IHF1ZXJ5W2Ake25hbWV9RnJvbWBdO1xuICAgICAgY29uc3QgZW5kID0gcXVlcnlbYCR7bmFtZX1Ub2BdO1xuXG4gICAgICByZXR1cm4ge1xuICAgICAgICBncm91cElkOiBncm91cC5pZCxcbiAgICAgICAgdmFsdWU6IChzdGFydCB8fCBlbmQpID8geyBzdGFydDogc3RhcnQgfHwgbnVsbCwgZW5kOiBlbmQgfHwgbnVsbCB9IDogbnVsbCxcbiAgICAgIH07XG4gICAgfVxuXG4gICAgaWYgKGdyb3VwLnR5cGUgPT09ICdzZWxlY3QnKSB7XG4gICAgICBjb25zdCB2YWx1ZXMgPSBzZWxlY3RRdWVyeVZhbHVlcyhxdWVyeVtuYW1lXSk7XG5cbiAgICAgIHJldHVybiB7IGdyb3VwSWQ6IGdyb3VwLmlkLCB2YWx1ZTogdmFsdWVzLmxlbmd0aCA/IHsgdmFsdWVzIH0gOiBudWxsIH07XG4gICAgfVxuXG4gICAgY29uc3Qga2V5d29yZCA9IFN0cmluZyhxdWVyeVtuYW1lXSA/PyAnJykudHJpbSgpO1xuXG4gICAgcmV0dXJuIHsgZ3JvdXBJZDogZ3JvdXAuaWQsIHZhbHVlOiBrZXl3b3JkID8geyB2YWx1ZToga2V5d29yZCB9IDogbnVsbCB9O1xuICB9KTtcbn1cblxuLy8gZnMtZmlsdGVyJ3MgQXV0b0NvbXBsZXRlQ2hpcHMgc2VyaWFsaXNlcyBhIG11bHRpLXNlbGVjdCBpbnRvIE9ORSBxdWVyeSB2YWx1ZTpcbi8vIHRoZSBzZWxlY3RlZCB2YWx1ZXMgam9pbmVkIGJ5IFwiLFwiIChpdHMgYHF1ZXJ5YCBnZXR0ZXIgZG9lcyBgLm1hcCh2YWx1ZSkuam9pbignLCcpYCkuXG4vLyBTbyBhIDIrIHNlbGVjdGlvbiBhcnJpdmVzIGFzIHRoZSBzdHJpbmcgXCJhLGJcIiwgbm90IGFuIGFycmF5IOKAlCBzcGxpdHRpbmcgb24gXCIsXCJcbi8vIHJldmVyc2VzIHRoYXQgZmFpdGhmdWxseS4gV2l0aG91dCB0aGlzLCBhIG11bHRpLXNlbGVjdCB3YXMgc2VudCBhcyB0aGUgc2luZ2xlXG4vLyB2YWx1ZSBbXCJhLGJcIl0sIHByb2R1Y2luZyBgY29sIElOICgnYSxiJylgIHNlcnZlci1zaWRlLCB3aGljaCBtYXRjaGVzIG5vdGhpbmcuXG5mdW5jdGlvbiBzZWxlY3RRdWVyeVZhbHVlcyhyYXc6IHVua25vd24pOiB1bmtub3duW10ge1xuICBpZiAoQXJyYXkuaXNBcnJheShyYXcpKSB7XG4gICAgcmV0dXJuIHJhdztcbiAgfVxuXG4gIGlmIChyYXcgPT09IG51bGwgfHwgcmF3ID09PSB1bmRlZmluZWQgfHwgcmF3ID09PSAnJykge1xuICAgIHJldHVybiBbXTtcbiAgfVxuXG4gIHJldHVybiBTdHJpbmcocmF3KS5zcGxpdCgnLCcpO1xufVxuIl19
143
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwb3J0LWZpbHRlci1pdGVtcy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9hcHAvcmVwb3J0cy9yZXBvcnQtZmlsdGVyLWl0ZW1zLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBcUIsUUFBUSxFQUFFLE1BQU0sb0JBQW9CLENBQUM7QUFFakUsT0FBTyxFQUFFLE1BQU0sRUFBRSxNQUFNLFVBQVUsQ0FBQztBQUVsQyxPQUFPLEVBQWMsRUFBRSxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBQ3RDLE9BQU8sRUFBRSxHQUFHLEVBQUUsV0FBVyxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFNbEQsMkVBQTJFO0FBQzNFLDRFQUE0RTtBQUM1RSx5RUFBeUU7QUFDekUsTUFBTSxVQUFVLGVBQWUsQ0FBQyxLQUF1QztJQUNyRSxJQUFJLEtBQUssWUFBWSxJQUFJLEVBQUUsQ0FBQztRQUMxQixPQUFPLE1BQU0sQ0FBQyxLQUFLLEVBQUUsWUFBWSxDQUFDLENBQUM7SUFDckMsQ0FBQztJQUVELHNFQUFzRTtJQUN0RSw4QkFBOEI7SUFDOUIsT0FBTyxLQUFLLENBQUMsQ0FBQyxDQUFDLE1BQU0sQ0FBQyxLQUFLLENBQUMsQ0FBQyxLQUFLLENBQUMsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUM7QUFDeEQsQ0FBQztBQUdELDhFQUE4RTtBQUM5RSwrRUFBK0U7QUFDL0UsNEVBQTRFO0FBQzVFLCtFQUErRTtBQUMvRSxpRUFBaUU7QUFDakUsRUFBRTtBQUNGLGdGQUFnRjtBQUNoRiw0REFBNEQ7QUFFNUQsc0RBQXNEO0FBQ3RELE1BQU0sUUFBUSxHQUFHLENBQUMsS0FBd0IsRUFBVSxFQUFFLENBQUMsSUFBSSxLQUFLLENBQUMsRUFBRSxFQUFFLENBQUM7QUFFdEUsZ0ZBQWdGO0FBQ2hGLGdGQUFnRjtBQUNoRixnRkFBZ0Y7QUFDaEYsZ0ZBQWdGO0FBQ2hGLDZFQUE2RTtBQUM3RSwr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T0FBTyxHQUFHLE1BQU0sQ0FBQyxLQUFLLENBQUMsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDLENBQUMsSUFBSSxFQUFFLENBQUM7UUFFakQsT0FBTyxFQUFFLE9BQU8sRUFBRSxLQUFLLENBQUMsRUFBRSxFQUFFLEtBQUssRUFBRSxPQUFPLENBQUMsQ0FBQyxDQUFDLEVBQUUsS0FBSyxFQUFFLE9BQU8sRUFBRSxDQUFDLENBQUMsQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUMzRSxDQUFDLENBQUMsQ0FBQztBQUNMLENBQUM7QUFFRCxnRkFBZ0Y7QUFDaEYsdUZBQXVGO0FBQ3ZGLGlGQUFpRjtBQUNqRixnRkFBZ0Y7QUFDaEYsZ0ZBQWdGO0FBQ2hGLFNBQVMsaUJBQWlCLENBQUMsR0FBWTtJQUNyQyxJQUFJLEtBQUssQ0FBQyxPQUFPLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQztRQUN2QixPQUFPLEdBQUcsQ0FBQztJQUNiLENBQUM7SUFFRCxJQUFJLEdBQUcsS0FBSyxJQUFJLElBQUksR0FBRyxLQUFLLFNBQVMsSUFBSSxHQUFHLEtBQUssRUFBRSxFQUFFLENBQUM7UUFDcEQsT0FBTyxFQUFFLENBQUM7SUFDWixDQUFDO0lBRUQsT0FBTyxNQUFNLENBQUMsR0FBRyxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxDQUFDO0FBQ2hDLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJRmlsdGVyQ29uZmlnSXRlbSwgSXRlbVR5cGUgfSBmcm9tICdAZmlyZXN0aXRjaC9maWx0ZXInO1xuXG5pbXBvcnQgeyBmb3JtYXQgfSBmcm9tICdkYXRlLWZucyc7XG5cbmltcG9ydCB7IE9ic2VydmFibGUsIG9mIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBtYXAsIHNoYXJlUmVwbGF5IH0gZnJvbSAncnhqcy9vcGVyYXRvcnMnO1xuXG5pbXBvcnQgeyBSZXBvcnREYXRhIH0gZnJvbSAnLi9kYXRhL3JlcG9ydC5kYXRhJztcbmltcG9ydCB7IEZpbHRlckdyb3VwVmFsdWUsIFJlcG9ydEZpbHRlckdyb3VwLCBSZXBvcnRGaWx0ZXJPcHRpb24gfSBmcm9tICcuL2ludGVyZmFjZXMvcmVwb3J0LmludGVyZmFjZSc7XG5cblxuLy8gQSBkYXRlLXJhbmdlIGJvdW5kYXJ5IGFzIHRoZSBwaWNrZWQgTE9DQUwgY2FsZW5kYXIgZGF5IChubyB0aW1lLCBubyB0eikuXG4vLyBEYXRlLXJhbmdlIGZpbHRlcnMgYXJlIGNhbGVuZGFyLWRheSBzZW1hbnRpY3MsIHNvIHRoZSBib3VuZGFyeSBtdXN0IGNhcnJ5XG4vLyBvbmx5IFktTS1EIOKAlCBuZXZlciBhIHRpbWV6b25lLWJlYXJpbmcgaW5zdGFudCB0aGUgYmFja2VuZCB3b3VsZCBzaGlmdC5cbmV4cG9ydCBmdW5jdGlvbiBkYXRlQm91bmRTdHJpbmcodmFsdWU6IERhdGUgfCBzdHJpbmcgfCBudWxsIHwgdW5kZWZpbmVkKTogc3RyaW5nIHwgdW5kZWZpbmVkIHtcbiAgaWYgKHZhbHVlIGluc3RhbmNlb2YgRGF0ZSkge1xuICAgIHJldHVybiBmb3JtYXQodmFsdWUsICd5eXl5LU1NLWRkJyk7XG4gIH1cblxuICAvLyBBdXRob3JlZC9yZWxhdGl2ZSBkZWZhdWx0cyBhcnJpdmUgYXMgc3RyaW5ncyBhbHJlYWR5IGluIFktTS1EIGZvcm07XG4gIC8vIGtlZXAganVzdCB0aGUgZGF0ZSBwb3J0aW9uLlxuICByZXR1cm4gdmFsdWUgPyBTdHJpbmcodmFsdWUpLnNsaWNlKDAsIDEwKSA6IHVuZGVmaW5lZDtcbn1cblxuXG4vLyBNYXBzIGEgcmVwb3J0IGZpbHRlciBHUk9VUCB0byBhbiBmcy1maWx0ZXIgY29uZmlnIGl0ZW0sIGFuZCByZWFkcyBmcy1maWx0ZXJcbi8vIHF1ZXJ5IHZhbHVlcyBiYWNrIGludG8gcGVyLWdyb3VwIEZpbHRlckdyb3VwVmFsdWVzLiBTaGFyZWQgYnkgdGhlIHJlcG9ydC1iYXJcbi8vIGZzLWZpbHRlciBhbmQgdGhlIHBlci1jb21wb25lbnQgZnMtZmlsdGVyIHNvIGJvdGggcmVuZGVyIHRocm91Z2ggdGhlIHNhbWVcbi8vIGxpYnJhcnkgYW5kIHdyaXRlIGludG8gUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlIGlkZW50aWNhbGx5LiBJdGVtcyBhcmUgbmFtZWRcbi8vIGBnPGdyb3VwSWQ+YCBzbyB0aGUgcXVlcnkga2V5cyBtYXAgc3RyYWlnaHQgYmFjayB0byB0aGUgZ3JvdXAuXG4vL1xuLy8gKExpc3RzIGtlZXAgdGhlaXIgb3duIGZpbHRlcnMgaW4gRnNMaXN0IGFuZCBuYW1lIGl0ZW1zIGBmPGZpbHRlcklkPmA7IHRoaXMgaXNcbi8vIHRoZSBncm91cC1rZXllZCBwYXRoIGZvciBjaGFydHMvS1BJcyBhbmQgdGhlIHJlcG9ydCBiYXIuKVxuXG4vLyBUaGUgcXVlcnkga2V5IGZzLWZpbHRlciB1c2VzIGZvciBhIGdyb3VwJ3MgaXRlbShzKS5cbmNvbnN0IGl0ZW1OYW1lID0gKGdyb3VwOiBSZXBvcnRGaWx0ZXJHcm91cCk6IHN0cmluZyA9PiBgZyR7Z3JvdXAuaWR9YDtcblxuLy8gQSBzZWxlY3QgZ3JvdXAncyBkaXN0aW5jdCBvcHRpb25zLCBhcyB7IG5hbWUsIHZhbHVlIH0gcGFpcnMuIFRoZSBzZXJ2ZXIgc2VuZHNcbi8vIHsgdmFsdWUsIGxhYmVsIH06IHRoZSB2YWx1ZSBpcyB3aGF0IHRoZSBmaWx0ZXIgbWF0Y2hlcyBvbiAoYW4gZW50aXR5J3Mgc3RhYmxlXG4vLyBpZCkgYW5kIHRoZSBsYWJlbCBpcyB3aGF0IHRoZSB2aWV3ZXIgcmVhZHMg4oCUIHNvIGEgcmVuYW1lZCBlbnRpdHkga2VlcHMgaXRzIGlkXG4vLyBhbmQgc2ltcGx5IHNob3dzIGl0cyBuZXcgbmFtZSBoZXJlLiBPcHRpb25zIGNvbWUgZnJvbSB0aGUgZmlyc3QgbWVtYmVyIGZpbHRlclxuLy8gdGhhdCBkZWNsYXJlcyB0aGVtIOKAlCBtZW1iZXJzIGFyZSB0aGUgc2FtZSBkYXRhIHBvaW50LCBzbyBhbnkgbWVtYmVyJ3MgbGlzdFxuLy8gc2VydmVzIHRoZSBncm91cC4gVGhlIGxpc3QgaXMgZmV0Y2hlZCBvbmNlICh0aGUgc2VydmVyIGNhcHMgaXQpIGFuZCByZXBsYXllZFxuLy8gKHNoYXJlUmVwbGF5KSwgc28gcmVwZWF0ZWQgcmVhZHMgbmV2ZXIgcmVmZXRjaC4gU2hhcmVkIGJ5IHRoZSByZXBvcnQtYmFyXG4vLyBzZWxlY3QgY29udHJvbCBhbmQgdGhlIHJlcG9ydC1zZXR0aW5ncyBkZWZhdWx0IHBpY2tlciBzbyB0aGUgdHdvIG5ldmVyIGRyaWZ0LlxuLy8gUmV0dXJucyBhbiBlbXB0eSBsaXN0IHdoZW4gbm8gbWVtYmVyIHByb3ZpZGVzIG9wdGlvbnMuXG5leHBvcnQgZnVuY3Rpb24gbG9hZEdyb3VwT3B0aW9ucyhcbiAgZ3JvdXA6IFJlcG9ydEZpbHRlckdyb3VwLFxuICByZXBvcnREYXRhOiBSZXBvcnREYXRhLFxuICByZXBvcnRJZDogbnVtYmVyLFxuKTogT2JzZXJ2YWJsZTx7IG5hbWU6IHN0cmluZzsgdmFsdWU6IHVua25vd24gfVtdPiB7XG4gIGNvbnN0IG9wdGlvbkZpbHRlciA9IChncm91cC5maWx0ZXJzID8/IFtdKS5maW5kKChtZW1iZXIpID0+IG1lbWJlci5oYXNPcHRpb25zKTtcbiAgaWYgKCFvcHRpb25GaWx0ZXIpIHtcbiAgICByZXR1cm4gb2YoW10pO1xuICB9XG5cbiAgcmV0dXJuIHJlcG9ydERhdGEuZmlsdGVyT3B0aW9ucyhyZXBvcnRJZCwgb3B0aW9uRmlsdGVyLmlkKVxuICAgIC5waXBlKFxuICAgICAgbWFwKChvcHRpb25zOiBSZXBvcnRGaWx0ZXJPcHRpb25bXSkgPT4gKG9wdGlvbnMgPz8gW10pXG4gICAgICAgIC5tYXAoKG9wdGlvbikgPT4gKHsgbmFtZTogb3B0aW9uLmxhYmVsLCB2YWx1ZTogb3B0aW9uLnZhbHVlIH0pKSksXG4gICAgICBzaGFyZVJlcGxheSh7IGJ1ZmZlclNpemU6IDEsIHJlZkNvdW50OiBmYWxzZSB9KSxcbiAgICApO1xufVxuXG4vLyBTdG9yZWQgZmlsdGVyIHZhbHVlcyAoaWRzKSBwYWlyZWQgYmFjayB3aXRoIHRoZSBsYWJlbHMgdG8gc2hvdyBmb3IgdGhlbS5cbi8vIEEgc2F2ZWQgZGVmYXVsdCBob2xkcyBvbmx5IHZhbHVlcywgc28gdGhlIG5hbWVzIGhhdmUgdG8gYmUgcmVhZCBiYWNrIG9mZiB0aGVcbi8vIG9wdGlvbiBsaXN0IOKAlCB0aGF0IGluZGlyZWN0aW9uIGlzIGV4YWN0bHkgd2hhdCBzdXJ2aXZlcyBhIHJlbmFtZS4gQSB2YWx1ZSB3aXRoXG4vLyBubyBtYXRjaGluZyBvcHRpb24gKGl0cyBlbnRpdHkgd2FzIGRlbGV0ZWQsIHNvIGl0IGlzIG5vIGxvbmdlciBsaXN0ZWQpIGZhbGxzXG4vLyBiYWNrIHRvIHNob3dpbmcgdGhlIHJhdyB2YWx1ZSByYXRoZXIgdGhhbiBkcm9wcGluZyB0aGUgY2hpcCwgd2hpY2ggd291bGRcbi8vIHNpbGVudGx5IHdpZGVuIHRoZSBmaWx0ZXIuXG5leHBvcnQgZnVuY3Rpb24gcmVzb2x2ZU9wdGlvblZhbHVlcyhcbiAgb3B0aW9ucyQ6IE9ic2VydmFibGU8eyBuYW1lOiBzdHJpbmc7IHZhbHVlOiB1bmtub3duIH1bXT4sXG4gIHZhbHVlczogdW5rbm93bltdLFxuKTogT2JzZXJ2YWJsZTx7IG5hbWU6IHN0cmluZzsgdmFsdWU6IHVua25vd24gfVtdPiB7XG4gIHJldHVybiBvcHRpb25zJC5waXBlKG1hcCgob3B0aW9ucykgPT4gdmFsdWVzLm1hcCgodmFsdWUpID0+IHtcbiAgICBjb25zdCBvcHRpb24gPSBvcHRpb25zLmZpbmQoKGNhbmRpZGF0ZSkgPT4gU3RyaW5nKGNhbmRpZGF0ZS52YWx1ZSkgPT09IFN0cmluZyh2YWx1ZSkpO1xuXG4gICAgcmV0dXJuIHsgbmFtZTogb3B0aW9uPy5uYW1lID8/IFN0cmluZyh2YWx1ZSksIHZhbHVlIH07XG4gIH0pKSk7XG59XG5cbi8vIENhc2UtaW5zZW5zaXRpdmUgbmFtZSBmaWx0ZXIgYXBwbGllZCB0byBhIGxvYWRlZCBvcHRpb24gbGlzdCDigJQgdGhlIHR5cGVkXG4vLyBrZXl3b3JkIGhhcyB0byBiZSBtYXRjaGVkIGhlcmUgYmVjYXVzZSBmcy1hdXRvY29tcGxldGUgcmVuZGVycyB3aGF0IHdlIHJldHVyblxuLy8gdmVyYmF0aW0uXG5leHBvcnQgZnVuY3Rpb24gbWF0Y2hPcHRpb25zKFxuICBvcHRpb25zJDogT2JzZXJ2YWJsZTx7IG5hbWU6IHN0cmluZzsgdmFsdWU6IHVua25vd24gfVtdPixcbiAga2V5d29yZD86IHN0cmluZyxcbik6IE9ic2VydmFibGU8eyBuYW1lOiBzdHJpbmc7IHZhbHVlOiB1bmtub3duIH1bXT4ge1xuICBjb25zdCB0ZXJtID0gKGtleXdvcmQgPz8gJycpLnRyaW0oKS50b0xvd2VyQ2FzZSgpO1xuXG4gIHJldHVybiBvcHRpb25zJC5waXBlKG1hcCgob3B0aW9ucykgPT4gdGVybVxuICAgID8gb3B0aW9ucy5maWx0ZXIoKG9wdGlvbikgPT4gb3B0aW9uLm5hbWUudG9Mb3dlckNhc2UoKS5pbmNsdWRlcyh0ZXJtKSlcbiAgICA6IG9wdGlvbnMpKTtcbn1cblxuLy8gQnVpbGQgdGhlIGZzLWZpbHRlciBjb25maWcgaXRlbSBmb3IgYSBncm91cCwgc2VlZGluZyBpdHMgZGVmYXVsdCBmcm9tIHRoZVxuLy8gY3VycmVudCBzZXNzaW9uIHZhbHVlIHNvIGF1dGhvcmVkL3JlbGF0aXZlIGRlZmF1bHRzIHNob3cgc2VsZWN0ZWQgb24gb3Blbi5cbmV4cG9ydCBmdW5jdGlvbiBmaWx0ZXJJdGVtRm9yR3JvdXAoXG4gIGdyb3VwOiBSZXBvcnRGaWx0ZXJHcm91cCxcbiAgcmVwb3J0RGF0YTogUmVwb3J0RGF0YSxcbiAgcmVwb3J0SWQ6IG51bWJlcixcbiAgaW5pdGlhbD86IEZpbHRlckdyb3VwVmFsdWUsXG4pOiBJRmlsdGVyQ29uZmlnSXRlbSB7XG4gIGNvbnN0IG5hbWUgPSBpdGVtTmFtZShncm91cCk7XG4gIGNvbnN0IGxhYmVsID0gZ3JvdXAubGFiZWwgfHwgZ3JvdXAuZmlsdGVycz8uWzBdPy5maWx0ZXJDb2x1bW4gfHwgJyc7XG5cbiAgc3dpdGNoIChncm91cC50eXBlKSB7XG4gICAgY2FzZSAnZGF0ZVJhbmdlJzpcbiAgICAgIHJldHVybiB7XG4gICAgICAgIG5hbWUsXG4gICAgICAgIHR5cGU6IEl0ZW1UeXBlLkRhdGVSYW5nZSxcbiAgICAgICAgbGFiZWw6IHsgZnJvbTogYCR7bGFiZWx9IEZyb21gLCB0bzogYCR7bGFiZWx9IFRvYCB9LFxuICAgICAgICBkZWZhdWx0OiAoaW5pdGlhbD8uc3RhcnQgfHwgaW5pdGlhbD8uZW5kKVxuICAgICAgICAgID8geyBmcm9tOiBpbml0aWFsLnN0YXJ0ID8/IHVuZGVmaW5lZCwgdG86IGluaXRpYWwuZW5kID8/IHVuZGVmaW5lZCB9XG4gICAgICAgICAgOiB1bmRlZmluZWQsXG4gICAgICB9O1xuXG4gICAgY2FzZSAnc2VsZWN0Jzoge1xuICAgICAgLy8gT25lIHNoYXJlZCwgcmVwbGF5ZWQgb3B0aW9uIHN0cmVhbSBzbyB0eXBpbmcgbmV2ZXIgcmVmZXRjaGVzLlxuICAgICAgY29uc3Qgb3B0aW9ucyQgPSBsb2FkR3JvdXBPcHRpb25zKGdyb3VwLCByZXBvcnREYXRhLCByZXBvcnRJZCk7XG4gICAgICBjb25zdCB2YWx1ZXMgPSBpbml0aWFsPy52YWx1ZXM7XG5cbiAgICAgIHJldHVybiB7XG4gICAgICAgIG5hbWUsXG4gICAgICAgIHR5cGU6IEl0ZW1UeXBlLkF1dG9Db21wbGV0ZUNoaXBzLFxuICAgICAgICBsYWJlbCxcbiAgICAgICAgZmV0Y2hPbkZvY3VzOiB0cnVlLFxuICAgICAgICB2YWx1ZXM6IChrZXl3b3JkPzogc3RyaW5nKSA9PiBtYXRjaE9wdGlvbnMob3B0aW9ucyQsIGtleXdvcmQpLFxuICAgICAgICAvLyBTdG9yZWQgdmFsdWVzIGFyZSBpZHMsIHNvIHRoZSBjaGlwcyBjYW4gb25seSBiZSBuYW1lZCBvbmNlIHRoZSBvcHRpb25cbiAgICAgICAgLy8gbGlzdCBoYXMgbG9hZGVkIOKAlCBoZW5jZSB0aGUgb2JzZXJ2YWJsZSBmb3JtIG9mIGBkZWZhdWx0YC5cbiAgICAgICAgZGVmYXVsdDogdmFsdWVzPy5sZW5ndGhcbiAgICAgICAgICA/ICgpID0+IHJlc29sdmVPcHRpb25WYWx1ZXMob3B0aW9ucyQsIHZhbHVlcylcbiAgICAgICAgICA6IHVuZGVmaW5lZCxcbiAgICAgIH07XG4gICAgfVxuXG4gICAgY2FzZSAna2V5d29yZCc6XG4gICAgZGVmYXVsdDpcbiAgICAgIHJldHVybiB7XG4gICAgICAgIG5hbWUsXG4gICAgICAgIHR5cGU6IEl0ZW1UeXBlLktleXdvcmQsXG4gICAgICAgIGxhYmVsLFxuICAgICAgICBkZWZhdWx0OiBpbml0aWFsPy52YWx1ZSxcbiAgICAgIH07XG4gIH1cbn1cblxuLy8gUmVhZCBhbiBmcy1maWx0ZXIgY2hhbmdlIHF1ZXJ5IGludG8gcGVyLWdyb3VwIHZhbHVlcy4gUmV0dXJucyBvbmUgZW50cnkgcGVyXG4vLyBncm91cCB3aXRoIHRoZSB2YWx1ZSB0byBzdG9yZSAob3IgbnVsbCB0byBjbGVhcikg4oCUIGNhbGxlcnMgZmVlZCB0aGVzZSB0b1xuLy8gUmVwb3J0RmlsdGVyU3RhdGVTZXJ2aWNlLnNldFZhbHVlLlxuZXhwb3J0IGZ1bmN0aW9uIGdyb3VwVmFsdWVzRnJvbVF1ZXJ5KFxuICBxdWVyeTogUmVjb3JkPHN0cmluZywgYW55PixcbiAgZ3JvdXBzOiBSZXBvcnRGaWx0ZXJHcm91cFtdLFxuKTogeyBncm91cElkOiBudW1iZXI7IHZhbHVlOiBGaWx0ZXJHcm91cFZhbHVlIHwgbnVsbCB9W10ge1xuICByZXR1cm4gZ3JvdXBzLm1hcCgoZ3JvdXApID0+IHtcbiAgICBjb25zdCBuYW1lID0gaXRlbU5hbWUoZ3JvdXApO1xuXG4gICAgaWYgKGdyb3VwLnR5cGUgPT09ICdkYXRlUmFuZ2UnKSB7XG4gICAgICBjb25zdCBzdGFydCA9IHF1ZXJ5W2Ake25hbWV9RnJvbWBdO1xuICAgICAgY29uc3QgZW5kID0gcXVlcnlbYCR7bmFtZX1Ub2BdO1xuXG4gICAgICByZXR1cm4ge1xuICAgICAgICBncm91cElkOiBncm91cC5pZCxcbiAgICAgICAgdmFsdWU6IChzdGFydCB8fCBlbmQpID8geyBzdGFydDogc3RhcnQgfHwgbnVsbCwgZW5kOiBlbmQgfHwgbnVsbCB9IDogbnVsbCxcbiAgICAgIH07XG4gICAgfVxuXG4gICAgaWYgKGdyb3VwLnR5cGUgPT09ICdzZWxlY3QnKSB7XG4gICAgICBjb25zdCB2YWx1ZXMgPSBzZWxlY3RRdWVyeVZhbHVlcyhxdWVyeVtuYW1lXSk7XG5cbiAgICAgIHJldHVybiB7IGdyb3VwSWQ6IGdyb3VwLmlkLCB2YWx1ZTogdmFsdWVzLmxlbmd0aCA/IHsgdmFsdWVzIH0gOiBudWxsIH07XG4gICAgfVxuXG4gICAgY29uc3Qga2V5d29yZCA9IFN0cmluZyhxdWVyeVtuYW1lXSA/PyAnJykudHJpbSgpO1xuXG4gICAgcmV0dXJuIHsgZ3JvdXBJZDogZ3JvdXAuaWQsIHZhbHVlOiBrZXl3b3JkID8geyB2YWx1ZToga2V5d29yZCB9IDogbnVsbCB9O1xuICB9KTtcbn1cblxuLy8gZnMtZmlsdGVyJ3MgQXV0b0NvbXBsZXRlQ2hpcHMgc2VyaWFsaXNlcyBhIG11bHRpLXNlbGVjdCBpbnRvIE9ORSBxdWVyeSB2YWx1ZTpcbi8vIHRoZSBzZWxlY3RlZCB2YWx1ZXMgam9pbmVkIGJ5IFwiLFwiIChpdHMgYHF1ZXJ5YCBnZXR0ZXIgZG9lcyBgLm1hcCh2YWx1ZSkuam9pbignLCcpYCkuXG4vLyBTbyBhIDIrIHNlbGVjdGlvbiBhcnJpdmVzIGFzIHRoZSBzdHJpbmcgXCJhLGJcIiwgbm90IGFuIGFycmF5IOKAlCBzcGxpdHRpbmcgb24gXCIsXCJcbi8vIHJldmVyc2VzIHRoYXQgZmFpdGhmdWxseS4gV2l0aG91dCB0aGlzLCBhIG11bHRpLXNlbGVjdCB3YXMgc2VudCBhcyB0aGUgc2luZ2xlXG4vLyB2YWx1ZSBbXCJhLGJcIl0sIHByb2R1Y2luZyBgY29sIElOICgnYSxiJylgIHNlcnZlci1zaWRlLCB3aGljaCBtYXRjaGVzIG5vdGhpbmcuXG5mdW5jdGlvbiBzZWxlY3RRdWVyeVZhbHVlcyhyYXc6IHVua25vd24pOiB1bmtub3duW10ge1xuICBpZiAoQXJyYXkuaXNBcnJheShyYXcpKSB7XG4gICAgcmV0dXJuIHJhdztcbiAgfVxuXG4gIGlmIChyYXcgPT09IG51bGwgfHwgcmF3ID09PSB1bmRlZmluZWQgfHwgcmF3ID09PSAnJykge1xuICAgIHJldHVybiBbXTtcbiAgfVxuXG4gIHJldHVybiBTdHJpbmcocmF3KS5zcGxpdCgnLCcpO1xufVxuIl19
@@ -3,7 +3,7 @@ import { GridComponent, TooltipComponent, LegendComponent, DatasetComponent } fr
3
3
  import * as echarts from 'echarts/core';
4
4
  export { echarts as default };
5
5
  import { CanvasRenderer } from 'echarts/renderers';
6
- import { R as REPORT_CHART_COLORS_CSS } from './firestitch-report-firestitch-report-BNHGwPj2.mjs';
6
+ import { R as REPORT_CHART_COLORS_CSS } from './firestitch-report-firestitch-report-BwC8lvzk.mjs';
7
7
 
8
8
  // Tree-shaken ECharts build for the reports renderer: only the chart types and
9
9
  // components the option-builder emits are registered, keeping the lazy chunk
@@ -57,4 +57,4 @@ echarts.registerTheme('report', {
57
57
  axisLabel: { color: '#52606d', fontSize: 11 },
58
58
  },
59
59
  });
60
- //# sourceMappingURL=firestitch-report-echarts-1VNsyco5.mjs.map
60
+ //# sourceMappingURL=firestitch-report-echarts-D9IzyGer.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"firestitch-report-echarts-1VNsyco5.mjs","sources":["../../src/app/reports/theme/echarts.ts"],"sourcesContent":["// Tree-shaken ECharts build for the reports renderer: only the chart types and\n// components the option-builder emits are registered, keeping the lazy chunk\n// lean. Loaded on demand by ngx-echarts via provideEchartsCore — see\n// REPORT_ECHARTS_PROVIDERS in reports-echarts.provider.ts.\n//\n// The canvas renderer (not SVG) is deliberate: chart.getDataURL() needs it for\n// the high-res images the PPT/PDF exports will use.\n\nimport { BarChart, LineChart, PieChart } from 'echarts/charts';\nimport {\n DatasetComponent,\n GridComponent,\n LegendComponent,\n TooltipComponent,\n} from 'echarts/components';\nimport * as echarts from 'echarts/core';\nimport { CanvasRenderer } from 'echarts/renderers';\n\nimport { REPORT_CHART_COLORS_CSS } from './palette';\n\necharts.use([\n BarChart,\n LineChart,\n PieChart,\n GridComponent,\n TooltipComponent,\n LegendComponent,\n DatasetComponent,\n CanvasRenderer,\n]);\n\n// The house theme — the single place report chart \"standards\" live (palette,\n// typography, tooltip styling). Polished defaults now; refined in the polish\n// phase.\necharts.registerTheme('report', {\n color: REPORT_CHART_COLORS_CSS,\n textStyle: {\n fontFamily: 'Roboto, \"Helvetica Neue\", sans-serif',\n },\n title: {\n textStyle: { color: '#1f2933', fontSize: 14, fontWeight: 600 },\n },\n legend: {\n textStyle: { color: '#52606d', fontSize: 11 },\n },\n tooltip: {\n backgroundColor: 'rgba(31, 41, 51, 0.92)',\n borderWidth: 0,\n textStyle: { color: '#fff', fontSize: 12 },\n },\n categoryAxis: {\n axisLine: { lineStyle: { color: '#cbd2d9' } },\n axisTick: { show: false },\n axisLabel: { color: '#52606d', fontSize: 11 },\n splitLine: { show: false },\n },\n valueAxis: {\n axisLine: { show: false },\n axisLabel: { color: '#52606d', fontSize: 11 },\n splitLine: { lineStyle: { color: '#e4e7eb' } },\n },\n timeAxis: {\n axisLine: { lineStyle: { color: '#cbd2d9' } },\n axisLabel: { color: '#52606d', fontSize: 11 },\n },\n});\n\nexport default echarts;\n"],"names":[],"mappings":";;;;;;;AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AAcA,OAAO,CAAC,GAAG,CAAC;IACV,QAAQ;IACR,SAAS;IACT,QAAQ;IACR,aAAa;IACb,gBAAgB;IAChB,eAAe;IACf,gBAAgB;IAChB,cAAc;AACf,CAAA,CAAC,CAAC;AAEH;AACA;AACA;AACA,OAAO,CAAC,aAAa,CAAC,QAAQ,EAAE;AAC9B,IAAA,KAAK,EAAE,uBAAuB;AAC9B,IAAA,SAAS,EAAE;AACT,QAAA,UAAU,EAAE,sCAAsC;AACnD,KAAA;AACD,IAAA,KAAK,EAAE;AACL,QAAA,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE,UAAU,EAAE,GAAG,EAAE;AAC/D,KAAA;AACD,IAAA,MAAM,EAAE;QACN,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC9C,KAAA;AACD,IAAA,OAAO,EAAE;AACP,QAAA,eAAe,EAAE,wBAAwB;AACzC,QAAA,WAAW,EAAE,CAAC;QACd,SAAS,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC3C,KAAA;AACD,IAAA,YAAY,EAAE;QACZ,QAAQ,EAAE,EAAE,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE;AAC7C,QAAA,QAAQ,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;QACzB,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC7C,QAAA,SAAS,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;AAC3B,KAAA;AACD,IAAA,SAAS,EAAE;AACT,QAAA,QAAQ,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;QACzB,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;QAC7C,SAAS,EAAE,EAAE,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE;AAC/C,KAAA;AACD,IAAA,QAAQ,EAAE;QACR,QAAQ,EAAE,EAAE,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE;QAC7C,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC9C,KAAA;AACF,CAAA,CAAC"}
1
+ {"version":3,"file":"firestitch-report-echarts-D9IzyGer.mjs","sources":["../../src/app/reports/theme/echarts.ts"],"sourcesContent":["// Tree-shaken ECharts build for the reports renderer: only the chart types and\n// components the option-builder emits are registered, keeping the lazy chunk\n// lean. Loaded on demand by ngx-echarts via provideEchartsCore — see\n// REPORT_ECHARTS_PROVIDERS in reports-echarts.provider.ts.\n//\n// The canvas renderer (not SVG) is deliberate: chart.getDataURL() needs it for\n// the high-res images the PPT/PDF exports will use.\n\nimport { BarChart, LineChart, PieChart } from 'echarts/charts';\nimport {\n DatasetComponent,\n GridComponent,\n LegendComponent,\n TooltipComponent,\n} from 'echarts/components';\nimport * as echarts from 'echarts/core';\nimport { CanvasRenderer } from 'echarts/renderers';\n\nimport { REPORT_CHART_COLORS_CSS } from './palette';\n\necharts.use([\n BarChart,\n LineChart,\n PieChart,\n GridComponent,\n TooltipComponent,\n LegendComponent,\n DatasetComponent,\n CanvasRenderer,\n]);\n\n// The house theme — the single place report chart \"standards\" live (palette,\n// typography, tooltip styling). Polished defaults now; refined in the polish\n// phase.\necharts.registerTheme('report', {\n color: REPORT_CHART_COLORS_CSS,\n textStyle: {\n fontFamily: 'Roboto, \"Helvetica Neue\", sans-serif',\n },\n title: {\n textStyle: { color: '#1f2933', fontSize: 14, fontWeight: 600 },\n },\n legend: {\n textStyle: { color: '#52606d', fontSize: 11 },\n },\n tooltip: {\n backgroundColor: 'rgba(31, 41, 51, 0.92)',\n borderWidth: 0,\n textStyle: { color: '#fff', fontSize: 12 },\n },\n categoryAxis: {\n axisLine: { lineStyle: { color: '#cbd2d9' } },\n axisTick: { show: false },\n axisLabel: { color: '#52606d', fontSize: 11 },\n splitLine: { show: false },\n },\n valueAxis: {\n axisLine: { show: false },\n axisLabel: { color: '#52606d', fontSize: 11 },\n splitLine: { lineStyle: { color: '#e4e7eb' } },\n },\n timeAxis: {\n axisLine: { lineStyle: { color: '#cbd2d9' } },\n axisLabel: { color: '#52606d', fontSize: 11 },\n },\n});\n\nexport default echarts;\n"],"names":[],"mappings":";;;;;;;AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AAcA,OAAO,CAAC,GAAG,CAAC;IACV,QAAQ;IACR,SAAS;IACT,QAAQ;IACR,aAAa;IACb,gBAAgB;IAChB,eAAe;IACf,gBAAgB;IAChB,cAAc;AACf,CAAA,CAAC,CAAC;AAEH;AACA;AACA;AACA,OAAO,CAAC,aAAa,CAAC,QAAQ,EAAE;AAC9B,IAAA,KAAK,EAAE,uBAAuB;AAC9B,IAAA,SAAS,EAAE;AACT,QAAA,UAAU,EAAE,sCAAsC;AACnD,KAAA;AACD,IAAA,KAAK,EAAE;AACL,QAAA,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE,UAAU,EAAE,GAAG,EAAE;AAC/D,KAAA;AACD,IAAA,MAAM,EAAE;QACN,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC9C,KAAA;AACD,IAAA,OAAO,EAAE;AACP,QAAA,eAAe,EAAE,wBAAwB;AACzC,QAAA,WAAW,EAAE,CAAC;QACd,SAAS,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC3C,KAAA;AACD,IAAA,YAAY,EAAE;QACZ,QAAQ,EAAE,EAAE,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE;AAC7C,QAAA,QAAQ,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;QACzB,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC7C,QAAA,SAAS,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;AAC3B,KAAA;AACD,IAAA,SAAS,EAAE;AACT,QAAA,QAAQ,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;QACzB,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;QAC7C,SAAS,EAAE,EAAE,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE;AAC/C,KAAA;AACD,IAAA,QAAQ,EAAE;QACR,QAAQ,EAAE,EAAE,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,EAAE;QAC7C,SAAS,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,EAAE,EAAE;AAC9C,KAAA;AACF,CAAA,CAAC"}
@@ -350,12 +350,15 @@ function dateBoundString(value) {
350
350
  // the group-keyed path for charts/KPIs and the report bar.)
351
351
  // The query key fs-filter uses for a group's item(s).
352
352
  const itemName = (group) => `g${group.id}`;
353
- // A select group's distinct options, as { name, value } pairs. Options come from
354
- // the first member filter that declares them — members are the same data point,
355
- // so any member's list serves the group. The list is fetched once (the server
356
- // caps it) and replayed (shareReplay), so repeated reads never refetch. Shared
357
- // by the report-bar select control and the report-settings default picker so the
358
- // two never drift. Returns an empty list when no member provides options.
353
+ // A select group's distinct options, as { name, value } pairs. The server sends
354
+ // { value, label }: the value is what the filter matches on (an entity's stable
355
+ // id) and the label is what the viewer reads — so a renamed entity keeps its id
356
+ // and simply shows its new name here. Options come from the first member filter
357
+ // that declares them — members are the same data point, so any member's list
358
+ // serves the group. The list is fetched once (the server caps it) and replayed
359
+ // (shareReplay), so repeated reads never refetch. Shared by the report-bar
360
+ // select control and the report-settings default picker so the two never drift.
361
+ // Returns an empty list when no member provides options.
359
362
  function loadGroupOptions(group, reportData, reportId) {
360
363
  const optionFilter = (group.filters ?? []).find((member) => member.hasOptions);
361
364
  if (!optionFilter) {
@@ -363,7 +366,19 @@ function loadGroupOptions(group, reportData, reportId) {
363
366
  }
364
367
  return reportData.filterOptions(reportId, optionFilter.id)
365
368
  .pipe(map((options) => (options ?? [])
366
- .map((option) => ({ name: String(option), value: option }))), shareReplay({ bufferSize: 1, refCount: false }));
369
+ .map((option) => ({ name: option.label, value: option.value }))), shareReplay({ bufferSize: 1, refCount: false }));
370
+ }
371
+ // Stored filter values (ids) paired back with the labels to show for them.
372
+ // A saved default holds only values, so the names have to be read back off the
373
+ // option list — that indirection is exactly what survives a rename. A value with
374
+ // no matching option (its entity was deleted, so it is no longer listed) falls
375
+ // back to showing the raw value rather than dropping the chip, which would
376
+ // silently widen the filter.
377
+ function resolveOptionValues(options$, values) {
378
+ return options$.pipe(map((options) => values.map((value) => {
379
+ const option = options.find((candidate) => String(candidate.value) === String(value));
380
+ return { name: option?.name ?? String(value), value };
381
+ })));
367
382
  }
368
383
  // Case-insensitive name filter applied to a loaded option list — the typed
369
384
  // keyword has to be matched here because fs-autocomplete renders what we return
@@ -392,14 +407,17 @@ function filterItemForGroup(group, reportData, reportId, initial) {
392
407
  case 'select': {
393
408
  // One shared, replayed option stream so typing never refetches.
394
409
  const options$ = loadGroupOptions(group, reportData, reportId);
410
+ const values = initial?.values;
395
411
  return {
396
412
  name,
397
413
  type: ItemType.AutoCompleteChips,
398
414
  label,
399
415
  fetchOnFocus: true,
400
416
  values: (keyword) => matchOptions(options$, keyword),
401
- default: initial?.values?.length
402
- ? initial.values.map((value) => ({ name: String(value), value }))
417
+ // Stored values are ids, so the chips can only be named once the option
418
+ // list has loaded — hence the observable form of `default`.
419
+ default: values?.length
420
+ ? () => resolveOptionValues(options$, values)
403
421
  : undefined,
404
422
  };
405
423
  }
@@ -1104,9 +1122,11 @@ class ComponentListComponent {
1104
1122
  name,
1105
1123
  type: ItemType.AutoCompleteChips,
1106
1124
  label,
1125
+ // The server sends { value, label }: the filter matches on the value
1126
+ // (an entity's stable id) while the viewer reads the label.
1107
1127
  values: () => this._reportData.filterOptions(this.reportId, filter.id)
1108
1128
  .pipe(map$1((options) => (options ?? [])
1109
- .map((option) => ({ name: String(option), value: option })))),
1129
+ .map((option) => ({ name: option.label, value: option.value })))),
1110
1130
  };
1111
1131
  case 'keyword':
1112
1132
  default:
@@ -2335,24 +2355,45 @@ class ReportSettingsComponent {
2335
2355
  // in bar order, seeding each draft from the group's stored default.
2336
2356
  _buildFilterRows(report) {
2337
2357
  const reportId = report.id;
2338
- const rows = (report.filterGroups ?? [])
2358
+ const built = (report.filterGroups ?? [])
2339
2359
  .filter((group) => group.level === 'report' || group.level === 'both')
2340
2360
  .sort((a, b) => a.order - b.order)
2341
2361
  .map((group) => {
2342
2362
  const groupDefault = group.config?.default;
2343
- return {
2363
+ // One shared, replayed option stream per group: the chips fetch and the
2364
+ // stored default's labels read the same list, so it is fetched once.
2365
+ const options$ = loadGroupOptions(group, this._reportData, reportId);
2366
+ const row = {
2344
2367
  group,
2345
2368
  label: group.label || group.filters?.[0]?.filterColumn || 'Filter',
2346
2369
  start: dateFromBound(groupDefault?.start),
2347
2370
  end: dateFromBound(groupDefault?.end),
2348
- values: (groupDefault?.values ?? []).map((value) => ({ name: String(value), value })),
2371
+ // Named below, once the option list carrying their labels is in.
2372
+ values: [],
2349
2373
  value: groupDefault?.value ?? '',
2350
2374
  // fs-autocomplete-chips fetch: the group's distinct options, name-filtered.
2351
2375
  // Same loader the report bar uses, so the two never drift.
2352
- fetch: (keyword) => matchOptions(loadGroupOptions(group, this._reportData, reportId), keyword),
2376
+ fetch: (keyword) => matchOptions(options$, keyword),
2353
2377
  };
2378
+ return { row, options$, values: groupDefault?.values ?? [] };
2379
+ });
2380
+ const rows = built.map((entry) => entry.row);
2381
+ const seeded = built.filter((entry) => entry.values.length);
2382
+ // Nothing to name — publish immediately rather than waiting on a request
2383
+ // no row needs.
2384
+ if (!seeded.length) {
2385
+ this.filterRows.set(rows);
2386
+ return;
2387
+ }
2388
+ // A stored select default holds ids, so its chips can only be named once the
2389
+ // option list is in. Resolve every seeded row first and publish the rows in
2390
+ // one go, so the tab never renders a chip showing a raw id.
2391
+ forkJoin(seeded.map((entry) => resolveOptionValues(entry.options$, entry.values)))
2392
+ .pipe(takeUntilDestroyed(this._destroyRef))
2393
+ .subscribe((resolved) => {
2394
+ resolved.forEach((values, index) => seeded[index].row.values = values);
2395
+ this.filterRows.set(rows);
2354
2396
  });
2355
- this.filterRows.set(rows);
2356
2397
  }
2357
2398
  // The draft default normalized to the wire shape for this row's type, or null
2358
2399
  // when empty (which clears the stored default).
@@ -2541,7 +2582,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
2541
2582
  // complete synchronously after setOption.
2542
2583
  async function renderChartImage(component, data, width, height, pixelRatio = 3) {
2543
2584
  // The same tree-shaken echarts build + 'report' theme the live canvas uses.
2544
- const echarts = (await import('./firestitch-report-echarts-1VNsyco5.mjs')).default;
2585
+ const echarts = (await import('./firestitch-report-echarts-D9IzyGer.mjs')).default;
2545
2586
  const host = document.createElement('div');
2546
2587
  host.style.width = `${width}px`;
2547
2588
  host.style.height = `${height}px`;
@@ -3285,7 +3326,7 @@ class ReportComponent {
3285
3326
  ReportPdfService,
3286
3327
  // Tree-shaken ECharts core + the 'report' house theme, loaded lazily with
3287
3328
  // this route's chunk.
3288
- provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-1VNsyco5.mjs').then((module) => module.default) }),
3329
+ provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-D9IzyGer.mjs').then((module) => module.default) }),
3289
3330
  ], viewQueries: [{ propertyName: "_split", first: true, predicate: ["split"], descendants: true, static: true }, { propertyName: "_chatPanel", first: true, predicate: ["chatPanel"], descendants: true, read: ElementRef, static: true }], ngImport: i0, template: "<div\n #split\n class=\"report fs-row.align-start\">\n <fs-ai-chat\n #chatPanel\n class=\"chat\"\n style=\"min-height: 500px;\"\n basePath=\"reports\"\n [requestData]=\"{ reportId: selected?.id ?? null }\"\n [introMessage]=\"introMessage\"\n (response)=\"onChatResponse($event)\">\n </fs-ai-chat>\n <div\n class=\"resizer\"\n (pointerdown)=\"onResizeStart($event)\">\n </div>\n <div class=\"viewer fs-flex fs-column\">\n <div class=\"fs-row.align-center.gap-sm\">\n <fs-autocomplete-chips\n class=\"fs-flex\"\n [fetch]=\"fetchReports\"\n [(ngModel)]=\"selected\"\n [disabled]=\"loadingReports\"\n [padless]=\"true\"\n [multiple]=\"false\"\n [fetchOnFocus]=\"true\"\n (ngModelChange)=\"reportChange($event)\"\n placeholder=\"Report\"\n name=\"report\">\n <ng-template\n fsAutocompleteChipsTemplate\n let-object=\"object\">\n {{ object.name }}\n </ng-template>\n <ng-template\n fsAutocompleteChipsStatic\n (click)=\"createReport()\">\n Create Report\n </ng-template>\n </fs-autocomplete-chips>\n @if (report) {\n <fs-menu>\n <ng-template\n fs-menu-item\n (click)=\"reportSettings()\">\n <mat-icon>\n tune\n </mat-icon>\n Report settings\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"toggleEditMode()\"\n [disabled]=\"editMode\">\n <mat-icon>\n dashboard_2_edit\n </mat-icon>\n {{ editMode ? 'Done editing layout' : 'Edit layout' }}\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"exportPowerpoint()\">\n <mat-icon>\n slideshow\n </mat-icon>\n Export PowerPoint\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"exportPdf()\">\n <mat-icon>\n picture_as_pdf\n </mat-icon>\n Export PDF\n </ng-template>\n </fs-menu>\n }\n </div>\n @if (report) {\n <!-- Report-level filters only (the report's actions live in the menu\n above). fs-filter reads its config once at init, so it's keyed on the\n filter signature: when the report-level filter set changes the block\n is recreated and re-reads the rebuilt config. -->\n @if (reportHasFilters) {\n @for (key of [reportFilterKey]; track key) {\n <fs-filter [config]=\"reportFilterConfig\"></fs-filter>\n }\n }\n <app-report-canvas\n [report]=\"report\"\n [editMode]=\"editMode\"\n (componentSettings)=\"componentSettings($event)\"\n (reportChanged)=\"onCanvasReportChanged()\"\n (editDone)=\"toggleEditMode()\">\n </app-report-canvas>\n }\n </div>\n</div>", styles: [".report{height:100%;min-height:500px}.report .chat{display:block;flex:0 0 25%;width:100%;height:100%;min-height:500px;min-width:0;border:none}.report .viewer{display:flex;flex-direction:column;min-width:0;height:100%;overflow:hidden}.report .viewer fs-filter{flex:0 0 auto;margin-top:10px;margin-bottom:0}.report .viewer ::ng-deep .mat-mdc-form-field-subscript-wrapper{display:none}.report .resizer{flex:0 0 11px;align-self:stretch;display:flex;justify-content:center;cursor:col-resize;touch-action:none;-webkit-user-select:none;user-select:none}.report .resizer:before{content:\"\";width:0px;background:#0000001f;transition:width .12s ease,background-color .12s ease}.report .resizer:hover:before{width:3px;background:var(--brand-primary-color)}.report.resizing{cursor:col-resize;-webkit-user-select:none;user-select:none}.report.resizing .resizer:before{width:3px;background:var(--brand-primary-color)}.report.resizing .chat,.report.resizing .viewer{pointer-events:none}::ng-deep body.body-report-reports .mat-mdc-card-content{display:flex;flex-direction:column;box-sizing:border-box}::ng-deep body.body-report-reports .mat-mdc-card-content mat-tab-nav-panel{flex:1;min-height:0}::ng-deep body.body-report-reports .mat-mdc-card-content mat-tab-nav-panel router-outlet+ng-component{height:100%}\n"], dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "ngmodule", type: FsAutocompleteChipsModule }, { kind: "component", type: i2$2.FsAutocompleteChipsComponent, selector: "fs-autocomplete-chips", inputs: ["fetch", "appearance", "floatLabel", "readonly", "size", "label", "placeholder", "chipImage", "chipBackground", "chipColor", "chipIcon", "chipIconColor", "chipClass", "chipPadding", "shape", "hint", "allowText", "allowObject", "delay", "minPanelWidth", "maxPanelHeight", "validateText", "removable", "allowClear", "color", "background", "orderable", "padless", "initOnClick", "fetchOnFocus", "multiple", "multipleAdd", "confirm", "disabled", "groupBy", "panelWidth", "panelClass", "compareWith"], outputs: ["selected", "removed", "reordered", "clear", "panelOpened", "panelClosed"] }, { kind: "directive", type: i2$2.FsAutocompleteObjectDirective, selector: "[fsAutocompleteObject],[fsAutocompleteChipsTemplate]" }, { kind: "directive", type: i2$2.FsAutocompleteChipsStaticDirective, selector: "[fsAutocompleteChipsStatic]", inputs: ["show", "disable"], outputs: ["click", "selected"] }, { kind: "ngmodule", type: FsFilterModule }, { kind: "component", type: i2.FilterComponent, selector: "fs-filter", inputs: ["config"], outputs: ["closed", "opened", "ready"] }, { kind: "ngmodule", type: FsMenuModule }, { kind: "component", type: i2$3.FsMenuComponent, selector: "fs-menu", inputs: ["class", "buttonClass", "buttonType", "buttonColor"], outputs: ["opened", "closed"] }, { kind: "directive", type: i2$3.FsMenuItemDirective, selector: "fs-menu-group,[fs-menu-item]" }, { kind: "component", type: FsAiChatComponent, selector: "fs-ai-chat", inputs: ["basePath", "requestData", "introMessage"], outputs: ["response"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: ReportCanvasComponent, selector: "app-report-canvas", inputs: ["report", "editMode"], outputs: ["componentSettings", "reportChanged", "editDone"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
3290
3331
  }
3291
3332
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ReportComponent, decorators: [{
@@ -3299,7 +3340,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
3299
3340
  ReportPdfService,
3300
3341
  // Tree-shaken ECharts core + the 'report' house theme, loaded lazily with
3301
3342
  // this route's chunk.
3302
- provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-1VNsyco5.mjs').then((module) => module.default) }),
3343
+ provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-D9IzyGer.mjs').then((module) => module.default) }),
3303
3344
  ], imports: [
3304
3345
  FormsModule,
3305
3346
  FsAutocompleteChipsModule,
@@ -4157,7 +4198,7 @@ class FsAiReportComponent {
4157
4198
  ReportPptxService,
4158
4199
  ReportPdfService,
4159
4200
  // Tree-shaken ECharts core + the 'report' house theme, loaded lazily.
4160
- provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-1VNsyco5.mjs').then((module) => module.default) }),
4201
+ provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-D9IzyGer.mjs').then((module) => module.default) }),
4161
4202
  ], viewQueries: [{ propertyName: "_split", first: true, predicate: ["split"], descendants: true, static: true }, { propertyName: "_chatPanel", first: true, predicate: ["chatPanel"], descendants: true, read: ElementRef, static: true }], ngImport: i0, template: "<div class=\"fs-ai-report fs-column\">\n\n <div class=\"fs-ai-report__header fs-row.align-center\">\n <h2 class=\"fs-ai-report__title fs-flex\">{{ report?.name }}</h2>\n\n @if (report) {\n <!-- Report-level filters, inline with the toolbar actions. fs-filter\n reads its config once at init, so it's keyed on the filter\n signature: when the report-level filter set changes the block is\n recreated and re-reads the rebuilt config. -->\n @if (reportHasFilters) {\n @for (key of [reportFilterKey]; track key) {\n <fs-filter\n class=\"fs-ai-report__filters\"\n [config]=\"reportFilterConfig\">\n </fs-filter>\n }\n }\n\n <button\n mat-icon-button\n type=\"button\"\n [matTooltip]=\"editMode ? 'Done' : 'Edit layout'\"\n (click)=\"toggleEditMode()\">\n <mat-icon>{{ editMode ? 'lock' : 'open_with' }}</mat-icon>\n </button>\n\n <button\n mat-icon-button\n type=\"button\"\n matTooltip=\"Export\"\n [fsMenuTriggerFor]=\"exportMenu\">\n <mat-icon>download</mat-icon>\n </button>\n <fs-menu #exportMenu>\n <ng-template\n fs-menu-item\n (click)=\"exportPowerpoint()\">\n Export PowerPoint\n </ng-template>\n <ng-template\n fs-menu-item\n (click)=\"exportPdf()\">\n Export PDF\n </ng-template>\n </fs-menu>\n\n <button\n mat-icon-button\n type=\"button\"\n matTooltip=\"Report settings\"\n (click)=\"reportSettings()\">\n <mat-icon>settings</mat-icon>\n </button>\n }\n </div>\n\n <div\n #split\n class=\"fs-ai-report__split fs-row.align-start\">\n <fs-ai-chat\n #chatPanel\n class=\"chat\"\n [basePath]=\"basePath()\"\n [requestData]=\"{ reportId: reportId() }\"\n (response)=\"onChatResponse($event)\">\n </fs-ai-chat>\n\n <div\n class=\"resizer\"\n (pointerdown)=\"onResizeStart($event)\">\n </div>\n\n <div class=\"viewer fs-flex fs-column\">\n @if (report) {\n <app-report-canvas\n [report]=\"report\"\n [editMode]=\"editMode\"\n (componentSettings)=\"componentSettings($event)\"\n (reportChanged)=\"onCanvasReportChanged()\"\n (editDone)=\"toggleEditMode()\">\n </app-report-canvas>\n }\n </div>\n </div>\n</div>\n", styles: [".fs-ai-report{height:100%;min-height:500px;display:flex;flex-direction:column}.fs-ai-report__header{flex:0 0 auto;margin-bottom:10px}.fs-ai-report__title{margin:0;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.fs-ai-report__filters{flex:0 0 auto;display:block;margin:0 5px 0 0}.fs-ai-report__filters ::ng-deep .filter-bar-container{align-items:center!important}.fs-ai-report__filters ::ng-deep .mat-mdc-form-field-subscript-wrapper{display:none}.fs-ai-report__split{flex:1 1 auto;min-height:0}.fs-ai-report .chat{display:block;flex:0 0 25%;width:100%;height:100%;min-height:400px;min-width:0;border:none}.fs-ai-report .viewer{display:flex;flex-direction:column;min-width:0;height:100%;overflow:hidden}.fs-ai-report .resizer{flex:0 0 11px;align-self:stretch;display:flex;justify-content:center;cursor:col-resize;touch-action:none;-webkit-user-select:none;user-select:none}.fs-ai-report .resizer:before{content:\"\";width:3px;border-radius:3px;background:transparent;transition:background-color .12s ease}.fs-ai-report .resizer:hover:before{background:var(--brand-primary-color)}.fs-ai-report__split.resizing{cursor:col-resize;-webkit-user-select:none;user-select:none}.fs-ai-report__split.resizing .resizer:before{background:var(--brand-primary-color)}.fs-ai-report__split.resizing .chat,.fs-ai-report__split.resizing .viewer{pointer-events:none}\n"], dependencies: [{ kind: "ngmodule", type: FsFilterModule }, { kind: "component", type: i2.FilterComponent, selector: "fs-filter", inputs: ["config"], outputs: ["closed", "opened", "ready"] }, { kind: "ngmodule", type: FsMenuModule }, { kind: "component", type: i2$3.FsMenuComponent, selector: "fs-menu", inputs: ["class", "buttonClass", "buttonType", "buttonColor"], outputs: ["opened", "closed"] }, { kind: "directive", type: i2$3.FsMenuItemDirective, selector: "fs-menu-group,[fs-menu-item]" }, { kind: "directive", type: i2$3.FsMenuTriggerDirective, selector: "[fsMenuTriggerFor]", inputs: ["fsMenuTriggerFor"] }, { kind: "component", type: FsAiChatComponent, selector: "fs-ai-chat", inputs: ["basePath", "requestData", "introMessage"], outputs: ["response"] }, { kind: "ngmodule", type: MatButtonModule }, { kind: "component", type: i3$1.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "ngmodule", type: MatIconModule }, { kind: "component", type: i4$2.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "ngmodule", type: MatTooltipModule }, { kind: "directive", type: i2$5.MatTooltip, selector: "[matTooltip]", inputs: ["matTooltipPosition", "matTooltipPositionAtOrigin", "matTooltipDisabled", "matTooltipShowDelay", "matTooltipHideDelay", "matTooltipTouchGestures", "matTooltip", "matTooltipClass"], exportAs: ["matTooltip"] }, { kind: "component", type: ReportCanvasComponent, selector: "app-report-canvas", inputs: ["report", "editMode"], outputs: ["componentSettings", "reportChanged", "editDone"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
4162
4203
  }
4163
4204
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: FsAiReportComponent, decorators: [{
@@ -4170,7 +4211,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
4170
4211
  ReportPptxService,
4171
4212
  ReportPdfService,
4172
4213
  // Tree-shaken ECharts core + the 'report' house theme, loaded lazily.
4173
- provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-1VNsyco5.mjs').then((module) => module.default) }),
4214
+ provideEchartsCore({ echarts: () => import('./firestitch-report-echarts-D9IzyGer.mjs').then((module) => module.default) }),
4174
4215
  ], imports: [
4175
4216
  FsFilterModule,
4176
4217
  FsMenuModule,
@@ -4201,4 +4242,4 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
4201
4242
  */
4202
4243
 
4203
4244
  export { FsAiReportsComponent as F, REPORT_CHART_COLORS_CSS as R, ReportComponent as a, FsAiReportComponent as b, ReportData as c, ReportService as d, ReportFilterStateService as e, FREQUENCY_OPTIONS as f };
4204
- //# sourceMappingURL=firestitch-report-firestitch-report-BNHGwPj2.mjs.map
4245
+ //# sourceMappingURL=firestitch-report-firestitch-report-BwC8lvzk.mjs.map