@smallpearl/ngx-helper 0.33.26 → 0.33.28

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.
@@ -0,0 +1,11 @@
1
+ import { HttpContext, HttpContextToken } from '@angular/common/http';
2
+ export type HttpContextInput = [[HttpContextToken<any>, any]] | [HttpContextToken<any>, any] | HttpContext;
3
+ /**
4
+ * Converts array of HttpContextToken key, value pairs to HttpContext
5
+ * object in argument 'context'.
6
+ * @param context HTTP context to which the key, value pairs are added
7
+ * @param reqContext HttpContextToken key, value pairs array
8
+ * @returns HttpContext object, with the key, value pairs added. This is
9
+ * the same object as the 'context' argument.
10
+ */
11
+ export declare function convertHttpContextInputToHttpContext(context: HttpContext, reqContext: HttpContextInput): HttpContext;
@@ -3,6 +3,7 @@ import { ChangeDetectorRef, OnDestroy, OnInit } from '@angular/core';
3
3
  import { AbstractControl } from '@angular/forms';
4
4
  import { TranslocoService } from '@jsverse/transloco';
5
5
  import { Observable, Subscription } from 'rxjs';
6
+ import { HttpContextInput } from './context-param-to-http-context';
6
7
  import { SPMatEntityCrudCreateEditBridge } from './mat-entity-crud-types';
7
8
  import * as i0 from "@angular/core";
8
9
  /**
@@ -16,11 +17,39 @@ import * as i0 from "@angular/core";
16
17
  * checking form.touched), then a 'Lose Changes' prompt is displayed allowing
17
18
  * the user to cancel the closure.
18
19
  *
19
- * The @Component is fake just to keep the VSCode angular linter quiet.
20
+ * The `@Component` decorator is fake to keep the VSCode angular linter quiet.
20
21
  *
21
- * To use this class:-
22
+ * This class can be used in two modes:
22
23
  *
23
- * 1. Declare a FormGroup<> type as
24
+ * I. SPMatEntityCrudComponent mode
25
+ * This mode relies on a bridge interface that implements the
26
+ * SPMatEntityCrudCreateEditBridge interface to perform the entity
27
+ * load/create/update operations. This is the intended mode when the
28
+ * component is used as a part of the SPMatEntityCrudComponent to
29
+ * create/update an entity. This mode requires the following properties
30
+ * to be set:
31
+ * - entity: TEntity | TEntity[IdKey] | undefined (for create)
32
+ * - bridge: SPMatEntityCrudCreateEditBridge
33
+ *
34
+ * II. Standalone mode
35
+ * This mode does not rely on the bridge interface and the component
36
+ * itself performs the entity load/create/update operations.
37
+ * This mode requires the following properties to be set:
38
+ * - entity: TEntity | TEntity[IdKey] | undefined (for create)
39
+ * - baseUrl: string - Base URL for CRUD operations. This URL does not
40
+ * include the entity id. The entity id will be appended to this URL
41
+ * for entity load and update operations. For create operation, this
42
+ * URL is used as is.
43
+ * - entityName: string - Name of the entity, used to parse sideloaded
44
+ * entity responses.
45
+ * - httpReqContext?: HttpContextInput - Optional HTTP context to be
46
+ * passed to the HTTP requests. For instance, if your app has a HTTP
47
+ * interceptor that adds authentication tokens to the requests based
48
+ * on a HttpContextToken, then you can pass that token here.
49
+ *
50
+ * I. SPMatEntityCrudComponent mode:
51
+ *
52
+ * 1. Declare a FormGroup<> type as
24
53
  *
25
54
  * ```
26
55
  * type MyForm = FormGroup<{
@@ -30,59 +59,88 @@ import * as i0 from "@angular/core";
30
59
  * }>;
31
60
  * ```
32
61
  *
33
- * 2. Derive your form's component class from this and implement the
62
+ * 2. Derive your form's component class from this and implement the
34
63
  * createForm() method returing the FormGroup<> instance that matches
35
64
  * the FormGroup concrete type above.
36
65
  *
37
- * ```
38
- * class MyFormComponent extends SPMatEntityCrudFormBase<MyForm, MyEntity> {
39
- * constructor() {
40
- * super()
41
- * }
42
- *
43
- * createForm() {
44
- * return new FormGroup([...])
66
+ * ```
67
+ * class MyFormComponent extends SPMatEntityCrudFormBase<MyForm, MyEntity> {
68
+ * constructor() {
69
+ * super()
70
+ * }
71
+ * createForm() {
72
+ * return new FormGroup([...])
73
+ * }
45
74
  * }
46
- * }
47
- * ```
75
+ * ```
48
76
  *
49
- * 3. If you form's value requires manipulation before being sent to the
77
+ * 3. If your form's value requires manipulation before being sent to the
50
78
  * server, override `getFormValue()` method and do it there before returning
51
79
  * the modified values.
52
80
  *
53
- * 4. Wire up the form in the template as:
54
- *
55
- * ```
56
- * @if (loadEntity$ | async) {
57
- * <form [formGroup]='form'.. (ngSubmit)="onSubmit()">
58
- * <button type="submit">Submit</button>
59
- * </form>
60
- * } @else {
61
- * <div>Loading...</div>
62
- * }
63
- * ```
64
- * Here `loadEntity$` is an Observable<boolean> that upon emission of `true`
65
- * indicates that the entity has been loaded from server (in case of edit)
66
- * and the form is ready to be displayed. Note that if the full entity was
67
- * passed in the `entity` input property, then no server load is necessary
68
- * and the form will be created immediately.
69
- *
70
- * 5. If the entity shape required by the form requires additional parameters
71
- * to be loaded from server, initialize `entity` property with it's id.
72
- * Then override the `getLoadEntityParams()` method to return the additional
73
- * load parameters. The parameters returned by this method will be
74
- * passed to the `loadEntity()` method of the bridge interface.
81
+ * 4. Wire up the form in the template as below
82
+ *
83
+ * ```html
84
+ * @if (loadEntity$ | async) {
85
+ * <form [formGroup]='form'.. (ngSubmit)="onSubmit()">
86
+ * <button type="submit">Submit</button>
87
+ * </form>
88
+ * } @else {
89
+ * <div>Loading...</div>
90
+ * }
91
+ * ```
92
+ *
93
+ * Here `loadEntity$` is an Observable<boolean> that upon emission of `true`
94
+ * indicates that the entity has been loaded from server (in case of edit)
95
+ * and the form is ready to be displayed. Note that if the full entity was
96
+ * passed in the `entity` input property, then no server load is necessary
97
+ * and the form will be created immediately.
98
+ *
99
+ * 5. In the parent component that hosts the SPMatEntityCrudComponent, set
100
+ * the `entity` and `bridge` input properties of this component to
101
+ * appropriate values. For instance, if your form component has the
102
+ * selector `app-my-entity-form`, then the parent component's template
103
+ * will have:
104
+ *
105
+ * ```html
106
+ * <sp-mat-entity-crud
107
+ * ...
108
+ * createEditFormTemplate="entityFormTemplate"
109
+ * ></sp-mat-entity-crud>
110
+ * <ng-template #entityFormTemplate let-data="data">
111
+ * <app-my-entity-form
112
+ * [entity]="data.entity"
113
+ * [bridge]="data.bridge"
114
+ * ></app-my-entity-form>
115
+ * </ng-template>
116
+ * ```
117
+ *
118
+ * II. Standalone mode
119
+ *
120
+ * 1..4. Same as above, except set the required `bridge` input to `undefined`.
121
+ * 5. Initialize the component's inputs `baseUrl` and `entityName` with the
122
+ * appropriate values. If you would like to pass additional HTTP context to
123
+ * the HTTP requests, then set the `httpReqContext` input as well.
124
+ * If the entity uses an id key other than 'id', then set the `idKey` input
125
+ * to the appropriate id key name.
126
+ * 6. If you want to retrieve the created/updated entity after the create/update
127
+ * operation, override the `onPostCreate()` and/or `onPostUpdate()` methods
128
+ * respectively.
75
129
  */
76
130
  export declare abstract class SPMatEntityCrudFormBase<TFormGroup extends AbstractControl, TEntity extends {
77
131
  [P in IdKey]: PropertyKey;
78
132
  }, IdKey extends string = 'id'> implements OnInit, OnDestroy {
79
- _form: import("@angular/core").WritableSignal<TFormGroup | undefined>;
80
133
  entity: import("@angular/core").InputSignal<TEntity | TEntity[IdKey]>;
81
134
  bridge: import("@angular/core").InputSignal<SPMatEntityCrudCreateEditBridge>;
82
135
  params: import("@angular/core").InputSignal<any>;
136
+ entityName: import("@angular/core").InputSignal<string | undefined>;
137
+ baseUrl: import("@angular/core").InputSignal<string | undefined>;
138
+ httpReqContext: import("@angular/core").InputSignal<HttpContextInput | undefined>;
139
+ idKey: import("@angular/core").InputSignal<string>;
83
140
  loadEntity$: Observable<boolean>;
84
141
  _entity: import("@angular/core").WritableSignal<TEntity | undefined>;
85
142
  sub$: Subscription;
143
+ _form: import("@angular/core").WritableSignal<TFormGroup | undefined>;
86
144
  form: import("@angular/core").Signal<TFormGroup>;
87
145
  transloco: TranslocoService;
88
146
  cdr: ChangeDetectorRef;
@@ -99,14 +157,16 @@ export declare abstract class SPMatEntityCrudFormBase<TFormGroup extends Abstrac
99
157
  getLoadEntityParams(): string | HttpParams;
100
158
  /**
101
159
  * Return the TEntity object from the response returned by the
102
- * loadEntity() method of the bridge. Typically entity load return the actual
160
+ * load() method. Typically entity load returns the actual
103
161
  * entity object itself. In some cases, where response is sideloaded, the
104
162
  * default implementation here uses the `sideloadToComposite()` utility to
105
163
  * extract the entity from the response after merging (inplace) the
106
164
  * sideloaded data into a composite.
107
165
  *
108
- * If you have a different response shape, override this method to
109
- * extract the TEntity object from the response.
166
+ * If you have a different response shape, or if your sideloaded object
167
+ * response requires custom custom `sideloadDataMap`, override this method
168
+ * and implement your custom logic to extract the TEntity object from the
169
+ * response.
110
170
  * @param resp
111
171
  * @returns
112
172
  */
@@ -130,6 +190,34 @@ export declare abstract class SPMatEntityCrudFormBase<TFormGroup extends Abstrac
130
190
  */
131
191
  getFormValue(): any;
132
192
  onSubmit(): void;
193
+ onPostCreate(entity: TEntity): void;
194
+ onPostUpdate(entity: TEntity): void;
195
+ /**
196
+ * Loads the entity if `this.entity()` is of type TEntity[IdKey]. If `bridge`
197
+ * input is defined, then it's `loadEntity()` method is used to load the
198
+ * entity. Otherwise, then this method attempts to load the entity using
199
+ * HTTP GET from the URL derived from `baseUrl` input.
200
+ * @param entityId
201
+ * @param params
202
+ * @returns
203
+ */
204
+ load(entityId: any): Observable<TEntity>;
205
+ /**
206
+ * Create a new entity using the bridge if defined, otherwise using HTTP
207
+ * POST to the `baseUrl`.
208
+ * @param values
209
+ * @returns
210
+ */
211
+ protected create(values: any): Observable<TEntity>;
212
+ /**
213
+ * Update an existing entity using the bridge if defined, otherwise using HTTP
214
+ * PATCH to the URL derived from `baseUrl` and the entity id.
215
+ * @param id
216
+ * @param values
217
+ * @returns
218
+ */
219
+ protected update(id: any, values: any): Observable<TEntity>;
220
+ protected getEntityUrl(entityId: any): string;
133
221
  static ɵfac: i0.ɵɵFactoryDeclaration<SPMatEntityCrudFormBase<any, any, any>, never>;
134
- static ɵcmp: i0.ɵɵComponentDeclaration<SPMatEntityCrudFormBase<any, any, any>, "_#_sp-mat-entity-crud-form-base_#_", never, { "entity": { "alias": "entity"; "required": true; "isSignal": true; }; "bridge": { "alias": "bridge"; "required": true; "isSignal": true; }; "params": { "alias": "params"; "required": false; "isSignal": true; }; }, {}, never, never, false, never>;
222
+ static ɵcmp: i0.ɵɵComponentDeclaration<SPMatEntityCrudFormBase<any, any, any>, "_#_sp-mat-entity-crud-form-base_#_", never, { "entity": { "alias": "entity"; "required": true; "isSignal": true; }; "bridge": { "alias": "bridge"; "required": true; "isSignal": true; }; "params": { "alias": "params"; "required": false; "isSignal": true; }; "entityName": { "alias": "entityName"; "required": false; "isSignal": true; }; "baseUrl": { "alias": "baseUrl"; "required": false; "isSignal": true; }; "httpReqContext": { "alias": "httpReqContext"; "required": false; "isSignal": true; }; "idKey": { "alias": "idKey"; "required": false; "isSignal": true; }; }, {}, never, never, false, never>;
135
223
  }
@@ -17,7 +17,16 @@ export interface SPMatEntityCrudComponentBase<TEntity extends {
17
17
  */
18
18
  getEntityName(): string;
19
19
  getEntityNamePlural(): string;
20
+ /**
21
+ * Wrapper around idKey property.
22
+ */
20
23
  getIdKey(): string;
24
+ /**
25
+ * This method should return the entity URL for the given entity id.
26
+ * The entity URL should include any additional query parameters that were
27
+ * passed to the SPMatEntityCrudComponentBase component's `url` property.
28
+ * @param id
29
+ */
21
30
  getEntityUrl(id: TEntity[IdKey] | undefined): string;
22
31
  /**
23
32
  * FormViewHostComponent will call this to close the Create/Edit pane.
@@ -26,9 +26,9 @@ export interface SPMatEntityCrudConfig {
26
26
  * This is the interface through which the client provided CRUD form component
27
27
  * interacts with the 'host' SPMatEntityCrudComponent. When the form wants to
28
28
  * submit an entity to the server (for create or update), it should call the
29
- * one of the create or update methods. The interface also other methods for
30
- * the form component to interact with SPMatEntityCrudComponent such as
31
- * refresh its entities list, close the form pane, etc.
29
+ * one of the create or update methods. The interface also provides other
30
+ * methods for the form component to interact with SPMatEntityCrudComponent
31
+ * such as refresh its entities list, close the form pane, etc.
32
32
  *
33
33
  * The interface name has a 'Bridge' as the interface acts as a bridge between
34
34
  * the client provided form handler component and the host
@@ -45,6 +45,12 @@ export interface SPMatEntityCrudCreateEditBridge {
45
45
  * @returns The entity id key string.
46
46
  */
47
47
  getIdKey(): string;
48
+ /**
49
+ * Get Entity url
50
+ * @param cancel
51
+ * @returns
52
+ */
53
+ getEntityUrl(entityId: any): string;
48
54
  /**
49
55
  * Close the edit/update form pane. This WON'T call the 'cancelEditCallback'
50
56
  * even if one is registered.
package/package.json CHANGED
@@ -6,7 +6,7 @@
6
6
  "path": "src/assets/i18n/"
7
7
  }
8
8
  ],
9
- "version": "0.33.26",
9
+ "version": "0.33.28",
10
10
  "peerDependencies": {
11
11
  "@angular/common": "^19.1.0",
12
12
  "@angular/core": "^19.1.0",
@@ -48,6 +48,14 @@
48
48
  "types": "./entities/index.d.ts",
49
49
  "default": "./fesm2022/smallpearl-ngx-helper-entities.mjs"
50
50
  },
51
+ "./entity-field": {
52
+ "types": "./entity-field/index.d.ts",
53
+ "default": "./fesm2022/smallpearl-ngx-helper-entity-field.mjs"
54
+ },
55
+ "./mat-busy-wheel": {
56
+ "types": "./mat-busy-wheel/index.d.ts",
57
+ "default": "./fesm2022/smallpearl-ngx-helper-mat-busy-wheel.mjs"
58
+ },
51
59
  "./locale": {
52
60
  "types": "./locale/index.d.ts",
53
61
  "default": "./fesm2022/smallpearl-ngx-helper-locale.mjs"
@@ -60,14 +68,6 @@
60
68
  "types": "./forms/index.d.ts",
61
69
  "default": "./fesm2022/smallpearl-ngx-helper-forms.mjs"
62
70
  },
63
- "./mat-busy-wheel": {
64
- "types": "./mat-busy-wheel/index.d.ts",
65
- "default": "./fesm2022/smallpearl-ngx-helper-mat-busy-wheel.mjs"
66
- },
67
- "./entity-field": {
68
- "types": "./entity-field/index.d.ts",
69
- "default": "./fesm2022/smallpearl-ngx-helper-entity-field.mjs"
70
- },
71
71
  "./mat-context-menu": {
72
72
  "types": "./mat-context-menu/index.d.ts",
73
73
  "default": "./fesm2022/smallpearl-ngx-helper-mat-context-menu.mjs"