@e22m4u/js-repository 0.1.6 → 0.1.7
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/README.md +31 -0
- package/docs/assets/navigation.js +1 -1
- package/docs/assets/search.js +1 -1
- package/docs/classes/Adapter.html +1 -1
- package/docs/classes/AdapterLoader.html +1 -1
- package/docs/classes/AdapterRegistry.html +1 -1
- package/docs/classes/BelongsToResolver.html +1 -1
- package/docs/classes/DatasourceDefinitionValidator.html +1 -1
- package/docs/classes/DefinitionRegistry.html +1 -1
- package/docs/classes/FieldsClauseTool.html +1 -1
- package/docs/classes/HasManyResolver.html +1 -1
- package/docs/classes/HasOneResolver.html +1 -1
- package/docs/classes/IncludeClauseTool.html +1 -1
- package/docs/classes/InvalidArgumentError.html +1 -1
- package/docs/classes/InvalidOperatorValueError.html +1 -1
- package/docs/classes/ModelDataSanitizer.html +1 -1
- package/docs/classes/ModelDataTransformer.html +16 -0
- package/docs/classes/ModelDataValidator.html +1 -1
- package/docs/classes/ModelDefinitionUtils.html +1 -1
- package/docs/classes/ModelDefinitionValidator.html +1 -1
- package/docs/classes/NotImplementedError.html +1 -1
- package/docs/classes/OperatorClauseTool.html +1 -1
- package/docs/classes/OrderClauseTool.html +1 -1
- package/docs/classes/PrimaryKeysDefinitionValidator.html +1 -1
- package/docs/classes/PropertiesDefinitionValidator.html +1 -1
- package/docs/classes/PropertyTransformerRegistry.html +20 -0
- package/docs/classes/PropertyValidatorRegistry.html +1 -1
- package/docs/classes/ReferencesManyResolver.html +1 -1
- package/docs/classes/RelationsDefinitionValidator.html +1 -1
- package/docs/classes/Repository.html +1 -1
- package/docs/classes/RepositoryRegistry.html +1 -1
- package/docs/classes/Schema.html +1 -1
- package/docs/classes/SliceClauseTool.html +1 -1
- package/docs/classes/WhereClauseTool.html +1 -1
- package/docs/enums/DataType.html +1 -1
- package/docs/enums/DecoratorTargetType.html +1 -1
- package/docs/enums/RelationType.html +1 -1
- package/docs/functions/capitalize.html +1 -1
- package/docs/functions/cloneDeep.html +1 -1
- package/docs/functions/excludeObjectKeys.html +1 -1
- package/docs/functions/getCtorName.html +1 -1
- package/docs/functions/getDecoratorTargetType.html +1 -1
- package/docs/functions/getValueByPath.html +1 -1
- package/docs/functions/isCtor.html +1 -1
- package/docs/functions/isPureObject.html +1 -1
- package/docs/functions/selectObjectKeys.html +1 -1
- package/docs/functions/singularize.html +1 -1
- package/docs/functions/stringToRegexp.html +1 -1
- package/docs/index.html +16 -1
- package/docs/interfaces/AndClause.html +1 -1
- package/docs/interfaces/Constructor.html +1 -1
- package/docs/interfaces/OrClause.html +1 -1
- package/docs/modules.html +6 -1
- package/docs/types/AnyObject.html +1 -1
- package/docs/types/BelongsToDefinition.html +1 -1
- package/docs/types/DEFAULT_PRIMARY_KEY_PROPERTY_NAME.html +1 -1
- package/docs/types/DatasourceDefinition.html +1 -1
- package/docs/types/FieldsClause.html +1 -1
- package/docs/types/FilterClause.html +1 -1
- package/docs/types/Flatten.html +1 -1
- package/docs/types/FullPropertyDefinition.html +1 -1
- package/docs/types/HasManyDefinition.html +1 -1
- package/docs/types/HasOneDefinition.html +1 -1
- package/docs/types/Identity.html +1 -1
- package/docs/types/IncludeClause.html +1 -1
- package/docs/types/ItemFilterClause.html +1 -1
- package/docs/types/ModelData.html +1 -1
- package/docs/types/ModelDefinition.html +1 -1
- package/docs/types/ModelId.html +1 -1
- package/docs/types/NestedIncludeClause.html +1 -1
- package/docs/types/NormalizedFieldsClause.html +1 -1
- package/docs/types/NormalizedIncludeClause.html +1 -1
- package/docs/types/OperatorClause.html +1 -1
- package/docs/types/OptionalUnlessRequiredId.html +1 -1
- package/docs/types/OrderClause.html +1 -1
- package/docs/types/PartialBy.html +1 -1
- package/docs/types/PartialWithoutId.html +1 -1
- package/docs/types/PolyBelongsToDefinition.html +1 -1
- package/docs/types/PolyHasManyDefinitionWithTargetKeys.html +1 -1
- package/docs/types/PolyHasManyDefinitionWithTargetRelationName.html +1 -1
- package/docs/types/PolyHasOneDefinitionWithTargetKeys.html +1 -1
- package/docs/types/PolyHasOneDefinitionWithTargetRelationName.html +1 -1
- package/docs/types/PropertiesClause.html +1 -1
- package/docs/types/PropertyDefinition.html +1 -1
- package/docs/types/PropertyDefinitionMap.html +1 -1
- package/docs/types/PropertyTransformOptions.html +2 -0
- package/docs/types/PropertyTransformer.html +2 -0
- package/docs/types/PropertyTransformerContext.html +2 -0
- package/docs/types/PropertyValidateOptions.html +1 -1
- package/docs/types/PropertyValidator.html +1 -1
- package/docs/types/PropertyValidatorContext.html +1 -1
- package/docs/types/ReferencesManyDefinition.html +1 -1
- package/docs/types/RelationDefinition.html +1 -1
- package/docs/types/RelationDefinitionMap.html +1 -1
- package/docs/types/WhereClause.html +1 -1
- package/docs/types/WithoutId.html +1 -1
- package/package.json +3 -3
- package/src/adapter/adapter.js +2 -0
- package/src/adapter/adapter.spec.js +9 -3
- package/src/adapter/decorator/data-transformation-decorator.d.ts +14 -0
- package/src/adapter/decorator/data-transformation-decorator.js +54 -0
- package/src/adapter/decorator/data-transformation-decorator.spec.js +95 -0
- package/src/adapter/decorator/data-validation-decorator.js +6 -5
- package/src/adapter/decorator/data-validation-decorator.spec.js +49 -21
- package/src/adapter/decorator/default-values-decorator.spec.js +89 -113
- package/src/adapter/decorator/index.d.ts +1 -0
- package/src/adapter/decorator/index.js +1 -0
- package/src/definition/model/index.d.ts +1 -0
- package/src/definition/model/index.js +1 -0
- package/src/definition/model/model-data-transformer.d.ts +15 -0
- package/src/definition/model/model-data-transformer.js +96 -0
- package/src/definition/model/model-data-transformer.spec.js +534 -0
- package/src/definition/model/model-data-validator.js +10 -12
- package/src/definition/model/model-data-validator.spec.js +133 -32
- package/src/definition/model/properties/index.d.ts +1 -0
- package/src/definition/model/properties/index.js +1 -0
- package/src/definition/model/properties/properties-definition-validator.js +47 -0
- package/src/definition/model/properties/properties-definition-validator.spec.js +52 -0
- package/src/definition/model/properties/property-transformer/builtin/index.d.ts +1 -0
- package/src/definition/model/properties/property-transformer/builtin/index.js +1 -0
- package/src/definition/model/properties/property-transformer/builtin/trim-transformer.d.ts +6 -0
- package/src/definition/model/properties/property-transformer/builtin/trim-transformer.js +19 -0
- package/src/definition/model/properties/property-transformer/builtin/trim-transformer.spec.js +39 -0
- package/src/definition/model/properties/property-transformer/index.d.ts +2 -0
- package/src/definition/model/properties/property-transformer/index.js +2 -0
- package/src/definition/model/properties/property-transformer/property-transformer-registry.d.ts +29 -0
- package/src/definition/model/properties/property-transformer/property-transformer-registry.js +72 -0
- package/src/definition/model/properties/property-transformer/property-transformer-registry.spec.js +129 -0
- package/src/definition/model/properties/property-transformer/property-transformer.d.ts +25 -0
- package/src/definition/model/properties/property-transformer/property-transformer.js +1 -0
- package/src/definition/model/properties/property-validator/builtin/max-length-validator.js +1 -1
- package/src/definition/model/properties/property-validator/builtin/max-length-validator.spec.js +10 -3
- package/src/definition/model/properties/property-validator/builtin/min-length-validator.js +1 -1
- package/src/definition/model/properties/property-validator/builtin/min-length-validator.spec.js +10 -3
- package/src/definition/model/properties/property-validator/builtin/regexp-validator.js +1 -1
- package/src/definition/model/properties/property-validator/builtin/regexp-validator.spec.js +10 -3
- package/src/definition/model/properties/property-validator/property-validator-registry.spec.js +51 -39
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import {Adapter} from '../adapter.js';
|
|
2
|
+
import {Service} from '@e22m4u/js-service';
|
|
3
|
+
import {InvalidArgumentError} from '../../errors/index.js';
|
|
4
|
+
import {ModelDataTransformer} from '../../definition/index.js';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Data transformation decorator.
|
|
8
|
+
*/
|
|
9
|
+
export class DataTransformationDecorator extends Service {
|
|
10
|
+
/**
|
|
11
|
+
* Decorate.
|
|
12
|
+
*
|
|
13
|
+
* @param {Adapter} adapter
|
|
14
|
+
*/
|
|
15
|
+
decorate(adapter) {
|
|
16
|
+
if (!adapter || !(adapter instanceof Adapter))
|
|
17
|
+
throw new InvalidArgumentError(
|
|
18
|
+
'The first argument of DataTransformerDecorator.decorate should be ' +
|
|
19
|
+
'an Adapter instance, but %v given.',
|
|
20
|
+
adapter,
|
|
21
|
+
);
|
|
22
|
+
const transformer = this.getService(ModelDataTransformer);
|
|
23
|
+
|
|
24
|
+
const create = adapter.create;
|
|
25
|
+
adapter.create = function (modelName, modelData, filter) {
|
|
26
|
+
modelData = transformer.transform(modelName, modelData);
|
|
27
|
+
return create.call(this, modelName, modelData, filter);
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
const replaceById = adapter.replaceById;
|
|
31
|
+
adapter.replaceById = function (modelName, id, modelData, filter) {
|
|
32
|
+
modelData = transformer.transform(modelName, modelData);
|
|
33
|
+
return replaceById.call(this, modelName, id, modelData, filter);
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
const replaceOrCreate = adapter.replaceOrCreate;
|
|
37
|
+
adapter.replaceOrCreate = function (modelName, modelData, filter) {
|
|
38
|
+
modelData = transformer.transform(modelName, modelData);
|
|
39
|
+
return replaceOrCreate.call(this, modelName, modelData, filter);
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
const patch = adapter.patch;
|
|
43
|
+
adapter.patch = function (modelName, modelData, where) {
|
|
44
|
+
modelData = transformer.transform(modelName, modelData, true);
|
|
45
|
+
return patch.call(this, modelName, modelData, where);
|
|
46
|
+
};
|
|
47
|
+
|
|
48
|
+
const patchById = adapter.patchById;
|
|
49
|
+
adapter.patchById = function (modelName, id, modelData, filter) {
|
|
50
|
+
modelData = transformer.transform(modelName, modelData, true);
|
|
51
|
+
return patchById.call(this, modelName, id, modelData, filter);
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
}
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
import chai from 'chai';
|
|
2
|
+
import {expect} from 'chai';
|
|
3
|
+
import {Adapter} from '../adapter.js';
|
|
4
|
+
import {Schema} from '../../schema.js';
|
|
5
|
+
import {ModelDataTransformer} from '../../definition/index.js';
|
|
6
|
+
|
|
7
|
+
const S = new Schema();
|
|
8
|
+
S.defineModel({name: 'model'});
|
|
9
|
+
|
|
10
|
+
class TestAdapter extends Adapter {
|
|
11
|
+
// eslint-disable-next-line no-unused-vars
|
|
12
|
+
create(modelName, modelData, filter = undefined) {
|
|
13
|
+
return Promise.resolve(modelData);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
// eslint-disable-next-line no-unused-vars
|
|
17
|
+
replaceById(modelName, id, modelData, filter = undefined) {
|
|
18
|
+
return Promise.resolve(modelData);
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
// eslint-disable-next-line no-unused-vars
|
|
22
|
+
replaceOrCreate(modelName, modelData, filter = undefined) {
|
|
23
|
+
return Promise.resolve(modelData);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
// eslint-disable-next-line no-unused-vars
|
|
27
|
+
patch(modelName, modelData, where = undefined) {
|
|
28
|
+
return Promise.resolve(modelData);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
// eslint-disable-next-line no-unused-vars
|
|
32
|
+
patchById(modelName, id, modelData, filter = undefined) {
|
|
33
|
+
return Promise.resolve(modelData);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
const A = S.getService(TestAdapter);
|
|
38
|
+
const V = S.getService(ModelDataTransformer);
|
|
39
|
+
const sandbox = chai.spy.sandbox();
|
|
40
|
+
|
|
41
|
+
describe('DataTransformationDecorator', function () {
|
|
42
|
+
afterEach(function () {
|
|
43
|
+
sandbox.restore();
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
it('overrides the "create" method and transforms a given data', async function () {
|
|
47
|
+
const modelData = {kind: 'modelData'};
|
|
48
|
+
const transformedData = {kind: 'transformedData'};
|
|
49
|
+
sandbox.on(V, 'transform', () => transformedData);
|
|
50
|
+
const res = await A.create('model', modelData);
|
|
51
|
+
expect(res).to.be.eql(transformedData);
|
|
52
|
+
expect(V.transform).to.be.called.once;
|
|
53
|
+
expect(V.transform).to.be.called.with.exactly('model', modelData);
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
it('overrides the "replaceById" method and transforms a given data', async function () {
|
|
57
|
+
const modelData = {kind: 'modelData'};
|
|
58
|
+
const transformedData = {kind: 'transformedData'};
|
|
59
|
+
sandbox.on(V, 'transform', () => transformedData);
|
|
60
|
+
const res = await A.replaceById('model', 1, modelData);
|
|
61
|
+
expect(res).to.be.eql(transformedData);
|
|
62
|
+
expect(V.transform).to.be.called.once;
|
|
63
|
+
expect(V.transform).to.be.called.with.exactly('model', modelData);
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
it('overrides the "replaceOrCreate" method and transforms a given data', async function () {
|
|
67
|
+
const modelData = {kind: 'modelData'};
|
|
68
|
+
const transformedData = {kind: 'transformedData'};
|
|
69
|
+
sandbox.on(V, 'transform', () => transformedData);
|
|
70
|
+
const res = await A.replaceOrCreate('model', modelData);
|
|
71
|
+
expect(res).to.be.eql(transformedData);
|
|
72
|
+
expect(V.transform).to.be.called.once;
|
|
73
|
+
expect(V.transform).to.be.called.with.exactly('model', modelData);
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
it('overrides the "patch" method and transforms a given data', async function () {
|
|
77
|
+
const modelData = {kind: 'modelData'};
|
|
78
|
+
const transformedData = {kind: 'transformedData'};
|
|
79
|
+
sandbox.on(V, 'transform', () => transformedData);
|
|
80
|
+
const res = await A.patch('model', modelData);
|
|
81
|
+
expect(res).to.be.eql(transformedData);
|
|
82
|
+
expect(V.transform).to.be.called.once;
|
|
83
|
+
expect(V.transform).to.be.called.with.exactly('model', modelData, true);
|
|
84
|
+
});
|
|
85
|
+
|
|
86
|
+
it('overrides the "patchById" method and transforms a given data', async function () {
|
|
87
|
+
const modelData = {kind: 'modelData'};
|
|
88
|
+
const transformedData = {kind: 'transformedData'};
|
|
89
|
+
sandbox.on(V, 'transform', () => transformedData);
|
|
90
|
+
const res = await A.patchById('model', 1, modelData);
|
|
91
|
+
expect(res).to.be.eql(transformedData);
|
|
92
|
+
expect(V.transform).to.be.called.once;
|
|
93
|
+
expect(V.transform).to.be.called.with.exactly('model', modelData, true);
|
|
94
|
+
});
|
|
95
|
+
});
|
|
@@ -19,34 +19,35 @@ export class DataValidationDecorator extends Service {
|
|
|
19
19
|
'an Adapter instance, but %v given.',
|
|
20
20
|
adapter,
|
|
21
21
|
);
|
|
22
|
+
const validator = this.getService(ModelDataValidator);
|
|
22
23
|
|
|
23
24
|
const create = adapter.create;
|
|
24
25
|
adapter.create = function (modelName, modelData, filter) {
|
|
25
|
-
|
|
26
|
+
validator.validate(modelName, modelData);
|
|
26
27
|
return create.call(this, modelName, modelData, filter);
|
|
27
28
|
};
|
|
28
29
|
|
|
29
30
|
const replaceById = adapter.replaceById;
|
|
30
31
|
adapter.replaceById = function (modelName, id, modelData, filter) {
|
|
31
|
-
|
|
32
|
+
validator.validate(modelName, modelData);
|
|
32
33
|
return replaceById.call(this, modelName, id, modelData, filter);
|
|
33
34
|
};
|
|
34
35
|
|
|
35
36
|
const replaceOrCreate = adapter.replaceOrCreate;
|
|
36
37
|
adapter.replaceOrCreate = function (modelName, modelData, filter) {
|
|
37
|
-
|
|
38
|
+
validator.validate(modelName, modelData);
|
|
38
39
|
return replaceOrCreate.call(this, modelName, modelData, filter);
|
|
39
40
|
};
|
|
40
41
|
|
|
41
42
|
const patch = adapter.patch;
|
|
42
43
|
adapter.patch = function (modelName, modelData, where) {
|
|
43
|
-
|
|
44
|
+
validator.validate(modelName, modelData, true);
|
|
44
45
|
return patch.call(this, modelName, modelData, where);
|
|
45
46
|
};
|
|
46
47
|
|
|
47
48
|
const patchById = adapter.patchById;
|
|
48
49
|
adapter.patchById = function (modelName, id, modelData, filter) {
|
|
49
|
-
|
|
50
|
+
validator.validate(modelName, modelData, true);
|
|
50
51
|
return patchById.call(this, modelName, id, modelData, filter);
|
|
51
52
|
};
|
|
52
53
|
}
|
|
@@ -10,27 +10,27 @@ S.defineModel({name: 'model'});
|
|
|
10
10
|
class TestAdapter extends Adapter {
|
|
11
11
|
// eslint-disable-next-line no-unused-vars
|
|
12
12
|
create(modelName, modelData, filter = undefined) {
|
|
13
|
-
return Promise.resolve(
|
|
13
|
+
return Promise.resolve(modelData);
|
|
14
14
|
}
|
|
15
15
|
|
|
16
16
|
// eslint-disable-next-line no-unused-vars
|
|
17
17
|
replaceById(modelName, id, modelData, filter = undefined) {
|
|
18
|
-
return Promise.resolve(
|
|
18
|
+
return Promise.resolve(modelData);
|
|
19
19
|
}
|
|
20
20
|
|
|
21
21
|
// eslint-disable-next-line no-unused-vars
|
|
22
22
|
replaceOrCreate(modelName, modelData, filter = undefined) {
|
|
23
|
-
return Promise.resolve(
|
|
23
|
+
return Promise.resolve(modelData);
|
|
24
24
|
}
|
|
25
25
|
|
|
26
26
|
// eslint-disable-next-line no-unused-vars
|
|
27
27
|
patch(modelName, modelData, where = undefined) {
|
|
28
|
-
return Promise.resolve(
|
|
28
|
+
return Promise.resolve(modelData);
|
|
29
29
|
}
|
|
30
30
|
|
|
31
31
|
// eslint-disable-next-line no-unused-vars
|
|
32
32
|
patchById(modelName, id, modelData, filter = undefined) {
|
|
33
|
-
return Promise.resolve(
|
|
33
|
+
return Promise.resolve(modelData);
|
|
34
34
|
}
|
|
35
35
|
}
|
|
36
36
|
|
|
@@ -44,34 +44,62 @@ describe('DataValidationDecorator', function () {
|
|
|
44
44
|
});
|
|
45
45
|
|
|
46
46
|
it('overrides the "create" method and validates a given data', async function () {
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
47
|
+
const data = {kind: 'data'};
|
|
48
|
+
sandbox.on(V, 'validate', (modelName, modelData, isPartial = false) => {
|
|
49
|
+
expect(modelName).to.be.eq('model');
|
|
50
|
+
expect(modelData).to.be.eql(data);
|
|
51
|
+
expect(isPartial).to.be.false;
|
|
52
|
+
});
|
|
53
|
+
const res = await A.create('model', data);
|
|
54
|
+
expect(res).to.be.eql(data);
|
|
50
55
|
expect(V.validate).to.be.called.once;
|
|
51
|
-
expect(V.validate).to.be.called.with.exactly('model', data);
|
|
52
56
|
});
|
|
53
57
|
|
|
54
58
|
it('overrides the "replaceById" method and validates a given data', async function () {
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
59
|
+
const data = {kind: 'data'};
|
|
60
|
+
sandbox.on(V, 'validate', (modelName, modelData, isPartial = false) => {
|
|
61
|
+
expect(modelName).to.be.eq('model');
|
|
62
|
+
expect(modelData).to.be.eql(data);
|
|
63
|
+
expect(isPartial).to.be.false;
|
|
64
|
+
});
|
|
65
|
+
const res = await A.replaceById('model', 1, data);
|
|
66
|
+
expect(res).to.be.eql(data);
|
|
58
67
|
expect(V.validate).to.be.called.once;
|
|
59
|
-
expect(V.validate).to.be.called.with.exactly('model', data);
|
|
60
68
|
});
|
|
61
69
|
|
|
62
70
|
it('overrides the "replaceOrCreate" method and validates a given data', async function () {
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
71
|
+
const data = {kind: 'data'};
|
|
72
|
+
sandbox.on(V, 'validate', (modelName, modelData, isPartial = false) => {
|
|
73
|
+
expect(modelName).to.be.eq('model');
|
|
74
|
+
expect(modelData).to.be.eql(data);
|
|
75
|
+
expect(isPartial).to.be.false;
|
|
76
|
+
});
|
|
77
|
+
const res = await A.replaceOrCreate('model', data);
|
|
78
|
+
expect(res).to.be.eql(data);
|
|
79
|
+
expect(V.validate).to.be.called.once;
|
|
80
|
+
});
|
|
81
|
+
|
|
82
|
+
it('overrides the "patch" method and validates a given data', async function () {
|
|
83
|
+
const data = {kind: 'data'};
|
|
84
|
+
sandbox.on(V, 'validate', (modelName, modelData, isPartial = false) => {
|
|
85
|
+
expect(modelName).to.be.eq('model');
|
|
86
|
+
expect(modelData).to.be.eql(data);
|
|
87
|
+
expect(isPartial).to.be.true;
|
|
88
|
+
});
|
|
89
|
+
const res = await A.patch('model', data);
|
|
90
|
+
expect(res).to.be.eql(data);
|
|
66
91
|
expect(V.validate).to.be.called.once;
|
|
67
|
-
expect(V.validate).to.be.called.with.exactly('model', data);
|
|
68
92
|
});
|
|
69
93
|
|
|
70
94
|
it('overrides the "patchById" method and validates a given data', async function () {
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
95
|
+
const data = {kind: 'data'};
|
|
96
|
+
sandbox.on(V, 'validate', (modelName, modelData, isPartial = false) => {
|
|
97
|
+
expect(modelName).to.be.eq('model');
|
|
98
|
+
expect(modelData).to.be.eql(data);
|
|
99
|
+
expect(isPartial).to.be.true;
|
|
100
|
+
});
|
|
101
|
+
const res = await A.patchById('model', 1, data);
|
|
102
|
+
expect(res).to.be.eql(data);
|
|
74
103
|
expect(V.validate).to.be.called.once;
|
|
75
|
-
expect(V.validate).to.be.called.with.exactly('model', data, true);
|
|
76
104
|
});
|
|
77
105
|
});
|
|
@@ -17,6 +17,7 @@ S.defineModel({
|
|
|
17
17
|
});
|
|
18
18
|
|
|
19
19
|
const INPUT_DATA = {};
|
|
20
|
+
const INPUT_DATA_WITH_DEFAULTS = {prop: 'value'};
|
|
20
21
|
|
|
21
22
|
class TestAdapter extends Adapter {
|
|
22
23
|
// eslint-disable-next-line no-unused-vars
|
|
@@ -65,139 +66,114 @@ describe('DefaultValuesDecorator', function () {
|
|
|
65
66
|
});
|
|
66
67
|
|
|
67
68
|
it('overrides the "create" method method and sets default values to input data', async function () {
|
|
68
|
-
sandbox.on(
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
69
|
+
sandbox.on(
|
|
70
|
+
U,
|
|
71
|
+
'setDefaultValuesToEmptyProperties',
|
|
72
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
73
|
+
expect(modelName).to.be.eq('model');
|
|
74
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
75
|
+
expect(onlyProvidedProperties).to.be.false;
|
|
76
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
77
|
+
},
|
|
75
78
|
);
|
|
79
|
+
const res = await A.create('model', INPUT_DATA);
|
|
80
|
+
expect(res).to.be.eql(INPUT_DATA_WITH_DEFAULTS);
|
|
81
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
76
82
|
});
|
|
77
83
|
|
|
78
84
|
it('overrides the "replaceById" method and sets default values to input data', async function () {
|
|
79
|
-
sandbox.on(
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
85
|
+
sandbox.on(
|
|
86
|
+
U,
|
|
87
|
+
'setDefaultValuesToEmptyProperties',
|
|
88
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
89
|
+
expect(modelName).to.be.eq('model');
|
|
90
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
91
|
+
expect(onlyProvidedProperties).to.be.false;
|
|
92
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
93
|
+
},
|
|
86
94
|
);
|
|
95
|
+
const res = await A.replaceById('model', 1, INPUT_DATA);
|
|
96
|
+
expect(res).to.be.eql(INPUT_DATA_WITH_DEFAULTS);
|
|
97
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
87
98
|
});
|
|
88
99
|
|
|
89
100
|
it('overrides the "replaceOrCreate" method and sets default values to input data', async function () {
|
|
90
|
-
sandbox.on(
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
101
|
+
sandbox.on(
|
|
102
|
+
U,
|
|
103
|
+
'setDefaultValuesToEmptyProperties',
|
|
104
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
105
|
+
expect(modelName).to.be.eq('model');
|
|
106
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
107
|
+
expect(onlyProvidedProperties).to.be.false;
|
|
108
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
109
|
+
},
|
|
97
110
|
);
|
|
111
|
+
const res = await A.replaceOrCreate('model', INPUT_DATA);
|
|
112
|
+
expect(res).to.be.eql(INPUT_DATA_WITH_DEFAULTS);
|
|
113
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
98
114
|
});
|
|
99
115
|
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
it('does set default values to input properties of null', async function () {
|
|
115
|
-
sandbox.on(U, 'setDefaultValuesToEmptyProperties');
|
|
116
|
-
const data = {prop: null};
|
|
117
|
-
const retval = await A.patch('model', data);
|
|
118
|
-
expect(retval).to.be.eql({prop: 'value'});
|
|
119
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
120
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.with.exactly(
|
|
121
|
-
'model',
|
|
122
|
-
data,
|
|
123
|
-
true,
|
|
124
|
-
);
|
|
125
|
-
});
|
|
126
|
-
|
|
127
|
-
it('does set default values to input properties of undefined', async function () {
|
|
128
|
-
sandbox.on(U, 'setDefaultValuesToEmptyProperties');
|
|
129
|
-
const data = {prop: undefined};
|
|
130
|
-
const retval = await A.patch('model', data);
|
|
131
|
-
expect(retval).to.be.eql({prop: 'value'});
|
|
132
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
133
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.with.exactly(
|
|
134
|
-
'model',
|
|
135
|
-
data,
|
|
136
|
-
true,
|
|
137
|
-
);
|
|
138
|
-
});
|
|
116
|
+
it('overrides the "patch" method and sets default values to input data', async function () {
|
|
117
|
+
sandbox.on(
|
|
118
|
+
U,
|
|
119
|
+
'setDefaultValuesToEmptyProperties',
|
|
120
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
121
|
+
expect(modelName).to.be.eq('model');
|
|
122
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
123
|
+
expect(onlyProvidedProperties).to.be.true;
|
|
124
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
125
|
+
},
|
|
126
|
+
);
|
|
127
|
+
const res = await A.patch('model', INPUT_DATA);
|
|
128
|
+
expect(res).to.be.eql(INPUT_DATA_WITH_DEFAULTS);
|
|
129
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
139
130
|
});
|
|
140
131
|
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
it('does set default values to input properties of null', async function () {
|
|
156
|
-
sandbox.on(U, 'setDefaultValuesToEmptyProperties');
|
|
157
|
-
const data = {prop: null};
|
|
158
|
-
const retval = await A.patchById('model', 2, data);
|
|
159
|
-
expect(retval).to.be.eql({prop: 'value'});
|
|
160
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
161
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.with.exactly(
|
|
162
|
-
'model',
|
|
163
|
-
data,
|
|
164
|
-
true,
|
|
165
|
-
);
|
|
166
|
-
});
|
|
167
|
-
|
|
168
|
-
it('does set default values to input properties of undefined', async function () {
|
|
169
|
-
sandbox.on(U, 'setDefaultValuesToEmptyProperties');
|
|
170
|
-
const data = {prop: undefined};
|
|
171
|
-
const retval = await A.patchById('model', 3, data);
|
|
172
|
-
expect(retval).to.be.eql({prop: 'value'});
|
|
173
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
174
|
-
expect(U.setDefaultValuesToEmptyProperties).to.be.called.with.exactly(
|
|
175
|
-
'model',
|
|
176
|
-
data,
|
|
177
|
-
true,
|
|
178
|
-
);
|
|
179
|
-
});
|
|
132
|
+
it('overrides the "patchById" method and sets default values to input data', async function () {
|
|
133
|
+
sandbox.on(
|
|
134
|
+
U,
|
|
135
|
+
'setDefaultValuesToEmptyProperties',
|
|
136
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
137
|
+
expect(modelName).to.be.eq('model');
|
|
138
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
139
|
+
expect(onlyProvidedProperties).to.be.true;
|
|
140
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
141
|
+
},
|
|
142
|
+
);
|
|
143
|
+
const res = await A.patchById('model', 1, INPUT_DATA);
|
|
144
|
+
expect(res).to.be.eql(INPUT_DATA_WITH_DEFAULTS);
|
|
145
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
180
146
|
});
|
|
181
147
|
|
|
182
148
|
it('overrides the "find" method and sets default values to output data', async function () {
|
|
183
|
-
sandbox.on(
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
149
|
+
sandbox.on(
|
|
150
|
+
U,
|
|
151
|
+
'setDefaultValuesToEmptyProperties',
|
|
152
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
153
|
+
expect(modelName).to.be.eq('model');
|
|
154
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
155
|
+
expect(onlyProvidedProperties).to.be.false;
|
|
156
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
157
|
+
},
|
|
190
158
|
);
|
|
159
|
+
const res = await A.find('model');
|
|
160
|
+
expect(res).to.be.eql([INPUT_DATA_WITH_DEFAULTS]);
|
|
161
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
191
162
|
});
|
|
192
163
|
|
|
193
164
|
it('overrides the "findById" method and sets default values to output data', async function () {
|
|
194
|
-
sandbox.on(
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
165
|
+
sandbox.on(
|
|
166
|
+
U,
|
|
167
|
+
'setDefaultValuesToEmptyProperties',
|
|
168
|
+
(modelName, modelData, onlyProvidedProperties = false) => {
|
|
169
|
+
expect(modelName).to.be.eq('model');
|
|
170
|
+
expect(modelData).to.be.eql(INPUT_DATA);
|
|
171
|
+
expect(onlyProvidedProperties).to.be.false;
|
|
172
|
+
return INPUT_DATA_WITH_DEFAULTS;
|
|
173
|
+
},
|
|
201
174
|
);
|
|
175
|
+
const res = await A.findById('model', 1);
|
|
176
|
+
expect(res).to.be.eql(INPUT_DATA_WITH_DEFAULTS);
|
|
177
|
+
expect(U.setDefaultValuesToEmptyProperties).to.be.called.once;
|
|
202
178
|
});
|
|
203
179
|
});
|
|
@@ -3,5 +3,6 @@ export * from './properties/index.js';
|
|
|
3
3
|
export * from './model-definition.js';
|
|
4
4
|
export * from './model-data-validator.js';
|
|
5
5
|
export * from './model-data-sanitizer.js';
|
|
6
|
+
export * from './model-data-transformer.js';
|
|
6
7
|
export * from './model-definition-utils.js';
|
|
7
8
|
export * from './model-definition-validator.js';
|
|
@@ -3,5 +3,6 @@ export * from './properties/index.js';
|
|
|
3
3
|
export * from './model-definition.js';
|
|
4
4
|
export * from './model-data-validator.js';
|
|
5
5
|
export * from './model-data-sanitizer.js';
|
|
6
|
+
export * from './model-data-transformer.js';
|
|
6
7
|
export * from './model-definition-utils.js';
|
|
7
8
|
export * from './model-definition-validator.js';
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import {ModelData} from '../../types.js';
|
|
2
|
+
import {Service} from '@e22m4u/js-service';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Model data transformer.
|
|
6
|
+
*/
|
|
7
|
+
export declare class ModelDataTransformer extends Service {
|
|
8
|
+
/**
|
|
9
|
+
* Transform.
|
|
10
|
+
*
|
|
11
|
+
* @param modelName
|
|
12
|
+
* @param modelData
|
|
13
|
+
*/
|
|
14
|
+
transform(modelName: string, modelData: ModelData): ModelData;
|
|
15
|
+
}
|