ngx-dynamic-entity 1.3.0 → 1.5.0

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.
Files changed (91) hide show
  1. package/README.md +14 -0
  2. package/fesm2022/ngx-dynamic-entity.mjs +255 -157
  3. package/fesm2022/ngx-dynamic-entity.mjs.map +1 -1
  4. package/package.json +6 -7
  5. package/types/ngx-dynamic-entity.d.ts +1730 -0
  6. package/esm2022/lib/field-types/array-field.component.mjs +0 -168
  7. package/esm2022/lib/field-types/boolean-field.component.mjs +0 -101
  8. package/esm2022/lib/field-types/checkbox-field.component.mjs +0 -82
  9. package/esm2022/lib/field-types/currency-field.component.mjs +0 -102
  10. package/esm2022/lib/field-types/date-field.component.mjs +0 -91
  11. package/esm2022/lib/field-types/date-time-field.component.mjs +0 -138
  12. package/esm2022/lib/field-types/dropdown-field.component.mjs +0 -176
  13. package/esm2022/lib/field-types/email-field.component.mjs +0 -102
  14. package/esm2022/lib/field-types/entity-ref-field.component.mjs +0 -195
  15. package/esm2022/lib/field-types/field-component.contract.mjs +0 -2
  16. package/esm2022/lib/field-types/file-field.component.mjs +0 -157
  17. package/esm2022/lib/field-types/group-field.component.mjs +0 -89
  18. package/esm2022/lib/field-types/image-field.component.mjs +0 -169
  19. package/esm2022/lib/field-types/month-year-field.component.mjs +0 -152
  20. package/esm2022/lib/field-types/multi-select-field.component.mjs +0 -146
  21. package/esm2022/lib/field-types/number-field.component.mjs +0 -112
  22. package/esm2022/lib/field-types/password-field.component.mjs +0 -110
  23. package/esm2022/lib/field-types/radio-field.component.mjs +0 -153
  24. package/esm2022/lib/field-types/text-field.component.mjs +0 -121
  25. package/esm2022/lib/field-types/textarea-field.component.mjs +0 -85
  26. package/esm2022/lib/field-types/time-field.component.mjs +0 -96
  27. package/esm2022/lib/form/dynamic-field/dynamic-field.component.mjs +0 -152
  28. package/esm2022/lib/form/dynamic-form.component.mjs +0 -899
  29. package/esm2022/lib/form/dynamic-record-form.component.mjs +0 -531
  30. package/esm2022/lib/providers/provide-field-types.mjs +0 -75
  31. package/esm2022/lib/providers/provide-ngx-dynamic-entity.mjs +0 -27
  32. package/esm2022/lib/services/cascade-data.service.mjs +0 -129
  33. package/esm2022/lib/services/config-source.service.mjs +0 -67
  34. package/esm2022/lib/services/entity-ref-cache.mjs +0 -20
  35. package/esm2022/lib/services/entity-ref-registry.service.mjs +0 -31
  36. package/esm2022/lib/services/entity-ref-selection.service.mjs +0 -27
  37. package/esm2022/lib/services/entity-reference.service.mjs +0 -168
  38. package/esm2022/lib/services/field-registry.service.mjs +0 -55
  39. package/esm2022/lib/services/file-upload.service.mjs +0 -89
  40. package/esm2022/lib/services/hook-registry.service.mjs +0 -26
  41. package/esm2022/lib/services/lookup-registry.service.mjs +0 -246
  42. package/esm2022/lib/services/rbac.service.mjs +0 -46
  43. package/esm2022/lib/services/rules-evaluation.service.mjs +0 -27
  44. package/esm2022/lib/services/validation-messages.service.mjs +0 -56
  45. package/esm2022/lib/services/validator-registry.service.mjs +0 -99
  46. package/esm2022/lib/tokens/injection-tokens.mjs +0 -126
  47. package/esm2022/ngx-dynamic-entity.mjs +0 -5
  48. package/esm2022/public-api.mjs +0 -58
  49. package/index.d.ts +0 -5
  50. package/lib/field-types/array-field.component.d.ts +0 -28
  51. package/lib/field-types/boolean-field.component.d.ts +0 -18
  52. package/lib/field-types/checkbox-field.component.d.ts +0 -13
  53. package/lib/field-types/currency-field.component.d.ts +0 -17
  54. package/lib/field-types/date-field.component.d.ts +0 -15
  55. package/lib/field-types/date-time-field.component.d.ts +0 -30
  56. package/lib/field-types/dropdown-field.component.d.ts +0 -34
  57. package/lib/field-types/email-field.component.d.ts +0 -15
  58. package/lib/field-types/entity-ref-field.component.d.ts +0 -49
  59. package/lib/field-types/field-component.contract.d.ts +0 -49
  60. package/lib/field-types/file-field.component.d.ts +0 -25
  61. package/lib/field-types/group-field.component.d.ts +0 -17
  62. package/lib/field-types/image-field.component.d.ts +0 -30
  63. package/lib/field-types/month-year-field.component.d.ts +0 -28
  64. package/lib/field-types/multi-select-field.component.d.ts +0 -27
  65. package/lib/field-types/number-field.component.d.ts +0 -16
  66. package/lib/field-types/password-field.component.d.ts +0 -17
  67. package/lib/field-types/radio-field.component.d.ts +0 -33
  68. package/lib/field-types/text-field.component.d.ts +0 -23
  69. package/lib/field-types/textarea-field.component.d.ts +0 -14
  70. package/lib/field-types/time-field.component.d.ts +0 -27
  71. package/lib/form/dynamic-field/dynamic-field.component.d.ts +0 -78
  72. package/lib/form/dynamic-form.component.d.ts +0 -293
  73. package/lib/form/dynamic-record-form.component.d.ts +0 -199
  74. package/lib/providers/provide-field-types.d.ts +0 -24
  75. package/lib/providers/provide-ngx-dynamic-entity.d.ts +0 -56
  76. package/lib/services/cascade-data.service.d.ts +0 -45
  77. package/lib/services/config-source.service.d.ts +0 -14
  78. package/lib/services/entity-ref-cache.d.ts +0 -27
  79. package/lib/services/entity-ref-registry.service.d.ts +0 -21
  80. package/lib/services/entity-ref-selection.service.d.ts +0 -24
  81. package/lib/services/entity-reference.service.d.ts +0 -49
  82. package/lib/services/field-registry.service.d.ts +0 -32
  83. package/lib/services/file-upload.service.d.ts +0 -27
  84. package/lib/services/hook-registry.service.d.ts +0 -12
  85. package/lib/services/lookup-registry.service.d.ts +0 -94
  86. package/lib/services/rbac.service.d.ts +0 -27
  87. package/lib/services/rules-evaluation.service.d.ts +0 -17
  88. package/lib/services/validation-messages.service.d.ts +0 -43
  89. package/lib/services/validator-registry.service.d.ts +0 -32
  90. package/lib/tokens/injection-tokens.d.ts +0 -134
  91. package/public-api.d.ts +0 -42
@@ -1,168 +0,0 @@
1
- import { Injectable, inject } from '@angular/core';
2
- import { buildReferenceCacheKey, entityKeyFromCacheKey, normalizeReferenceOptions, resolveLabel, valuesMatch, } from '@dynamic-entity/core';
3
- import { ENTITY_REF_CACHE_STORE } from '../tokens/injection-tokens';
4
- import { EntityRefRegistryService } from './entity-ref-registry.service';
5
- import * as i0 from "@angular/core";
6
- /** Label-cache field separator. Kept out of template literals so it stays visible in source. */
7
- const LABEL_SEP = '|';
8
- /**
9
- * EntityReferenceService — the cache in front of consumer-registered option loaders.
10
- *
11
- * Three layers, matching the reference implementation:
12
- * 1. **options** — resolved `ReferenceOption[]` per (entity, lang, displayFields, filters).
13
- * 2. **in-flight** — the pending Promise, so N fields referencing one entity trigger one
14
- * load rather than N. This is the layer that actually removes duplicate HTTP calls;
15
- * an options cache alone does nothing for concurrent first loads.
16
- * 3. **labels** — synchronous value → text, for rendering a stored reference without
17
- * waiting on a load.
18
- *
19
- * Invalidation is per entity, not global. The reference could only `clearCache()` everything
20
- * (issue #16), so saving one record re-fetched every entity's options.
21
- */
22
- export class EntityReferenceService {
23
- registry = inject(EntityRefRegistryService);
24
- store = inject(ENTITY_REF_CACHE_STORE);
25
- /** Loads in progress, keyed the same way as the options cache. */
26
- inFlight = new Map();
27
- /** `entityKey|lang|canonicalValue` -> display text. */
28
- labels = new Map();
29
- /**
30
- * Options for an entity, from cache when present.
31
- * Concurrent callers with the same key share one load.
32
- */
33
- async load(entityKey, ctx = {}) {
34
- const key = buildReferenceCacheKey(entityKey, {
35
- lang: ctx.lang,
36
- filters: ctx.filters,
37
- displayFields: ctx.displayFields,
38
- parentValue: ctx.parentValue,
39
- });
40
- const cached = this.store.get(key);
41
- if (cached)
42
- return cached;
43
- const pending = this.inFlight.get(key);
44
- if (pending)
45
- return pending;
46
- const loader = this.registry.resolve(entityKey);
47
- if (!loader)
48
- return [];
49
- const load = this.invoke(loader, ctx)
50
- .then(raw => {
51
- // displayFields drive label building, which is why they are part of the cache key.
52
- const options = normalizeReferenceOptions(raw, ctx.displayFields ? { enabled: true, displayFields: ctx.displayFields } : undefined, ctx.lang ?? 'en');
53
- this.store.set(key, options);
54
- this.rememberLabels(entityKey, ctx.lang ?? 'en', options);
55
- return options;
56
- });
57
- // A failed load resolves to [] for the caller but is never written to the store, so a
58
- // transient error is retried on the next call instead of poisoning the cache. Only the
59
- // `.then` above caches, and a rejection skips it.
60
- const guarded = load
61
- .catch(() => [])
62
- .finally(() => this.inFlight.delete(key));
63
- this.inFlight.set(key, guarded);
64
- return guarded;
65
- }
66
- /** Cached options without triggering a load. `undefined` when not cached. */
67
- peek(entityKey, ctx = {}) {
68
- return this.store.get(buildReferenceCacheKey(entityKey, {
69
- lang: ctx.lang,
70
- filters: ctx.filters,
71
- displayFields: ctx.displayFields,
72
- parentValue: ctx.parentValue,
73
- }));
74
- }
75
- /**
76
- * Display text for a stored reference value, synchronously.
77
- * Returns `undefined` when the entity's options have never been loaded.
78
- */
79
- labelFor(entityKey, value, lang = 'en') {
80
- return this.labels.get(this.labelKey(entityKey, lang, value));
81
- }
82
- /** Drop everything cached for one entity, leaving other entities intact. */
83
- invalidate(entityKey) {
84
- for (const key of this.store.keys()) {
85
- if (entityKeyFromCacheKey(key) === entityKey)
86
- this.store.delete(key);
87
- }
88
- for (const key of [...this.inFlight.keys()]) {
89
- if (entityKeyFromCacheKey(key) === entityKey)
90
- this.inFlight.delete(key);
91
- }
92
- const prefix = `${entityKey}${LABEL_SEP}`;
93
- for (const key of [...this.labels.keys()]) {
94
- if (key.startsWith(prefix))
95
- this.labels.delete(key);
96
- }
97
- }
98
- clear() {
99
- this.store.clear();
100
- this.inFlight.clear();
101
- this.labels.clear();
102
- }
103
- rememberLabels(entityKey, lang, options) {
104
- for (const option of options) {
105
- this.labels.set(this.labelKey(entityKey, lang, option.value), option.label);
106
- }
107
- }
108
- /** Label-cache key. An object value collapses to its resolved text for the active language. */
109
- labelKey(entityKey, lang, value) {
110
- const canonical = value !== null && typeof value === 'object'
111
- ? resolveLabel(value, lang)
112
- : String(value ?? '');
113
- return [entityKey, lang, canonical].join(LABEL_SEP);
114
- }
115
- // ─── Loader result coercion (array | Promise | Observable) ──────────────────
116
- invoke(loader, ctx) {
117
- let result;
118
- try {
119
- result = loader(ctx);
120
- }
121
- catch (err) {
122
- // Reject rather than resolve empty: `load` must be able to tell failure from
123
- // "no matches", or it would cache the failure.
124
- return Promise.reject(err);
125
- }
126
- return this.toPromise(result);
127
- }
128
- toPromise(result) {
129
- if (Array.isArray(result))
130
- return Promise.resolve(result);
131
- if (this.isSubscribable(result)) {
132
- // First emission wins, so an Observable that stays open still resolves the load.
133
- return new Promise((resolve, reject) => {
134
- let settled = false;
135
- const settle = (fn) => {
136
- if (settled)
137
- return;
138
- settled = true;
139
- fn();
140
- };
141
- result.subscribe({
142
- next: value => settle(() => resolve(value ?? [])),
143
- // An erroring stream is a failed load, not an empty one — see `invoke`.
144
- error: err => settle(() => reject(err)),
145
- // Completing without emitting is a legitimate empty result, and is cached.
146
- complete: () => settle(() => resolve([])),
147
- });
148
- });
149
- }
150
- return Promise.resolve(result);
151
- }
152
- isSubscribable(value) {
153
- return (typeof value === 'object' &&
154
- value !== null &&
155
- typeof value.subscribe === 'function');
156
- }
157
- /** Exposed for cascade filtering, which matches a parent value against option values. */
158
- matches(a, b, lang = 'en') {
159
- return valuesMatch(a, b, lang);
160
- }
161
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: EntityReferenceService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
162
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: EntityReferenceService, providedIn: 'root' });
163
- }
164
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: EntityReferenceService, decorators: [{
165
- type: Injectable,
166
- args: [{ providedIn: 'root' }]
167
- }] });
168
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZW50aXR5LXJlZmVyZW5jZS5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vc3JjL2xpYi9zZXJ2aWNlcy9lbnRpdHktcmVmZXJlbmNlLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFTbkQsT0FBTyxFQUNMLHNCQUFzQixFQUN0QixxQkFBcUIsRUFDckIseUJBQXlCLEVBQ3pCLFlBQVksRUFDWixXQUFXLEdBQ1osTUFBTSxzQkFBc0IsQ0FBQztBQUM5QixPQUFPLEVBQUUsc0JBQXNCLEVBQUUsTUFBTSw0QkFBNEIsQ0FBQztBQUNwRSxPQUFPLEVBQUUsd0JBQXdCLEVBQUUsTUFBTSwrQkFBK0IsQ0FBQzs7QUFFekUsZ0dBQWdHO0FBQ2hHLE1BQU0sU0FBUyxHQUFHLEdBQUcsQ0FBQztBQUV0Qjs7Ozs7Ozs7Ozs7OztHQWFHO0FBRUgsTUFBTSxPQUFPLHNCQUFzQjtJQUNoQixRQUFRLEdBQUcsTUFBTSxDQUFDLHdCQUF3QixDQUFDLENBQUM7SUFDNUMsS0FBSyxHQUFHLE1BQU0sQ0FBQyxzQkFBc0IsQ0FBQyxDQUFDO0lBRXhELGtFQUFrRTtJQUNqRCxRQUFRLEdBQUcsSUFBSSxHQUFHLEVBQXNDLENBQUM7SUFDMUUsdURBQXVEO0lBQ3RDLE1BQU0sR0FBRyxJQUFJLEdBQUcsRUFBa0IsQ0FBQztJQUVwRDs7O09BR0c7SUFDSCxLQUFLLENBQUMsSUFBSSxDQUFDLFNBQWlCLEVBQUUsTUFBOEIsRUFBRTtRQUM1RCxNQUFNLEdBQUcsR0FBRyxzQkFBc0IsQ0FBQyxTQUFTLEVBQUU7WUFDNUMsSUFBSSxFQUFFLEdBQUcsQ0FBQyxJQUFJO1lBQ2QsT0FBTyxFQUFFLEdBQUcsQ0FBQyxPQUFPO1lBQ3BCLGFBQWEsRUFBRSxHQUFHLENBQUMsYUFBYTtZQUNoQyxXQUFXLEVBQUUsR0FBRyxDQUFDLFdBQVc7U0FDN0Is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QUFFLENBQUMsT0FBTyxDQUFDLEtBQUssSUFBSSxFQUFFLENBQUMsQ0FBQztvQkFDakQsd0VBQXdFO29CQUN4RSxLQUFLLEVBQUUsR0FBRyxDQUFDLEVBQUUsQ0FBQyxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDO29CQUN2QywyRUFBMkU7b0JBQzNFLFFBQVEsRUFBRSxHQUFHLEVBQUUsQ0FBQyxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsT0FBTyxDQUFDLEVBQUUsQ0FBQyxDQUFDO2lCQUMxQyxDQUFDLENBQUM7WUFDTCxDQUFDLENBQUMsQ0FBQztRQUNMLENBQUM7UUFDRCxPQUFPLE9BQU8sQ0FBQyxPQUFPLENBQUMsTUFBb0MsQ0FBQyxDQUFDO0lBQy9ELENBQUM7SUFFTyxjQUFjLENBQUMsS0FBYztRQUNuQyxPQUFPLENBQ0wsT0FBTyxLQUFLLEtBQUssUUFBUTtZQUN6QixLQUFLLEtBQUssSUFBSTtZQUNkLE9BQVEsS0FBeUMsQ0FBQyxTQUFTLEtBQUssVUFBVSxDQUMzRSxDQUFDO0lBQ0osQ0FBQztJQUVELHlGQUF5RjtJQUN6RixPQUFPLENBQUMsQ0FBVSxFQUFFLENBQVUsRUFBRSxJQUFJLEdBQUcsSUFBSTtRQUN6QyxPQUFPLFdBQVcsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxFQUFFLElBQUksQ0FBQyxDQUFDO0lBQ2pDLENBQUM7d0dBaEtVLHNCQUFzQjs0R0FBdEIsc0JBQXNCLGNBRFQsTUFBTTs7NEZBQ25CLHNCQUFzQjtrQkFEbEMsVUFBVTttQkFBQyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJbmplY3RhYmxlLCBpbmplY3QgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB0eXBlIHtcbiAgRW50aXR5UmVmZXJlbmNlTG9hZGVyLFxuICBSYXdSZWZlcmVuY2VJdGVtLFxuICBSZWZlcmVuY2VMb2FkZXJDb250ZXh0LFxuICBSZWZlcmVuY2VMb2FkZXJSZXN1bHQsXG4gIFJlZmVyZW5jZU9wdGlvbixcbiAgU3Vic2NyaWJhYmxlLFxufSBmcm9tICdAZHluYW1pYy1lbnRpdHkvY29yZSc7XG5pbXBvcnQge1xuICBidWlsZFJlZmVyZW5jZUNhY2hlS2V5LFxuICBlbnRpdHlLZXlGcm9tQ2FjaGVLZXksXG4gIG5vcm1hbGl6ZVJlZmVyZW5jZU9wdGlvbnMsXG4gIHJlc29sdmVMYWJlbCxcbiAgdmFsdWVzTWF0Y2gsXG59IGZyb20gJ0BkeW5hbWljLWVudGl0eS9jb3JlJztcbmltcG9ydCB7IEVOVElUWV9SRUZfQ0FDSEVfU1RPUkUgfSBmcm9tICcuLi90b2tlbnMvaW5qZWN0aW9uLXRva2Vucyc7XG5pbXBvcnQgeyBFbnRpdHlSZWZSZWdpc3RyeVNlcnZpY2UgfSBmcm9tICcuL2VudGl0eS1yZWYtcmVnaXN0cnkuc2VydmljZSc7XG5cbi8qKiBMYWJlbC1jYWNoZSBmaWVsZCBzZXBhcmF0b3IuIEtlcHQgb3V0IG9mIHRlbXBsYXRlIGxpdGVyYWxzIHNvIGl0IHN0YXlzIHZpc2libGUgaW4gc291cmNlLiAqL1xuY29uc3QgTEFCRUxfU0VQID0gJ3wnO1xuXG4vKipcbiAqIEVudGl0eVJlZmVyZW5jZVNlcnZpY2Ug4oCUIHRoZSBjYWNoZSBpbiBmcm9udCBvZiBjb25zdW1lci1yZWdpc3RlcmVkIG9wdGlvbiBsb2FkZXJzLlxuICpcbiAqIFRocmVlIGxheWVycywgbWF0Y2hpbmcgdGhlIHJlZmVyZW5jZSBpbXBsZW1lbnRhdGlvbjpcbiAqICAxLiAqKm9wdGlvbnMqKiDigJQgcmVzb2x2ZWQgYFJlZmVyZW5jZU9wdGlvbltdYCBwZXIgKGVudGl0eSwgbGFuZywgZGlzcGxheUZpZWxkcywgZmlsdGVycykuXG4gKiAgMi4gKippbi1mbGlnaHQqKiDigJQgdGhlIHBlbmRpbmcgUHJvbWlzZSwgc28gTiBmaWVsZHMgcmVmZXJlbmNpbmcgb25lIGVudGl0eSB0cmlnZ2VyIG9uZVxuICogICAgIGxvYWQgcmF0aGVyIHRoYW4gTi4gVGhpcyBpcyB0aGUgbGF5ZXIgdGhhdCBhY3R1YWxseSByZW1vdmVzIGR1cGxpY2F0ZSBIVFRQIGNhbGxzO1xuICogICAgIGFuIG9wdGlvbnMgY2FjaGUgYWxvbmUgZG9lcyBub3RoaW5nIGZvciBjb25jdXJyZW50IGZpcnN0IGxvYWRzLlxuICogIDMuICoqbGFiZWxzKiog4oCUIHN5bmNocm9ub3VzIHZhbHVlIOKGkiB0ZXh0LCBmb3IgcmVuZGVyaW5nIGEgc3RvcmVkIHJlZmVyZW5jZSB3aXRob3V0XG4gKiAgICAgd2FpdGluZyBvbiBhIGxvYWQuXG4gKlxuICogSW52YWxpZGF0aW9uIGlzIHBlciBlbnRpdHksIG5vdCBnbG9iYWwuIFRoZSByZWZlcmVuY2UgY291bGQgb25seSBgY2xlYXJDYWNoZSgpYCBldmVyeXRoaW5nXG4gKiAoaXNzdWUgIzE2KSwgc28gc2F2aW5nIG9uZSByZWNvcmQgcmUtZmV0Y2hlZCBldmVyeSBlbnRpdHkncyBvcHRpb25zLlxuICovXG5ASW5qZWN0YWJsZSh7IHByb3ZpZGVkSW46ICdyb290JyB9KVxuZXhwb3J0IGNsYXNzIEVudGl0eVJlZmVyZW5jZVNlcnZpY2Uge1xuICBwcml2YXRlIHJlYWRvbmx5IHJlZ2lzdHJ5ID0gaW5qZWN0KEVudGl0eVJlZlJlZ2lzdHJ5U2VydmljZSk7XG4gIHByaXZhdGUgcmVhZG9ubHkgc3RvcmUgPSBpbmplY3QoRU5USVRZX1JFRl9DQUNIRV9TVE9SRSk7XG5cbiAgLyoqIExvYWRzIGluIHByb2dyZXNzLCBrZXllZCB0aGUgc2FtZSB3YXkgYXMgdGhlIG9wdGlvbnMgY2FjaGUuICovXG4gIHByaXZhdGUgcmVhZG9ubHkgaW5GbGlnaHQgPSBuZXcgTWFwPHN0cmluZywgUHJvbWlzZTxSZWZlcmVuY2VPcHRpb25bXT4+KCk7XG4gIC8qKiBgZW50aXR5S2V5fGxhbmd8Y2Fub25pY2FsVmFsdWVgIC0+IGRpc3BsYXkgdGV4dC4gKi9cbiAgcHJpdmF0ZSByZWFkb25seSBsYWJlbHMgPSBuZXcgTWFwPHN0cmluZywgc3RyaW5nPigpO1xuXG4gIC8qKlxuICAgKiBPcHRpb25zIGZvciBhbiBlbnRpdHksIGZyb20gY2FjaGUgd2hlbiBwcmVzZW50LlxuICAgKiBDb25jdXJyZW50IGNhbGxlcnMgd2l0aCB0aGUgc2FtZSBrZXkgc2hhcmUgb25lIGxvYWQuXG4gICAqL1xuICBhc3luYyBsb2FkKGVudGl0eUtleTogc3RyaW5nLCBjdHg6IFJlZmVyZW5jZUxvYWRlckNvbnRleHQgPSB7fSk6IFByb21pc2U8UmVmZXJlbmNlT3B0aW9uW10+IHtcbiAgICBjb25zdCBrZXkgPSBidWlsZFJlZmVyZW5jZUNhY2hlS2V5KGVudGl0eUtleSwge1xuICAgICAgbGFuZzogY3R4LmxhbmcsXG4gICAgICBmaWx0ZXJzOiBjdHguZmlsdGVycyxcbiAgICAgIGRpc3BsYXlGaWVsZHM6IGN0eC5kaXNwbGF5RmllbGRzLFxuICAgICAgcGFyZW50VmFsdWU6IGN0eC5wYXJlbnRWYWx1ZSxcbiAgICB9KTtcblxuICAgIGNvbnN0IGNhY2hlZCA9IHRoaXMuc3RvcmUuZ2V0KGtleSk7XG4gICAgaWYgKGNhY2hlZCkgcmV0dXJuIGNhY2hlZDtcblxuICAgIGNvbnN0IHBlbmRpbmcgPSB0aGlzLmluRmxpZ2h0LmdldChrZXkpO1xuICAgIGlmIChwZW5kaW5nKSByZXR1cm4gcGVuZGluZztcblxuICAgIGNvbnN0IGxvYWRlciA9IHRoaXMucmVnaXN0cnkucmVzb2x2ZShlbnRpdHlLZXkpO1xuICAgIGlmICghbG9hZGVyKSByZXR1cm4gW107XG5cbiAgICBjb25zdCBsb2FkID0gdGhpcy5pbnZva2UobG9hZGVyLCBjdHgpXG4gICAgICAudGhlbihyYXcgPT4ge1xuICAgICAgICAvLyBkaXNwbGF5RmllbGRzIGRyaXZlIGxhYmVsIGJ1aWxkaW5nLCB3aGljaCBpcyB3aHkgdGhleSBhcmUgcGFydCBvZiB0aGUgY2FjaGUga2V5LlxuICAgICAgICBjb25zdCBvcHRpb25zID0gbm9ybWFsaXplUmVmZXJlbmNlT3B0aW9ucyhcbiAgICAgICAgICByYXcgYXMgUmF3UmVmZXJlbmNlSXRlbVtdLFxuICAgICAgICAgIGN0eC5kaXNwbGF5RmllbGRzID8geyBlbmFibGVkOiB0cnVlLCBkaXNwbGF5RmllbGRzOiBjdHguZGlzcGxheUZpZWxkcyB9IDogdW5kZWZpbmVkLFxuICAgICAgICAgIGN0eC5sYW5nID8/ICdlbicsXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuc3RvcmUuc2V0KGtleSwgb3B0aW9ucyk7XG4gICAgICAgIHRoaXMucmVtZW1iZXJMYWJlbHMoZW50aXR5S2V5LCBjdHgubGFuZyA/PyAnZW4nLCBvcHRpb25zKTtcbiAgICAgICAgcmV0dXJuIG9wdGlvbnM7XG4gICAgICB9KTtcblxuICAgIC8vIEEgZmFpbGVkIGxvYWQgcmVzb2x2ZXMgdG8gW10gZm9yIHRoZSBjYWxsZXIgYnV0IGlzIG5ldmVyIHdyaXR0ZW4gdG8gdGhlIHN0b3JlLCBzbyBhXG4gICAgLy8gdHJhbnNpZW50IGVycm9yIGlzIHJldHJpZWQgb24gdGhlIG5leHQgY2FsbCBpbnN0ZWFkIG9mIHBvaXNvbmluZyB0aGUgY2FjaGUuIE9ubHkgdGhlXG4gICAgLy8gYC50aGVuYCBhYm92ZSBjYWNoZXMsIGFuZCBhIHJlamVjdGlvbiBza2lwcyBpdC5cbiAgICBjb25zdCBndWFyZGVkID0gbG9hZFxuICAgICAgLmNhdGNoKCgpID0+IFtdIGFzIFJlZmVyZW5jZU9wdGlvbltdKVxuICAgICAgLmZpbmFsbHkoKCkgPT4gdGhpcy5pbkZsaWdodC5kZWxldGUoa2V5KSk7XG5cbiAgICB0aGlzLmluRmxpZ2h0LnNldChrZXksIGd1YXJkZWQpO1xuICAgIHJldHVybiBndWFyZGVkO1xuICB9XG5cbiAgLyoqIENhY2hlZCBvcHRpb25zIHdpdGhvdXQgdHJpZ2dlcmluZyBhIGxvYWQuIGB1bmRlZmluZWRgIHdoZW4gbm90IGNhY2hlZC4gKi9cbiAgcGVlayhlbnRpdHlLZXk6IHN0cmluZywgY3R4OiBSZWZlcmVuY2VMb2FkZXJDb250ZXh0ID0ge30pOiBSZWZlcmVuY2VPcHRpb25bXSB8IHVuZGVmaW5lZCB7XG4gICAgcmV0dXJuIHRoaXMuc3RvcmUuZ2V0KFxuICAgICAgYnVpbGRSZWZlcmVuY2VDYWNoZUtleShlbnRpdHlLZXksIHtcbiAgICAgICAgbGFuZzogY3R4LmxhbmcsXG4gICAgICAgIGZpbHRlcnM6IGN0eC5maWx0ZXJzLFxuICAgICAgICBkaXNwbGF5RmllbGRzOiBjdHguZGlzcGxheUZpZWxkcyxcbiAgICAgICAgcGFyZW50VmFsdWU6IGN0eC5wYXJlbnRWYWx1ZSxcbiAgICAgIH0pLFxuICAgICk7XG4gIH1cblxuICAvKipcbiAgICogRGlzcGxheSB0ZXh0IGZvciBhIHN0b3JlZCByZWZlcmVuY2UgdmFsdWUsIHN5bmNocm9ub3VzbHkuXG4gICAqIFJldHVybnMgYHVuZGVmaW5lZGAgd2hlbiB0aGUgZW50aXR5J3Mgb3B0aW9ucyBoYXZlIG5ldmVyIGJlZW4gbG9hZGVkLlxuICAgKi9cbiAgbGFiZWxGb3IoZW50aXR5S2V5OiBzdHJpbmcsIHZhbHVlOiB1bmtub3duLCBsYW5nID0gJ2VuJyk6IHN0cmluZyB8IHVuZGVmaW5lZCB7XG4gICAgcmV0dXJuIHRoaXMubGFiZWxzLmdldCh0aGlzLmxhYmVsS2V5KGVudGl0eUtleSwgbGFuZywgdmFsdWUpKTtcbiAgfVxuXG4gIC8qKiBEcm9wIGV2ZXJ5dGhpbmcgY2FjaGVkIGZvciBvbmUgZW50aXR5LCBsZWF2aW5nIG90aGVyIGVudGl0aWVzIGludGFjdC4gKi9cbiAgaW52YWxpZGF0ZShlbnRpdHlLZXk6IHN0cmluZyk6IHZvaWQge1xuICAgIGZvciAoY29uc3Qga2V5IG9mIHRoaXMuc3RvcmUua2V5cygpKSB7XG4gICAgICBpZiAoZW50aXR5S2V5RnJvbUNhY2hlS2V5KGtleSkgPT09IGVudGl0eUtleSkgdGhpcy5zdG9yZS5kZWxldGUoa2V5KTtcbiAgICB9XG4gICAgZm9yIChjb25zdCBrZXkgb2YgWy4uLnRoaXMuaW5GbGlnaHQua2V5cygpXSkge1xuICAgICAgaWYgKGVudGl0eUtleUZyb21DYWNoZUtleShrZXkpID09PSBlbnRpdHlLZXkpIHRoaXMuaW5GbGlnaHQuZGVsZXRlKGtleSk7XG4gICAgfVxuICAgIGNvbnN0IHByZWZpeCA9IGAke2VudGl0eUtleX0ke0xBQkVMX1NFUH1gO1xuICAgIGZvciAoY29uc3Qga2V5IG9mIFsuLi50aGlzLmxhYmVscy5rZXlzKCldKSB7XG4gICAgICBpZiAoa2V5LnN0YXJ0c1dpdGgocHJlZml4KSkgdGhpcy5sYWJlbHMuZGVsZXRlKGtleSk7XG4gICAgfVxuICB9XG5cbiAgY2xlYXIoKTogdm9pZCB7XG4gICAgdGhpcy5zdG9yZS5jbGVhcigpO1xuICAgIHRoaXMuaW5GbGlnaHQuY2xlYXIoKTtcbiAgICB0aGlzLmxhYmVscy5jbGVhcigpO1xuICB9XG5cbiAgcHJpdmF0ZSByZW1lbWJlckxhYmVscyhlbnRpdHlLZXk6IHN0cmluZywgbGFuZzogc3RyaW5nLCBvcHRpb25zOiBSZWZlcmVuY2VPcHRpb25bXSk6IHZvaWQge1xuICAgIGZvciAoY29uc3Qgb3B0aW9uIG9mIG9wdGlvbnMpIHtcbiAgICAgIHRoaXMubGFiZWxzLnNldCh0aGlzLmxhYmVsS2V5KGVudGl0eUtleSwgbGFuZywgb3B0aW9uLnZhbHVlKSwgb3B0aW9uLmxhYmVsKTtcbiAgICB9XG4gIH1cblxuICAvKiogTGFiZWwtY2FjaGUga2V5LiBBbiBvYmplY3QgdmFsdWUgY29sbGFwc2VzIHRvIGl0cyByZXNvbHZlZCB0ZXh0IGZvciB0aGUgYWN0aXZlIGxhbmd1YWdlLiAqL1xuICBwcml2YXRlIGxhYmVsS2V5KGVudGl0eUtleTogc3RyaW5nLCBsYW5nOiBzdHJpbmcsIHZhbHVlOiB1bmtub3duKTogc3RyaW5nIHtcbiAgICBjb25zdCBjYW5vbmljYWwgPVxuICAgICAgdmFsdWUgIT09IG51bGwgJiYgdHlwZW9mIHZhbHVlID09PSAnb2JqZWN0J1xuICAgICAgICA/IHJlc29sdmVMYWJlbCh2YWx1ZSBhcyBSZWNvcmQ8c3RyaW5nLCBzdHJpbmc+LCBsYW5nKVxuICAgICAgICA6IFN0cmluZyh2YWx1ZSA/PyAnJyk7XG4gICAgcmV0dXJuIFtlbnRpdHlLZXksIGxhbmcsIGNhbm9uaWNhbF0uam9pbihMQUJFTF9TRVApO1xuICB9XG5cbiAgLy8g4pSA4pSA4pSAIExvYWRlciByZXN1bHQgY29lcmNpb24gKGFycmF5IHwgUHJvbWlzZSB8IE9ic2VydmFibGUpIOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgFxuXG4gIHByaXZhdGUgaW52b2tlKFxuICAgIGxvYWRlcjogRW50aXR5UmVmZXJlbmNlTG9hZGVyLFxuICAgIGN0eDogUmVmZXJlbmNlTG9hZGVyQ29udGV4dCxcbiAgKTogUHJvbWlzZTxSZWZlcmVuY2VPcHRpb25bXT4ge1xuICAgIGxldCByZXN1bHQ6IFJlZmVyZW5jZUxvYWRlclJlc3VsdDtcbiAgICB0cnkge1xuICAgICAgcmVzdWx0ID0gbG9hZGVyKGN0eCk7XG4gICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICAvLyBSZWplY3QgcmF0aGVyIHRoYW4gcmVzb2x2ZSBlbXB0eTogYGxvYWRgIG11c3QgYmUgYWJsZSB0byB0ZWxsIGZhaWx1cmUgZnJvbVxuICAgICAgLy8gXCJubyBtYXRjaGVzXCIsIG9yIGl0IHdvdWxkIGNhY2hlIHRoZSBmYWlsdXJlLlxuICAgICAgcmV0dXJuIFByb21pc2UucmVqZWN0KGVycik7XG4gICAgfVxuICAgIHJldHVybiB0aGlzLnRvUHJvbWlzZShyZXN1bHQpO1xuICB9XG5cbiAgcHJpdmF0ZSB0b1Byb21pc2UocmVzdWx0OiBSZWZlcmVuY2VMb2FkZXJSZXN1bHQpOiBQcm9taXNlPFJlZmVyZW5jZU9wdGlvbltdPiB7XG4gICAgaWYgKEFycmF5LmlzQXJyYXkocmVzdWx0KSkgcmV0dXJuIFByb21pc2UucmVzb2x2ZShyZXN1bHQpO1xuICAgIGlmICh0aGlzLmlzU3Vic2NyaWJhYmxlKHJlc3VsdCkpIHtcbiAgICAgIC8vIEZpcnN0IGVtaXNzaW9uIHdpbnMsIHNvIGFuIE9ic2VydmFibGUgdGhhdCBzdGF5cyBvcGVuIHN0aWxsIHJlc29sdmVzIHRoZSBsb2FkLlxuICAgICAgcmV0dXJuIG5ldyBQcm9taXNlPFJlZmVyZW5jZU9wdGlvbltdPigocmVzb2x2ZSwgcmVqZWN0KSA9PiB7XG4gICAgICAgIGxldCBzZXR0bGVkID0gZmFsc2U7XG4gICAgICAgIGNvbnN0IHNldHRsZSA9IChmbjogKCkgPT4gdm9pZCkgPT4ge1xuICAgICAgICAgIGlmIChzZXR0bGVkKSByZXR1cm47XG4gICAgICAgICAgc2V0dGxlZCA9IHRydWU7XG4gICAgICAgICAgZm4oKTtcbiAgICAgICAgfTtcbiAgICAgICAgcmVzdWx0LnN1YnNjcmliZSh7XG4gICAgICAgICAgbmV4dDogdmFsdWUgPT4gc2V0dGxlKCgpID0+IHJlc29sdmUodmFsdWUgPz8gW10pKSxcbiAgICAgICAgICAvLyBBbiBlcnJvcmluZyBzdHJlYW0gaXMgYSBmYWlsZWQgbG9hZCwgbm90IGFuIGVtcHR5IG9uZSDigJQgc2VlIGBpbnZva2VgLlxuICAgICAgICAgIGVycm9yOiBlcnIgPT4gc2V0dGxlKCgpID0+IHJlamVjdChlcnIpKSxcbiAgICAgICAgICAvLyBDb21wbGV0aW5nIHdpdGhvdXQgZW1pdHRpbmcgaXMgYSBsZWdpdGltYXRlIGVtcHR5IHJlc3VsdCwgYW5kIGlzIGNhY2hlZC5cbiAgICAgICAgICBjb21wbGV0ZTogKCkgPT4gc2V0dGxlKCgpID0+IHJlc29sdmUoW10pKSxcbiAgICAgICAgfSk7XG4gICAgICB9KTtcbiAgICB9XG4gICAgcmV0dXJuIFByb21pc2UucmVzb2x2ZShyZXN1bHQgYXMgUHJvbWlzZTxSZWZlcmVuY2VPcHRpb25bXT4pO1xuICB9XG5cbiAgcHJpdmF0ZSBpc1N1YnNjcmliYWJsZSh2YWx1ZTogdW5rbm93bik6IHZhbHVlIGlzIFN1YnNjcmliYWJsZTxSZWZlcmVuY2VPcHRpb25bXT4ge1xuICAgIHJldHVybiAoXG4gICAgICB0eXBlb2YgdmFsdWUgPT09ICdvYmplY3QnICYmXG4gICAgICB2YWx1ZSAhPT0gbnVsbCAmJlxuICAgICAgdHlwZW9mICh2YWx1ZSBhcyBTdWJzY3JpYmFibGU8UmVmZXJlbmNlT3B0aW9uW10+KS5zdWJzY3JpYmUgPT09ICdmdW5jdGlvbidcbiAgICApO1xuICB9XG5cbiAgLyoqIEV4cG9zZWQgZm9yIGNhc2NhZGUgZmlsdGVyaW5nLCB3aGljaCBtYXRjaGVzIGEgcGFyZW50IHZhbHVlIGFnYWluc3Qgb3B0aW9uIHZhbHVlcy4gKi9cbiAgbWF0Y2hlcyhhOiB1bmtub3duLCBiOiB1bmtub3duLCBsYW5nID0gJ2VuJyk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB2YWx1ZXNNYXRjaChhLCBiLCBsYW5nKTtcbiAgfVxufVxuIl19
@@ -1,55 +0,0 @@
1
- import { Injectable, inject } from '@angular/core';
2
- import { FIELD_TYPE_REGISTRY, FIELD_TYPE_SETS } from '../tokens/injection-tokens';
3
- import * as i0 from "@angular/core";
4
- /**
5
- * FieldRegistryService — resolves field type strings to Angular component classes.
6
- *
7
- * **Tree-shaking contract:** this service holds *no* static imports of field components.
8
- * Nothing is bundled until something registers it, which is what makes the built-ins
9
- * opt-in. Register them with `provideBuiltInFieldTypes()` (all 19 keys) or a narrower
10
- * subset via `provideFieldTypes({ ... })` — see `providers/provide-field-types.ts`.
11
- *
12
- * Resolution order: consumer token registry → runtime registrations → nothing.
13
- */
14
- export class FieldRegistryService {
15
- consumerRegistry = inject(FIELD_TYPE_REGISTRY, { optional: true }) ?? new Map();
16
- dynamicRegistry = new Map();
17
- constructor() {
18
- // Sets contributed by provideFieldTypes()/provideBuiltInFieldTypes(), in declaration order.
19
- for (const set of inject(FIELD_TYPE_SETS, { optional: true }) ?? []) {
20
- this.registerAll(set);
21
- }
22
- }
23
- /** Register a field type component mapping at runtime. */
24
- register(type, component) {
25
- this.dynamicRegistry.set(type, component);
26
- }
27
- /** Register multiple field type component mappings at runtime. */
28
- registerAll(map) {
29
- for (const [type, comp] of Object.entries(map)) {
30
- this.dynamicRegistry.set(type, comp);
31
- }
32
- }
33
- /**
34
- * Resolve a field type string to a component class.
35
- * Consumer token registry takes priority over runtime registrations.
36
- */
37
- resolve(fieldType) {
38
- return this.consumerRegistry.get(fieldType) ?? this.dynamicRegistry.get(fieldType) ?? null;
39
- }
40
- /** Check if a field type has a registered component. */
41
- has(fieldType) {
42
- return this.consumerRegistry.has(fieldType) || this.dynamicRegistry.has(fieldType);
43
- }
44
- /** Every registered field type key. Consumer overrides and runtime registrations combined. */
45
- registeredTypes() {
46
- return [...new Set([...this.dynamicRegistry.keys(), ...this.consumerRegistry.keys()])].sort();
47
- }
48
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FieldRegistryService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
49
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FieldRegistryService, providedIn: 'root' });
50
- }
51
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FieldRegistryService, decorators: [{
52
- type: Injectable,
53
- args: [{ providedIn: 'root' }]
54
- }], ctorParameters: () => [] });
55
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmllbGQtcmVnaXN0cnkuc2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9saWIvc2VydmljZXMvZmllbGQtcmVnaXN0cnkuc2VydmljZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsVUFBVSxFQUFRLE1BQU0sRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUN6RCxPQUFPLEVBQUUsbUJBQW1CLEVBQUUsZUFBZSxFQUFFLE1BQU0sNEJBQTRCLENBQUM7O0FBRWxGOzs7Ozs7Ozs7R0FTRztBQUVILE1BQU0sT0FBTyxvQkFBb0I7SUFDZCxnQkFBZ0IsR0FDL0IsTUFBTSxDQUFDLG1CQUFtQixFQUFFLEVBQUUsUUFBUSxFQUFFLElBQUksRUFBRSxDQUFDLElBQUksSUFBSSxHQUFHLEVBQXFCLENBQUM7SUFDakUsZUFBZSxHQUFHLElBQUksR0FBRyxFQUFxQixDQUFDO0lBRWhFO1FBQ0UsNEZBQTRGO1FBQzVGLEtBQUssTUFBTSxHQUFHLElBQUksTUFBTSxDQUFDLGVBQWUsRUFBRSxFQUFFLFFBQVEsRUFBRSxJQUFJLEVBQUUsQ0FBQyxJQUFJLEVBQUUsRUFBRSxDQUFDO1lBQ3BFLElBQUksQ0FBQyxXQUFXLENBQUMsR0FBRyxDQUFDLENBQUM7UUFDeEIsQ0FBQztJQUNILENBQUM7SUFFRCwwREFBMEQ7SUFDMUQsUUFBUSxDQUFDLElBQVksRUFBRSxTQUFvQjtRQUN6QyxJQUFJLENBQUMsZUFBZSxDQUFDLEdBQUcsQ0FBQyxJQUFJLEVBQUUsU0FBUyxDQUFDLENBQUM7SUFDNUMsQ0FBQztJQUVELGtFQUFrRTtJQUNsRSxXQUFXLENBQUMsR0FBOEI7UUFDeEMsS0FBSyxNQUFNLENBQUMsSUFBSSxFQUFFLElBQUksQ0FBQyxJQUFJLE1BQU0sQ0FBQyxPQUFPLENBQUMsR0FBRyxDQUFDLEVBQUUsQ0FBQztZQUMvQyxJQUFJLENBQUMsZUFBZSxDQUFDLEdBQUcsQ0FBQyxJQUFJLEVBQUUsSUFBSSxDQUFDLENBQUM7UUFDdkMsQ0FBQztJQUNILENBQUM7SUFFRDs7O09BR0c7SUFDSCxPQUFPLENBQUMsU0FBaUI7UUFDdkIsT0FBTyxJQUFJLENBQUMsZ0JBQWdCLENBQUMsR0FBRyxDQUFDLFNBQVMsQ0FBQyxJQUFJLElBQUksQ0FBQyxlQUFlLENBQUMsR0FBRyxDQUFDLFNBQVMsQ0FBQyxJQUFJLElBQUksQ0FBQztJQUM3RixDQUFDO0lBRUQsd0RBQXdEO0lBQ3hELEdBQUcsQ0FBQyxTQUFpQjtRQUNuQixPQUFPLElBQUksQ0FBQyxnQkFBZ0IsQ0FBQyxHQUFHLENBQUMsU0FBUyxDQUFDLElBQUksSUFBSSxDQUFDLGVBQWUsQ0FBQyxHQUFHLENBQUMsU0FBUyxDQUFDLENBQUM7SUFDckYsQ0FBQztJQUVELDhGQUE4RjtJQUM5RixlQUFlO1FBQ2IsT0FBTyxDQUFDLEdBQUcsSUFBSSxHQUFHLENBQUMsQ0FBQyxHQUFHLElBQUksQ0FBQyxlQUFlLENBQUMsSUFBSSxFQUFFLEVBQUUsR0FBRyxJQUFJLENBQUMsZ0JBQWdCLENBQUMsSUFBSSxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUMsSUFBSSxFQUFFLENBQUM7SUFDaEcsQ0FBQzt3R0F4Q1Usb0JBQW9COzRHQUFwQixvQkFBb0IsY0FEUCxNQUFNOzs0RkFDbkIsb0JBQW9CO2tCQURoQyxVQUFVO21CQUFDLEVBQUUsVUFBVSxFQUFFLE1BQU0sRUFBRSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IEluamVjdGFibGUsIFR5cGUsIGluamVjdCB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgRklFTERfVFlQRV9SRUdJU1RSWSwgRklFTERfVFlQRV9TRVRTIH0gZnJvbSAnLi4vdG9rZW5zL2luamVjdGlvbi10b2tlbnMnO1xuXG4vKipcbiAqIEZpZWxkUmVnaXN0cnlTZXJ2aWNlIOKAlCByZXNvbHZlcyBmaWVsZCB0eXBlIHN0cmluZ3MgdG8gQW5ndWxhciBjb21wb25lbnQgY2xhc3Nlcy5cbiAqXG4gKiAqKlRyZWUtc2hha2luZyBjb250cmFjdDoqKiB0aGlzIHNlcnZpY2UgaG9sZHMgKm5vKiBzdGF0aWMgaW1wb3J0cyBvZiBmaWVsZCBjb21wb25lbnRzLlxuICogTm90aGluZyBpcyBidW5kbGVkIHVudGlsIHNvbWV0aGluZyByZWdpc3RlcnMgaXQsIHdoaWNoIGlzIHdoYXQgbWFrZXMgdGhlIGJ1aWx0LWluc1xuICogb3B0LWluLiBSZWdpc3RlciB0aGVtIHdpdGggYHByb3ZpZGVCdWlsdEluRmllbGRUeXBlcygpYCAoYWxsIDE5IGtleXMpIG9yIGEgbmFycm93ZXJcbiAqIHN1YnNldCB2aWEgYHByb3ZpZGVGaWVsZFR5cGVzKHsgLi4uIH0pYCDigJQgc2VlIGBwcm92aWRlcnMvcHJvdmlkZS1maWVsZC10eXBlcy50c2AuXG4gKlxuICogUmVzb2x1dGlvbiBvcmRlcjogY29uc3VtZXIgdG9rZW4gcmVnaXN0cnkg4oaSIHJ1bnRpbWUgcmVnaXN0cmF0aW9ucyDihpIgbm90aGluZy5cbiAqL1xuQEluamVjdGFibGUoeyBwcm92aWRlZEluOiAncm9vdCcgfSlcbmV4cG9ydCBjbGFzcyBGaWVsZFJlZ2lzdHJ5U2VydmljZSB7XG4gIHByaXZhdGUgcmVhZG9ubHkgY29uc3VtZXJSZWdpc3RyeSA9XG4gICAgaW5qZWN0KEZJRUxEX1RZUEVfUkVHSVNUUlksIHsgb3B0aW9uYWw6IHRydWUgfSkgPz8gbmV3IE1hcDxzdHJpbmcsIFR5cGU8YW55Pj4oKTtcbiAgcHJpdmF0ZSByZWFkb25seSBkeW5hbWljUmVnaXN0cnkgPSBuZXcgTWFwPHN0cmluZywgVHlwZTxhbnk+PigpO1xuXG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIC8vIFNldHMgY29udHJpYnV0ZWQgYnkgcHJvdmlkZUZpZWxkVHlwZXMoKS9wcm92aWRlQnVpbHRJbkZpZWxkVHlwZXMoKSwgaW4gZGVjbGFyYXRpb24gb3JkZXIuXG4gICAgZm9yIChjb25zdCBzZXQgb2YgaW5qZWN0KEZJRUxEX1RZUEVfU0VUUywgeyBvcHRpb25hbDogdHJ1ZSB9KSA/PyBbXSkge1xuICAgICAgdGhpcy5yZWdpc3RlckFsbChzZXQpO1xuICAgIH1cbiAgfVxuXG4gIC8qKiBSZWdpc3RlciBhIGZpZWxkIHR5cGUgY29tcG9uZW50IG1hcHBpbmcgYXQgcnVudGltZS4gKi9cbiAgcmVnaXN0ZXIodHlwZTogc3RyaW5nLCBjb21wb25lbnQ6IFR5cGU8YW55Pik6IHZvaWQge1xuICAgIHRoaXMuZHluYW1pY1JlZ2lzdHJ5LnNldCh0eXBlLCBjb21wb25lbnQpO1xuICB9XG5cbiAgLyoqIFJlZ2lzdGVyIG11bHRpcGxlIGZpZWxkIHR5cGUgY29tcG9uZW50IG1hcHBpbmdzIGF0IHJ1bnRpbWUuICovXG4gIHJlZ2lzdGVyQWxsKG1hcDogUmVjb3JkPHN0cmluZywgVHlwZTxhbnk+Pik6IHZvaWQge1xuICAgIGZvciAoY29uc3QgW3R5cGUsIGNvbXBdIG9mIE9iamVjdC5lbnRyaWVzKG1hcCkpIHtcbiAgICAgIHRoaXMuZHluYW1pY1JlZ2lzdHJ5LnNldCh0eXBlLCBjb21wKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogUmVzb2x2ZSBhIGZpZWxkIHR5cGUgc3RyaW5nIHRvIGEgY29tcG9uZW50IGNsYXNzLlxuICAgKiBDb25zdW1lciB0b2tlbiByZWdpc3RyeSB0YWtlcyBwcmlvcml0eSBvdmVyIHJ1bnRpbWUgcmVnaXN0cmF0aW9ucy5cbiAgICovXG4gIHJlc29sdmUoZmllbGRUeXBlOiBzdHJpbmcpOiBUeXBlPGFueT4gfCBudWxsIHtcbiAgICByZXR1cm4gdGhpcy5jb25zdW1lclJlZ2lzdHJ5LmdldChmaWVsZFR5cGUpID8/IHRoaXMuZHluYW1pY1JlZ2lzdHJ5LmdldChmaWVsZFR5cGUpID8/IG51bGw7XG4gIH1cblxuICAvKiogQ2hlY2sgaWYgYSBmaWVsZCB0eXBlIGhhcyBhIHJlZ2lzdGVyZWQgY29tcG9uZW50LiAqL1xuICBoYXMoZmllbGRUeXBlOiBzdHJpbmcpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5jb25zdW1lclJlZ2lzdHJ5LmhhcyhmaWVsZFR5cGUpIHx8IHRoaXMuZHluYW1pY1JlZ2lzdHJ5LmhhcyhmaWVsZFR5cGUpO1xuICB9XG5cbiAgLyoqIEV2ZXJ5IHJlZ2lzdGVyZWQgZmllbGQgdHlwZSBrZXkuIENvbnN1bWVyIG92ZXJyaWRlcyBhbmQgcnVudGltZSByZWdpc3RyYXRpb25zIGNvbWJpbmVkLiAqL1xuICByZWdpc3RlcmVkVHlwZXMoKTogc3RyaW5nW10ge1xuICAgIHJldHVybiBbLi4ubmV3IFNldChbLi4udGhpcy5keW5hbWljUmVnaXN0cnkua2V5cygpLCAuLi50aGlzLmNvbnN1bWVyUmVnaXN0cnkua2V5cygpXSldLnNvcnQoKTtcbiAgfVxufVxuIl19
@@ -1,89 +0,0 @@
1
- import { Injectable, inject } from '@angular/core';
2
- import { UPLOAD_HANDLER } from '../tokens/injection-tokens';
3
- import * as i0 from "@angular/core";
4
- /**
5
- * FileUploadService — the single place image-field and file-field agree on how a
6
- * selected `File` becomes a `FileRef`.
7
- *
8
- * With `UPLOAD_HANDLER` registered the file is persisted and stored as `{ url }`;
9
- * without one it is stored as `{ file }` for the consumer to upload at submit time.
10
- */
11
- export class FileUploadService {
12
- handler = inject(UPLOAD_HANDLER, { optional: true });
13
- get hasHandler() {
14
- return !!this.handler;
15
- }
16
- /** Metadata common to both persisted and unpersisted refs. */
17
- describe(file) {
18
- return { name: file.name, size: file.size, mimeType: file.type };
19
- }
20
- /**
21
- * Turn a selected File into the value to store on the control.
22
- * @throws when a registered handler rejects — callers surface it as a field error.
23
- */
24
- async toFileRef(file) {
25
- const meta = this.describe(file);
26
- if (!this.handler)
27
- return { ...meta, file };
28
- const result = await this.normalize(this.handler(file));
29
- return { ...meta, url: result.url, name: result.name ?? meta.name };
30
- }
31
- /** Object URL for previewing an unpersisted File. Callers must revoke it. */
32
- previewUrlFor(ref) {
33
- if (!ref)
34
- return null;
35
- if (ref.url)
36
- return ref.url;
37
- if (ref.file && typeof URL !== 'undefined' && typeof URL.createObjectURL === 'function') {
38
- return URL.createObjectURL(ref.file);
39
- }
40
- return null;
41
- }
42
- revokePreviewUrl(url) {
43
- if (!url || !url.startsWith('blob:'))
44
- return;
45
- if (typeof URL !== 'undefined' && typeof URL.revokeObjectURL === 'function') {
46
- URL.revokeObjectURL(url);
47
- }
48
- }
49
- normalize(result) {
50
- if (this.isSubscribable(result)) {
51
- return new Promise((resolve, reject) => {
52
- let settled = false;
53
- result.subscribe({
54
- next: value => {
55
- if (settled)
56
- return;
57
- settled = true;
58
- resolve(value);
59
- },
60
- error: err => {
61
- if (settled)
62
- return;
63
- settled = true;
64
- reject(err);
65
- },
66
- complete: () => {
67
- if (settled)
68
- return;
69
- settled = true;
70
- reject(new Error('Upload handler completed without emitting a result.'));
71
- },
72
- });
73
- });
74
- }
75
- return Promise.resolve(result);
76
- }
77
- isSubscribable(value) {
78
- return (typeof value === 'object' &&
79
- value !== null &&
80
- typeof value.subscribe === 'function');
81
- }
82
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FileUploadService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
83
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FileUploadService, providedIn: 'root' });
84
- }
85
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FileUploadService, decorators: [{
86
- type: Injectable,
87
- args: [{ providedIn: 'root' }]
88
- }] });
89
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmlsZS11cGxvYWQuc2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9saWIvc2VydmljZXMvZmlsZS11cGxvYWQuc2VydmljZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUVuRCxPQUFPLEVBQUUsY0FBYyxFQUFFLE1BQU0sNEJBQTRCLENBQUM7O0FBRTVEOzs7Ozs7R0FNRztBQUVILE1BQU0sT0FBTyxpQkFBaUI7SUFDWCxPQUFPLEdBQUcsTUFBTSxDQUFDLGNBQWMsRUFBRSxFQUFFLFFBQVEsRUFBRSxJQUFJLEVBQUUsQ0FBQyxDQUFDO0lBRXRFLElBQUksVUFBVTtRQUNaLE9BQU8sQ0FBQyxDQUFDLElBQUksQ0FBQyxPQUFPLENBQUM7SUFDeEIsQ0FBQztJQUVELDhEQUE4RDtJQUN0RCxRQUFRLENBQUMsSUFBVTtRQUN6QixPQUFPLEVBQUUsSUFBSSxFQUFFLElBQUksQ0FBQyxJQUFJLEVBQUUsSUFBSSxFQUFFLElBQUksQ0FBQyxJQUFJLEVBQUUsUUFBUSxFQUFFLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNuRSxDQUFDO0lBRUQ7OztPQUdHO0lBQ0gsS0FBSyxDQUFDLFNBQVMsQ0FBQyxJQUFVO1FBQ3hCLE1BQU0sSUFBSSxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDakMsSUFBSSxDQUFDLElBQUksQ0FBQyxPQUFPO1lBQUUsT0FBTyxFQUFFLEdBQUcsSUFBSSxFQUFFLElBQUksRUFBRSxDQUFDO1FBRTVDLE1BQU0sTUFBTSxHQUFHLE1BQU0sSUFBSSxDQUFDLFNBQVMsQ0FBQyxJQUFJLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUM7UUFDeEQsT0FBTyxFQUFFLEdBQUcsSUFBSSxFQUFFLEdBQUcsRUFBRSxNQUFNLENBQUMsR0FBRyxFQUFFLElBQUksRUFBRSxNQUFNLENBQUMsSUFBSSxJQUFJLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUN0RSxDQUFDO0lBRUQsNkVBQTZFO0lBQzdFLGFBQWEsQ0FBQyxHQUErQjtRQUMzQyxJQUFJLENBQUMsR0FBRztZQUFFLE9BQU8sSUFBSSxDQUFDO1FBQ3RCLElBQUksR0FBRyxDQUFDLEdBQUc7WUFBRSxPQUFPLEdBQUcsQ0FBQyxHQUFHLENBQUM7UUFDNUIsSUFBSSxHQUFHLENBQUMsSUFBSSxJQUFJLE9BQU8sR0FBRyxLQUFLLFdBQVcsSUFBSSxPQUFPLEdBQUcsQ0FBQyxlQUFlLEtBQUssVUFBVSxFQUFFLENBQUM7WUFDeEYsT0FBTyxHQUFHLENBQUMsZUFBZSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUN2QyxDQUFDO1FBQ0QsT0FBTyxJQUFJLENBQUM7SUFDZCxDQUFDO0lBRUQsZ0JBQWdCLENBQUMsR0FBa0I7UUFDakMsSUFBSSxDQUFDLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxVQUFVLENBQUMsT0FBTyxDQUFDO1lBQUUsT0FBTztRQUM3QyxJQUFJLE9BQU8sR0FBRyxLQUFLLFdBQVcsSUFBSSxPQUFPLEdBQUcsQ0FBQyxlQUFlLEtBQUssVUFBVSxFQUFFLENBQUM7WUFDNUUsR0FBRyxDQUFDLGVBQWUsQ0FBQyxHQUFHLENBQUMsQ0FBQztRQUMzQixDQUFDO0lBQ0gsQ0FBQztJQUVPLFNBQVMsQ0FDZixNQUF5RTtRQUV6RSxJQUFJLElBQUksQ0FBQyxjQUFjLENBQUMsTUFBTSxDQUFDLEVBQUUsQ0FBQztZQUNoQyxPQUFPLElBQUksT0FBTyxDQUFlLENBQUMsT0FBTyxFQUFFLE1BQU0sRUFBRSxFQUFFO2dCQUNuRCxJQUFJLE9BQU8sR0FBRyxLQUFLLENBQUM7Z0JBQ3BCLE1BQU0sQ0FBQyxTQUFTLENBQUM7b0JBQ2YsSUFBSSxFQUFFLEtBQUssQ0FBQyxFQUFFO3dCQUNaLElBQUksT0FBTzs0QkFBRSxPQUFPO3dCQUNwQixPQUFPLEdBQUcsSUFBSSxDQUFDO3dCQUNmLE9BQU8sQ0FBQyxLQUFLLENBQUMsQ0FBQztvQkFDakIsQ0FBQztvQkFDRCxLQUFLLEVBQUUsR0FBRyxDQUFDLEVBQUU7d0JBQ1gsSUFBSSxPQUFPOzRCQUFFLE9BQU87d0JBQ3BCLE9BQU8sR0FBRyxJQUFJLENBQUM7d0JBQ2YsTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDO29CQUNkLENBQUM7b0JBQ0QsUUFBUSxFQUFFLEdBQUcsRUFBRTt3QkFDYixJQUFJLE9BQU87NEJBQUUsT0FBTzt3QkFDcEIsT0FBTyxHQUFHLElBQUksQ0FBQzt3QkFDZixNQUFNLENBQUMsSUFBSSxLQUFLLENBQUMscURBQXFELENBQUMsQ0FBQyxDQUFDO29CQUMzRSxDQUFDO2lCQUNGLENBQUMsQ0FBQztZQUNMLENBQUMsQ0FBQyxDQUFDO1FBQ0wsQ0FBQztRQUNELE9BQU8sT0FBTyxDQUFDLE9BQU8sQ0FBQyxNQUE4QyxDQUFDLENBQUM7SUFDekUsQ0FBQztJQUVPLGNBQWMsQ0FBQyxLQUFjO1FBQ25DLE9BQU8sQ0FDTCxPQUFPLEtBQUssS0FBSyxRQUFRO1lBQ3pCLEtBQUssS0FBSyxJQUFJO1lBQ2QsT0FBUSxLQUFvQyxDQUFDLFNBQVMsS0FBSyxVQUFVLENBQ3RFLENBQUM7SUFDSixDQUFDO3dHQTNFVSxpQkFBaUI7NEdBQWpCLGlCQUFpQixjQURKLE1BQU07OzRGQUNuQixpQkFBaUI7a0JBRDdCLFVBQVU7bUJBQUMsRUFBRSxVQUFVLEVBQUUsTUFBTSxFQUFFIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSwgaW5qZWN0IH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgdHlwZSB7IEZpbGVSZWYsIFN1YnNjcmliYWJsZSwgVXBsb2FkUmVzdWx0IH0gZnJvbSAnQGR5bmFtaWMtZW50aXR5L2NvcmUnO1xuaW1wb3J0IHsgVVBMT0FEX0hBTkRMRVIgfSBmcm9tICcuLi90b2tlbnMvaW5qZWN0aW9uLXRva2Vucyc7XG5cbi8qKlxuICogRmlsZVVwbG9hZFNlcnZpY2Ug4oCUIHRoZSBzaW5nbGUgcGxhY2UgaW1hZ2UtZmllbGQgYW5kIGZpbGUtZmllbGQgYWdyZWUgb24gaG93IGFcbiAqIHNlbGVjdGVkIGBGaWxlYCBiZWNvbWVzIGEgYEZpbGVSZWZgLlxuICpcbiAqIFdpdGggYFVQTE9BRF9IQU5ETEVSYCByZWdpc3RlcmVkIHRoZSBmaWxlIGlzIHBlcnNpc3RlZCBhbmQgc3RvcmVkIGFzIGB7IHVybCB9YDtcbiAqIHdpdGhvdXQgb25lIGl0IGlzIHN0b3JlZCBhcyBgeyBmaWxlIH1gIGZvciB0aGUgY29uc3VtZXIgdG8gdXBsb2FkIGF0IHN1Ym1pdCB0aW1lLlxuICovXG5ASW5qZWN0YWJsZSh7IHByb3ZpZGVkSW46ICdyb290JyB9KVxuZXhwb3J0IGNsYXNzIEZpbGVVcGxvYWRTZXJ2aWNlIHtcbiAgcHJpdmF0ZSByZWFkb25seSBoYW5kbGVyID0gaW5qZWN0KFVQTE9BRF9IQU5ETEVSLCB7IG9wdGlvbmFsOiB0cnVlIH0pO1xuXG4gIGdldCBoYXNIYW5kbGVyKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiAhIXRoaXMuaGFuZGxlcjtcbiAgfVxuXG4gIC8qKiBNZXRhZGF0YSBjb21tb24gdG8gYm90aCBwZXJzaXN0ZWQgYW5kIHVucGVyc2lzdGVkIHJlZnMuICovXG4gIHByaXZhdGUgZGVzY3JpYmUoZmlsZTogRmlsZSk6IEZpbGVSZWYge1xuICAgIHJldHVybiB7IG5hbWU6IGZpbGUubmFtZSwgc2l6ZTogZmlsZS5zaXplLCBtaW1lVHlwZTogZmlsZS50eXBlIH07XG4gIH1cblxuICAvKipcbiAgICogVHVybiBhIHNlbGVjdGVkIEZpbGUgaW50byB0aGUgdmFsdWUgdG8gc3RvcmUgb24gdGhlIGNvbnRyb2wuXG4gICAqIEB0aHJvd3Mgd2hlbiBhIHJlZ2lzdGVyZWQgaGFuZGxlciByZWplY3RzIOKAlCBjYWxsZXJzIHN1cmZhY2UgaXQgYXMgYSBmaWVsZCBlcnJvci5cbiAgICovXG4gIGFzeW5jIHRvRmlsZVJlZihmaWxlOiBGaWxlKTogUHJvbWlzZTxGaWxlUmVmPiB7XG4gICAgY29uc3QgbWV0YSA9IHRoaXMuZGVzY3JpYmUoZmlsZSk7XG4gICAgaWYgKCF0aGlzLmhhbmRsZXIpIHJldHVybiB7IC4uLm1ldGEsIGZpbGUgfTtcblxuICAgIGNvbnN0IHJlc3VsdCA9IGF3YWl0IHRoaXMubm9ybWFsaXplKHRoaXMuaGFuZGxlcihmaWxlKSk7XG4gICAgcmV0dXJuIHsgLi4ubWV0YSwgdXJsOiByZXN1bHQudXJsLCBuYW1lOiByZXN1bHQubmFtZSA/PyBtZXRhLm5hbWUgfTtcbiAgfVxuXG4gIC8qKiBPYmplY3QgVVJMIGZvciBwcmV2aWV3aW5nIGFuIHVucGVyc2lzdGVkIEZpbGUuIENhbGxlcnMgbXVzdCByZXZva2UgaXQuICovXG4gIHByZXZpZXdVcmxGb3IocmVmOiBGaWxlUmVmIHwgbnVsbCB8IHVuZGVmaW5lZCk6IHN0cmluZyB8IG51bGwge1xuICAgIGlmICghcmVmKSByZXR1cm4gbnVsbDtcbiAgICBpZiAocmVmLnVybCkgcmV0dXJuIHJlZi51cmw7XG4gICAgaWYgKHJlZi5maWxlICYmIHR5cGVvZiBVUkwgIT09ICd1bmRlZmluZWQnICYmIHR5cGVvZiBVUkwuY3JlYXRlT2JqZWN0VVJMID09PSAnZnVuY3Rpb24nKSB7XG4gICAgICByZXR1cm4gVVJMLmNyZWF0ZU9iamVjdFVSTChyZWYuZmlsZSk7XG4gICAgfVxuICAgIHJldHVybiBudWxsO1xuICB9XG5cbiAgcmV2b2tlUHJldmlld1VybCh1cmw6IHN0cmluZyB8IG51bGwpOiB2b2lkIHtcbiAgICBpZiAoIXVybCB8fCAhdXJsLnN0YXJ0c1dpdGgoJ2Jsb2I6JykpIHJldHVybjtcbiAgICBpZiAodHlwZW9mIFVSTCAhPT0gJ3VuZGVmaW5lZCcgJiYgdHlwZW9mIFVSTC5yZXZva2VPYmplY3RVUkwgPT09ICdmdW5jdGlvbicpIHtcbiAgICAgIFVSTC5yZXZva2VPYmplY3RVUkwodXJsKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIG5vcm1hbGl6ZShcbiAgICByZXN1bHQ6IFVwbG9hZFJlc3VsdCB8IFByb21pc2U8VXBsb2FkUmVzdWx0PiB8IFN1YnNjcmliYWJsZTxVcGxvYWRSZXN1bHQ+LFxuICApOiBQcm9taXNlPFVwbG9hZFJlc3VsdD4ge1xuICAgIGlmICh0aGlzLmlzU3Vic2NyaWJhYmxlKHJlc3VsdCkpIHtcbiAgICAgIHJldHVybiBuZXcgUHJvbWlzZTxVcGxvYWRSZXN1bHQ+KChyZXNvbHZlLCByZWplY3QpID0+IHtcbiAgICAgICAgbGV0IHNldHRsZWQgPSBmYWxzZTtcbiAgICAgICAgcmVzdWx0LnN1YnNjcmliZSh7XG4gICAgICAgICAgbmV4dDogdmFsdWUgPT4ge1xuICAgICAgICAgICAgaWYgKHNldHRsZWQpIHJldHVybjtcbiAgICAgICAgICAgIHNldHRsZWQgPSB0cnVlO1xuICAgICAgICAgICAgcmVzb2x2ZSh2YWx1ZSk7XG4gICAgICAgICAgfSxcbiAgICAgICAgICBlcnJvcjogZXJyID0+IHtcbiAgICAgICAgICAgIGlmIChzZXR0bGVkKSByZXR1cm47XG4gICAgICAgICAgICBzZXR0bGVkID0gdHJ1ZTtcbiAgICAgICAgICAgIHJlamVjdChlcnIpO1xuICAgICAgICAgIH0sXG4gICAgICAgICAgY29tcGxldGU6ICgpID0+IHtcbiAgICAgICAgICAgIGlmIChzZXR0bGVkKSByZXR1cm47XG4gICAgICAgICAgICBzZXR0bGVkID0gdHJ1ZTtcbiAgICAgICAgICAgIHJlamVjdChuZXcgRXJyb3IoJ1VwbG9hZCBoYW5kbGVyIGNvbXBsZXRlZCB3aXRob3V0IGVtaXR0aW5nIGEgcmVzdWx0LicpKTtcbiAgICAgICAgICB9LFxuICAgICAgICB9KTtcbiAgICAgIH0pO1xuICAgIH1cbiAgICByZXR1cm4gUHJvbWlzZS5yZXNvbHZlKHJlc3VsdCBhcyBVcGxvYWRSZXN1bHQgfCBQcm9taXNlPFVwbG9hZFJlc3VsdD4pO1xuICB9XG5cbiAgcHJpdmF0ZSBpc1N1YnNjcmliYWJsZSh2YWx1ZTogdW5rbm93bik6IHZhbHVlIGlzIFN1YnNjcmliYWJsZTxVcGxvYWRSZXN1bHQ+IHtcbiAgICByZXR1cm4gKFxuICAgICAgdHlwZW9mIHZhbHVlID09PSAnb2JqZWN0JyAmJlxuICAgICAgdmFsdWUgIT09IG51bGwgJiZcbiAgICAgIHR5cGVvZiAodmFsdWUgYXMgU3Vic2NyaWJhYmxlPFVwbG9hZFJlc3VsdD4pLnN1YnNjcmliZSA9PT0gJ2Z1bmN0aW9uJ1xuICAgICk7XG4gIH1cbn1cbiJdfQ==
@@ -1,26 +0,0 @@
1
- import { Injectable, inject } from '@angular/core';
2
- import { HOOK_REGISTRY } from '../tokens/injection-tokens';
3
- import * as i0 from "@angular/core";
4
- /**
5
- * HookRegistryService — stores and runs Angular-side pre/post hooks.
6
- * Consumers register hooks via provideNgxDynamicEntity({ hooks: { 'clients:beforeSave': fn } }).
7
- */
8
- export class HookRegistryService {
9
- registry = inject(HOOK_REGISTRY, { optional: true }) ?? new Map();
10
- has(key) {
11
- return this.registry.has(key);
12
- }
13
- async run(key, data, context = {}) {
14
- const hook = this.registry.get(key);
15
- if (!hook)
16
- return data;
17
- return hook(data, context);
18
- }
19
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: HookRegistryService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
20
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: HookRegistryService, providedIn: 'root' });
21
- }
22
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: HookRegistryService, decorators: [{
23
- type: Injectable,
24
- args: [{ providedIn: 'root' }]
25
- }] });
26
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaG9vay1yZWdpc3RyeS5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vc3JjL2xpYi9zZXJ2aWNlcy9ob29rLXJlZ2lzdHJ5LnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDbkQsT0FBTyxFQUFFLGFBQWEsRUFBRSxNQUFNLDRCQUE0QixDQUFDOztBQUUzRDs7O0dBR0c7QUFFSCxNQUFNLE9BQU8sbUJBQW1CO0lBQ2IsUUFBUSxHQUFHLE1BQU0sQ0FBQyxhQUFhLEVBQUUsRUFBRSxRQUFRLEVBQUUsSUFBSSxFQUFFLENBQUMsSUFBSSxJQUFJLEdBQUcsRUFBRSxDQUFDO0lBRW5GLEdBQUcsQ0FBQyxHQUFXO1FBQ2IsT0FBTyxJQUFJLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxHQUFHLENBQUMsQ0FBQztJQUNoQyxDQUFDO0lBRUQsS0FBSyxDQUFDLEdBQUcsQ0FBQyxHQUFXLEVBQUUsSUFBUyxFQUFFLFVBQWUsRUFBRTtRQUNqRCxNQUFNLElBQUksR0FBRyxJQUFJLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxHQUFHLENBQUMsQ0FBQztRQUNwQyxJQUFJLENBQUMsSUFBSTtZQUFFLE9BQU8sSUFBSSxDQUFDO1FBQ3ZCLE9BQU8sSUFBSSxDQUFDLElBQUksRUFBRSxPQUFPLENBQUMsQ0FBQztJQUM3QixDQUFDO3dHQVhVLG1CQUFtQjs0R0FBbkIsbUJBQW1CLGNBRE4sTUFBTTs7NEZBQ25CLG1CQUFtQjtrQkFEL0IsVUFBVTttQkFBQyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJbmplY3RhYmxlLCBpbmplY3QgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IEhPT0tfUkVHSVNUUlkgfSBmcm9tICcuLi90b2tlbnMvaW5qZWN0aW9uLXRva2Vucyc7XG5cbi8qKlxuICogSG9va1JlZ2lzdHJ5U2VydmljZSDigJQgc3RvcmVzIGFuZCBydW5zIEFuZ3VsYXItc2lkZSBwcmUvcG9zdCBob29rcy5cbiAqIENvbnN1bWVycyByZWdpc3RlciBob29rcyB2aWEgcHJvdmlkZU5neER5bmFtaWNFbnRpdHkoeyBob29rczogeyAnY2xpZW50czpiZWZvcmVTYXZlJzogZm4gfSB9KS5cbiAqL1xuQEluamVjdGFibGUoeyBwcm92aWRlZEluOiAncm9vdCcgfSlcbmV4cG9ydCBjbGFzcyBIb29rUmVnaXN0cnlTZXJ2aWNlIHtcbiAgcHJpdmF0ZSByZWFkb25seSByZWdpc3RyeSA9IGluamVjdChIT09LX1JFR0lTVFJZLCB7IG9wdGlvbmFsOiB0cnVlIH0pID8/IG5ldyBNYXAoKTtcblxuICBoYXMoa2V5OiBzdHJpbmcpOiBib29sZWFuIHtcbiAgICByZXR1cm4gdGhpcy5yZWdpc3RyeS5oYXMoa2V5KTtcbiAgfVxuXG4gIGFzeW5jIHJ1bihrZXk6IHN0cmluZywgZGF0YTogYW55LCBjb250ZXh0OiBhbnkgPSB7fSk6IFByb21pc2U8YW55PiB7XG4gICAgY29uc3QgaG9vayA9IHRoaXMucmVnaXN0cnkuZ2V0KGtleSk7XG4gICAgaWYgKCFob29rKSByZXR1cm4gZGF0YTtcbiAgICByZXR1cm4gaG9vayhkYXRhLCBjb250ZXh0KTtcbiAgfVxufVxuIl19