@adaas/a-concept 0.1.4 → 0.1.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/src/global/A-Abstraction/A-Abstraction-Extend.decorator.js +5 -4
- package/dist/src/global/A-Abstraction/A-Abstraction-Extend.decorator.js.map +1 -1
- package/dist/src/global/A-Abstraction/A-Abstraction.class.d.ts +2 -1
- package/dist/src/global/A-Abstraction/A-Abstraction.class.js +7 -1
- package/dist/src/global/A-Abstraction/A-Abstraction.class.js.map +1 -1
- package/dist/src/global/A-Abstraction/A-Abstraction.types.d.ts +2 -1
- package/dist/src/global/A-Component/A-Component.meta.js +1 -1
- package/dist/src/global/A-Component/A-Component.meta.js.map +1 -1
- package/dist/src/global/A-Container/A-Container.class.d.ts +1 -1
- package/dist/src/global/A-Container/A-Container.class.js +1 -1
- package/dist/src/global/A-Container/A-Container.class.js.map +1 -1
- package/dist/src/global/A-Container/A-Container.constants.d.ts +2 -1
- package/dist/src/global/A-Container/A-Container.constants.js +1 -0
- package/dist/src/global/A-Container/A-Container.constants.js.map +1 -1
- package/dist/src/global/A-Container/A-Container.meta.d.ts +11 -3
- package/dist/src/global/A-Container/A-Container.meta.js +25 -0
- package/dist/src/global/A-Container/A-Container.meta.js.map +1 -1
- package/dist/src/global/A-Container/A-Container.types.d.ts +24 -1
- package/dist/src/global/A-Context/A-Context.class.d.ts +6 -14
- package/dist/src/global/A-Context/A-Context.class.js +16 -20
- package/dist/src/global/A-Context/A-Context.class.js.map +1 -1
- package/dist/src/global/A-Feature/A-Feature.class.d.ts +1 -1
- package/dist/src/global/A-Feature/A-Feature.class.js +6 -4
- package/dist/src/global/A-Feature/A-Feature.class.js.map +1 -1
- package/dist/src/global/A-Feature/A-Feature.types.d.ts +9 -2
- package/dist/src/global/A-Feature/A-Feature.types.js.map +1 -1
- package/dist/src/global/A-Scope/A-Scope.class.d.ts +7 -1
- package/dist/src/global/A-Scope/A-Scope.class.js +22 -2
- package/dist/src/global/A-Scope/A-Scope.class.js.map +1 -1
- package/dist/src/global/A-Scope/A-Scope.types.d.ts +6 -0
- package/dist/src/helpers/A_TypeGuards.helper.d.ts +3 -1
- package/dist/src/helpers/A_TypeGuards.helper.js +10 -2
- package/dist/src/helpers/A_TypeGuards.helper.js.map +1 -1
- package/package.json +1 -1
- package/src/global/A-Abstraction/A-Abstraction-Extend.decorator.ts +5 -4
- package/src/global/A-Abstraction/A-Abstraction.class.ts +12 -2
- package/src/global/A-Abstraction/A-Abstraction.types.ts +2 -1
- package/src/global/A-Component/A-Component.meta.ts +1 -1
- package/src/global/A-Container/A-Container.class.ts +1 -1
- package/src/global/A-Container/A-Container.constants.ts +1 -0
- package/src/global/A-Container/A-Container.meta.ts +38 -3
- package/src/global/A-Container/A-Container.types.ts +27 -2
- package/src/global/A-Context/A-Context.class.ts +22 -21
- package/src/global/A-Feature/A-Feature.class.ts +7 -5
- package/src/global/A-Feature/A-Feature.types.ts +9 -2
- package/src/global/A-Scope/A-Scope.class.ts +62 -13
- package/src/global/A-Scope/A-Scope.types.ts +7 -3
- package/src/helpers/A_TypeGuards.helper.ts +12 -3
- package/tests/A-Abstraction.test.ts +72 -0
- package/tests/A-Common.test.ts +2 -1
|
@@ -203,7 +203,7 @@ export class A_Feature<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__
|
|
|
203
203
|
): (param1: any) => void | (() => void) {
|
|
204
204
|
|
|
205
205
|
switch (true) {
|
|
206
|
-
case '
|
|
206
|
+
case !('template' in params):
|
|
207
207
|
return this.fromComponent;
|
|
208
208
|
|
|
209
209
|
case 'template' in params:
|
|
@@ -221,7 +221,7 @@ export class A_Feature<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__
|
|
|
221
221
|
* @param params
|
|
222
222
|
*/
|
|
223
223
|
protected fromTemplate(
|
|
224
|
-
params: A_TYPES__Feature_InitWithTemplate
|
|
224
|
+
params: A_TYPES__Feature_InitWithTemplate<T>
|
|
225
225
|
) {
|
|
226
226
|
if (!params.template || !Array.isArray(params.template)) {
|
|
227
227
|
throw new A_FeatureError(
|
|
@@ -230,7 +230,7 @@ export class A_Feature<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__
|
|
|
230
230
|
);
|
|
231
231
|
}
|
|
232
232
|
|
|
233
|
-
if (!params.scope || !(params.scope instanceof A_Scope)) {
|
|
233
|
+
if (!params.component && (!params.scope || !(params.scope instanceof A_Scope))) {
|
|
234
234
|
throw new A_FeatureError(
|
|
235
235
|
A_FeatureError.FeatureInitializationError,
|
|
236
236
|
`Invalid A-Feature scope provided of type: ${typeof params.scope} with value: ${JSON.stringify(params.scope).slice(0, 100)}...`
|
|
@@ -241,12 +241,14 @@ export class A_Feature<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__
|
|
|
241
241
|
this._name = params.name;
|
|
242
242
|
|
|
243
243
|
// 2) get scope from where feature is called
|
|
244
|
-
const componentScope = params.
|
|
244
|
+
const componentScope = params.component
|
|
245
|
+
? A_Context.scope(params.component)
|
|
246
|
+
: params.scope as A_Scope;
|
|
245
247
|
|
|
246
248
|
// 3) create caller wrapper for the simple injection of the caller component
|
|
247
249
|
// - Just to prevent issues with undefined caller in features without component
|
|
248
250
|
// - TODO: maybe would be better to allow passing caller in params?
|
|
249
|
-
this._caller = new A_Caller<T>(new A_Component() as T);
|
|
251
|
+
this._caller = new A_Caller<T>(params.component || new A_Component() as T);
|
|
250
252
|
|
|
251
253
|
// 4) allocate new scope for the feature
|
|
252
254
|
const scope = A_Context.allocate(this);
|
|
@@ -22,7 +22,7 @@ export type A_TYPES__Feature_Constructor<T = A_Feature> = new (...args: any[]) =
|
|
|
22
22
|
/**
|
|
23
23
|
* Feature initialization type
|
|
24
24
|
*/
|
|
25
|
-
export type A_TYPES__Feature_Init<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__FeatureAvailableComponents> = A_TYPES__Feature_InitWithComponent<T> | A_TYPES__Feature_InitWithTemplate
|
|
25
|
+
export type A_TYPES__Feature_Init<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__FeatureAvailableComponents> = A_TYPES__Feature_InitWithComponent<T> | A_TYPES__Feature_InitWithTemplate<T>
|
|
26
26
|
/**
|
|
27
27
|
* Feature initialization type using component
|
|
28
28
|
*/
|
|
@@ -42,7 +42,7 @@ export type A_TYPES__Feature_InitWithComponent<T extends A_TYPES__FeatureAvailab
|
|
|
42
42
|
/**
|
|
43
43
|
* Feature initialization type using template
|
|
44
44
|
*/
|
|
45
|
-
export type A_TYPES__Feature_InitWithTemplate = {
|
|
45
|
+
export type A_TYPES__Feature_InitWithTemplate<T extends A_TYPES__FeatureAvailableComponents = A_TYPES__FeatureAvailableComponents> = {
|
|
46
46
|
/**
|
|
47
47
|
* Feature Name
|
|
48
48
|
*/
|
|
@@ -53,6 +53,13 @@ export type A_TYPES__Feature_InitWithTemplate = {
|
|
|
53
53
|
* [!] Important for proper scoping.
|
|
54
54
|
*/
|
|
55
55
|
scope: A_Scope
|
|
56
|
+
/**
|
|
57
|
+
* The component from where the feature is calling. It's important for proper scoping.
|
|
58
|
+
* Based on the component would be retrieved connected components, entities and containers.
|
|
59
|
+
*
|
|
60
|
+
* [!] Could be Container, Entity, Component or Command
|
|
61
|
+
*/
|
|
62
|
+
component?: T,
|
|
56
63
|
/**
|
|
57
64
|
* Optional Feature template to be used instead of building it from decorators
|
|
58
65
|
*/
|
|
@@ -3,7 +3,8 @@ import {
|
|
|
3
3
|
A_TYPES__Scope_Init,
|
|
4
4
|
A_TYPES__ScopeLinkedComponents,
|
|
5
5
|
A_TYPES__ScopeResolvableComponents,
|
|
6
|
-
A_TYPES__Scope_Constructor
|
|
6
|
+
A_TYPES__Scope_Constructor,
|
|
7
|
+
A_TYPES__ScopeLinkedConstructors
|
|
7
8
|
} from './A-Scope.types'
|
|
8
9
|
import {
|
|
9
10
|
A_TYPES__A_InjectDecorator_EntityInjectionInstructions,
|
|
@@ -401,6 +402,11 @@ export class A_Scope<
|
|
|
401
402
|
|
|
402
403
|
break;
|
|
403
404
|
}
|
|
405
|
+
// check scope issuer
|
|
406
|
+
case this.issuer().constructor === ctor: {
|
|
407
|
+
found = true;
|
|
408
|
+
break;
|
|
409
|
+
}
|
|
404
410
|
}
|
|
405
411
|
|
|
406
412
|
if (!found && !!this._parent)
|
|
@@ -574,6 +580,13 @@ export class A_Scope<
|
|
|
574
580
|
*/
|
|
575
581
|
param1: A_TYPES__InjectableConstructors,
|
|
576
582
|
|
|
583
|
+
): T | Array<T>
|
|
584
|
+
resolve<T extends A_TYPES__ScopeLinkedConstructors>(
|
|
585
|
+
/**
|
|
586
|
+
* Provide a component, fragment or entity constructor or an array of constructors to resolve its instance(s) from the scope
|
|
587
|
+
*/
|
|
588
|
+
param1: T,
|
|
589
|
+
|
|
577
590
|
): T | Array<T>
|
|
578
591
|
resolve<T extends A_TYPES__ScopeResolvableComponents>(
|
|
579
592
|
/**
|
|
@@ -593,7 +606,7 @@ export class A_Scope<
|
|
|
593
606
|
}
|
|
594
607
|
|
|
595
608
|
case A_TypeGuards.isFunction(param1): {
|
|
596
|
-
return this.resolveOnce(param1, param2);
|
|
609
|
+
return this.resolveOnce(param1, param2) as T;
|
|
597
610
|
}
|
|
598
611
|
|
|
599
612
|
case A_TypeGuards.isString(param1): {
|
|
@@ -665,35 +678,68 @@ export class A_Scope<
|
|
|
665
678
|
* @param instructions
|
|
666
679
|
* @returns
|
|
667
680
|
*/
|
|
668
|
-
private resolveOnce
|
|
669
|
-
component:
|
|
681
|
+
private resolveOnce(
|
|
682
|
+
component: any,
|
|
670
683
|
instructions?: Partial<A_TYPES__A_InjectDecorator_EntityInjectionInstructions>
|
|
671
|
-
):
|
|
684
|
+
): A_TYPES__ScopeResolvableComponents | A_Scope | A_TYPES__ScopeLinkedComponents | Array<A_TYPES__ScopeResolvableComponents> {
|
|
685
|
+
|
|
686
|
+
if (!component || !this.has(component))
|
|
687
|
+
throw new A_ScopeError(
|
|
688
|
+
A_ScopeError.ResolutionError,
|
|
689
|
+
`Injected Component ${component} not found in the scope`
|
|
690
|
+
);
|
|
672
691
|
|
|
673
692
|
if (A_TypeGuards.isScopeConstructor(component))
|
|
674
693
|
component
|
|
675
694
|
|
|
676
|
-
if (typeof component == 'function' &&
|
|
695
|
+
if (typeof component == 'function' && component.name === 'A_Scope')
|
|
677
696
|
component
|
|
678
697
|
|
|
698
|
+
|
|
699
|
+
|
|
700
|
+
|
|
679
701
|
switch (true) {
|
|
702
|
+
case A_TypeGuards.isConstructorAllowedForScopeAllocation(component): {
|
|
703
|
+
return this.resolveIssuer(component);
|
|
704
|
+
}
|
|
680
705
|
case A_TypeGuards.isEntityConstructor(component): {
|
|
681
|
-
return this.resolveEntity(component, instructions)
|
|
706
|
+
return this.resolveEntity(component, instructions);
|
|
682
707
|
}
|
|
683
708
|
case A_TypeGuards.isFragmentConstructor(component): {
|
|
684
|
-
return this.resolveFragment(component)
|
|
709
|
+
return this.resolveFragment(component);
|
|
685
710
|
}
|
|
686
711
|
case A_TypeGuards.isScopeConstructor(component): {
|
|
687
|
-
return this.resolveScope(component)
|
|
712
|
+
return this.resolveScope(component);
|
|
688
713
|
}
|
|
689
714
|
case A_TypeGuards.isComponentConstructor(component): {
|
|
690
|
-
return this.resolveComponent(component)
|
|
715
|
+
return this.resolveComponent(component);
|
|
691
716
|
}
|
|
692
717
|
default:
|
|
693
|
-
throw new
|
|
718
|
+
throw new A_ScopeError(
|
|
719
|
+
A_ScopeError.ResolutionError,
|
|
720
|
+
`Injected Component ${component} not found in the scope`
|
|
721
|
+
);
|
|
694
722
|
}
|
|
695
723
|
}
|
|
696
724
|
|
|
725
|
+
private resolveIssuer(
|
|
726
|
+
ctor: A_TYPES__ScopeLinkedConstructors
|
|
727
|
+
): A_TYPES__ScopeLinkedComponents {
|
|
728
|
+
const isCurrent = ctor === this.issuer().constructor;
|
|
729
|
+
|
|
730
|
+
if (isCurrent) {
|
|
731
|
+
return this.issuer();
|
|
732
|
+
}
|
|
733
|
+
if (!!this._parent) {
|
|
734
|
+
return this._parent.resolveIssuer(ctor);
|
|
735
|
+
}
|
|
736
|
+
|
|
737
|
+
throw new A_ScopeError(
|
|
738
|
+
A_ScopeError.ResolutionError,
|
|
739
|
+
`Issuer ${ctor.name} not found in the scope ${this.name}`
|
|
740
|
+
);
|
|
741
|
+
}
|
|
742
|
+
|
|
697
743
|
/**
|
|
698
744
|
* This method is used internally to resolve a single entity from the scope based on the provided instructions
|
|
699
745
|
*
|
|
@@ -706,7 +752,7 @@ export class A_Scope<
|
|
|
706
752
|
private resolveEntity<T extends A_Entity>(
|
|
707
753
|
entity: A_TYPES__Entity_Constructor<T>,
|
|
708
754
|
instructions?: Partial<A_TYPES__A_InjectDecorator_EntityInjectionInstructions<T>>
|
|
709
|
-
): T | Array<T>
|
|
755
|
+
): T | Array<T> {
|
|
710
756
|
|
|
711
757
|
const query = instructions?.query || {} as Partial<A_TYPES__A_InjectDecorator_EntityInjectionQuery<T>>;
|
|
712
758
|
const count = instructions?.pagination?.count || 1;
|
|
@@ -729,7 +775,10 @@ export class A_Scope<
|
|
|
729
775
|
return this._parent.resolveEntity(entity, instructions);
|
|
730
776
|
|
|
731
777
|
default:
|
|
732
|
-
throw new
|
|
778
|
+
throw new A_ScopeError(
|
|
779
|
+
A_ScopeError.ResolutionError,
|
|
780
|
+
`Entity ${entity.name} not found in the scope ${this.name}`
|
|
781
|
+
);
|
|
733
782
|
}
|
|
734
783
|
}
|
|
735
784
|
/**
|
|
@@ -9,6 +9,8 @@ import { A_Caller } from "../A-Caller/A_Caller.class"
|
|
|
9
9
|
import { A_Error } from "../A-Error/A_Error.class"
|
|
10
10
|
import { A_TYPES__Error_Constructor } from "../A-Error/A_Error.types"
|
|
11
11
|
import { A_Scope } from "./A-Scope.class"
|
|
12
|
+
import { A_TYPES__Container_Constructor } from "../A-Container/A-Container.types"
|
|
13
|
+
import { A_TYPES__Feature_Constructor } from "../A-Feature/A-Feature.types"
|
|
12
14
|
|
|
13
15
|
|
|
14
16
|
// ============================================================================
|
|
@@ -68,8 +70,10 @@ export type A_TYPES__ScopeConfig = {
|
|
|
68
70
|
export type A_TYPES__Scope_Serialized = {}
|
|
69
71
|
|
|
70
72
|
|
|
71
|
-
|
|
72
|
-
|
|
73
|
+
/**
|
|
74
|
+
*
|
|
75
|
+
*/
|
|
76
|
+
export type A_TYPES__ScopeLinkedConstructors = A_TYPES__Container_Constructor | A_TYPES__Feature_Constructor;
|
|
73
77
|
/**
|
|
74
78
|
* A list of components that can have a scope associated with them
|
|
75
79
|
*/
|
|
@@ -77,7 +81,7 @@ export type A_TYPES__ScopeLinkedComponents = A_Container | A_Feature;
|
|
|
77
81
|
/**
|
|
78
82
|
* A list of components that can be resolved by a scope
|
|
79
83
|
*/
|
|
80
|
-
export type A_TYPES__ScopeResolvableComponents = A_Component | A_Fragment | A_Entity
|
|
84
|
+
export type A_TYPES__ScopeResolvableComponents = A_Component | A_Fragment | A_Entity
|
|
81
85
|
/**
|
|
82
86
|
* A list of components that are dependent on a scope and do not have their own scope
|
|
83
87
|
*/
|
|
@@ -25,7 +25,7 @@ import { A_TYPES__Caller_Constructor } from "../global/A-Caller/A_Caller.types";
|
|
|
25
25
|
import { A_Error } from "../global/A-Error/A_Error.class";
|
|
26
26
|
import { A_CommonHelper } from "./A_Common.helper";
|
|
27
27
|
import { A_TYPES__AbstractionAvailableComponents } from "../global/A-Abstraction/A-Abstraction.types";
|
|
28
|
-
import { A_TYPES__Scope_Constructor } from "../global/A-Scope/A-Scope.types";
|
|
28
|
+
import { A_TYPES__Scope_Constructor, A_TYPES__ScopeLinkedComponents, A_TYPES__ScopeLinkedConstructors } from "../global/A-Scope/A-Scope.types";
|
|
29
29
|
import { A_TYPES__InjectableTargets } from "../global/A-Inject/A-Inject.types";
|
|
30
30
|
|
|
31
31
|
|
|
@@ -273,9 +273,18 @@ export class A_TypeGuards {
|
|
|
273
273
|
// ==========================================================================
|
|
274
274
|
// ========================= SPECIAL Type Guards =============================
|
|
275
275
|
// ===========================================================================
|
|
276
|
-
static
|
|
276
|
+
static isConstructorAllowedForScopeAllocation(target: any): target is A_TYPES__ScopeLinkedConstructors {
|
|
277
277
|
return A_TypeGuards.isContainerConstructor(target)
|
|
278
|
-
|| A_TypeGuards.
|
|
278
|
+
|| A_TypeGuards.isFeatureConstructor(target);
|
|
279
|
+
}
|
|
280
|
+
static isInstanceAllowedForScopeAllocation(target: any): target is A_TYPES__ScopeLinkedComponents {
|
|
281
|
+
return A_TypeGuards.isContainerInstance(target)
|
|
282
|
+
|| A_TypeGuards.isFeatureInstance(target);
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
static isConstructorAvailableForAbstraction(target: any): target is A_TYPES__AbstractionAvailableComponents {
|
|
286
|
+
return A_TypeGuards.isContainerInstance(target)
|
|
287
|
+
|| A_TypeGuards.isComponentInstance(target);
|
|
279
288
|
}
|
|
280
289
|
|
|
281
290
|
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { A_Component } from '@adaas/a-concept/global/A-Component/A-Component.class';
|
|
2
|
+
import './test.setup'
|
|
3
|
+
import { A_Concept } from '@adaas/a-concept/global/A-Concept/A-Concept.class';
|
|
4
|
+
import { A_Container } from '@adaas/a-concept/global/A-Container/A-Container.class';
|
|
5
|
+
|
|
6
|
+
jest.retryTimes(0);
|
|
7
|
+
|
|
8
|
+
describe('A-Abstraction Tests', () => {
|
|
9
|
+
it('It should be possible to extend abstraction on A-Component level', async () => {
|
|
10
|
+
class MyComponent extends A_Component {
|
|
11
|
+
private _test: number = 0
|
|
12
|
+
|
|
13
|
+
@A_Concept.Load()
|
|
14
|
+
myMethod() {
|
|
15
|
+
this._test++;
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
});
|
|
19
|
+
|
|
20
|
+
it('It should be possible to extend abstraction on A-Container level', async () => {
|
|
21
|
+
class MyContainer extends A_Container {
|
|
22
|
+
private _test: number = 0
|
|
23
|
+
|
|
24
|
+
@A_Concept.Load()
|
|
25
|
+
myMethod() {
|
|
26
|
+
this._test++;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
});
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
it('It should be possible to proceed Concept Abstraction', async () => {
|
|
33
|
+
class MyComponent extends A_Component {
|
|
34
|
+
_test2: number = 0
|
|
35
|
+
|
|
36
|
+
@A_Concept.Load()
|
|
37
|
+
myMethod() {
|
|
38
|
+
this._test2++;
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
class MyContainer extends A_Container {
|
|
43
|
+
_test: number = 0
|
|
44
|
+
|
|
45
|
+
@A_Concept.Load()
|
|
46
|
+
myMethod() {
|
|
47
|
+
this._test++;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
const myContainer = new MyContainer({
|
|
52
|
+
name: 'MyContainer',
|
|
53
|
+
components: [MyComponent]
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
const testConcept = new A_Concept({
|
|
57
|
+
name: 'TestConcept',
|
|
58
|
+
containers: [myContainer]
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
await testConcept.load();
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
const resolvedComponent = myContainer.scope.resolve(MyComponent);
|
|
65
|
+
|
|
66
|
+
expect(resolvedComponent).toBeInstanceOf(MyComponent);
|
|
67
|
+
expect(myContainer._test).toBe(1);
|
|
68
|
+
expect(resolvedComponent._test2).toBe(1);
|
|
69
|
+
|
|
70
|
+
});
|
|
71
|
+
});
|
|
72
|
+
|
package/tests/A-Common.test.ts
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
|
+
import './test.setup'
|
|
1
2
|
import { A_CommonHelper } from "@adaas/a-concept/helpers/A_Common.helper";
|
|
2
3
|
import { A_IdentityHelper } from "@adaas/a-concept/helpers/A_Identity.helper";
|
|
3
4
|
import { A_TYPES__DeepPartial } from "@adaas/a-concept/types/A_Common.types";
|
|
4
5
|
jest.retryTimes(0);
|
|
5
6
|
|
|
6
|
-
describe('
|
|
7
|
+
describe('A-Common Tests', () => {
|
|
7
8
|
it('Deep Clone and Merge ', async () => {
|
|
8
9
|
|
|
9
10
|
type TestType = {
|