@platecms/delta-validation 0.13.0 → 1.3.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.
- package/package.json +4 -4
- package/src/index.ts +8 -7
- package/src/lib/enums/validation-rule-update-impact.enum.ts +5 -0
- package/src/lib/helpers/fields-to-schema.spec.ts +184 -0
- package/src/lib/helpers/fields-to-schema.ts +141 -0
- package/src/lib/helpers/get-content-value-type-name.ts +26 -0
- package/src/lib/helpers/is-superset.helper.ts +4 -0
- package/src/lib/helpers/rule-to-schema.spec.ts +4 -4
- package/src/lib/helpers/schema-builder.ts +5 -0
- package/src/lib/helpers/validate-with-function.spec.ts +3 -3
- package/src/lib/schemas/array.schema.spec.ts +1 -1
- package/src/lib/schemas/content-value.schema.spec.ts +5 -5
- package/src/lib/schemas/content-value.schema.ts +27 -2
- package/src/lib/schemas/date.schema.spec.ts +1 -1
- package/src/lib/schemas/object.schema.spec.ts +223 -0
- package/src/lib/schemas/object.schema.ts +106 -0
- package/src/lib/schemas/string.schema.spec.ts +1 -1
- package/src/lib/types/validation-schema.interface.ts +1 -1
- package/src/lib/validation-rules/allowed-values.validation-rule.spec.ts +30 -5
- package/src/lib/validation-rules/allowed-values.validation-rule.ts +15 -0
- package/src/lib/validation-rules/base.validation-rule.ts +21 -4
- package/src/lib/validation-rules/count.validation-rule.spec.ts +39 -1
- package/src/lib/validation-rules/count.validation-rule.ts +35 -0
- package/src/lib/validation-rules/date-between.validation-rule.spec.ts +84 -1
- package/src/lib/validation-rules/date-between.validation-rule.ts +19 -4
- package/src/lib/validation-rules/decimal-count.validation-rule.spec.ts +27 -1
- package/src/lib/validation-rules/decimal-count.validation-rule.ts +12 -0
- package/src/lib/validation-rules/number-between.validation-rule.spec.ts +45 -1
- package/src/lib/validation-rules/number-between.validation-rule.ts +14 -0
- package/src/lib/validation-rules/relatable-content-types.validation-rule.spec.ts +38 -13
- package/src/lib/validation-rules/relatable-content-types.validation-rule.ts +17 -0
- package/src/lib/validation-rules/string-format.validation-rule.spec.ts +48 -22
- package/src/lib/validation-rules/string-format.validation-rule.ts +14 -0
- package/src/lib/validation-rules/value-type.validation-rule.spec.ts +105 -75
- package/src/lib/validation-rules/value-type.validation-rule.ts +17 -2
|
@@ -1,108 +1,138 @@
|
|
|
1
1
|
import { PRN } from "@platecms/delta-plate-resource-notation";
|
|
2
|
-
import { ContentValueType, ContentValueTypeNames } from "@platecms/delta-types";
|
|
2
|
+
import { ContentValueType, ContentValueTypeName, ContentValueTypeNames } from "@platecms/delta-types";
|
|
3
|
+
import { ValidationRuleUpdateImpact } from "../enums/validation-rule-update-impact.enum";
|
|
3
4
|
import { ValueTypeValidationRule, ValueTypeValidationRuleSettings } from "./value-type.validation-rule";
|
|
4
5
|
|
|
5
6
|
describe("ValueTypeValidationRule", () => {
|
|
6
|
-
const rulePrn = PRN.fromString("prn:plate:-1:
|
|
7
|
+
const rulePrn = PRN.fromString("prn:plate:-1:cms:validation-rule:value-type");
|
|
7
8
|
|
|
8
|
-
describe
|
|
9
|
-
[
|
|
10
|
-
"with allowed string type",
|
|
11
|
-
{ allowedTypes: [ContentValueTypeNames.STRING] },
|
|
9
|
+
describe("validate", () => {
|
|
10
|
+
describe.each([
|
|
12
11
|
[
|
|
13
|
-
|
|
14
|
-
[
|
|
12
|
+
"with allowed string type",
|
|
13
|
+
{ allowedTypes: [ContentValueTypeNames.STRING] },
|
|
14
|
+
[
|
|
15
|
+
["foo", true],
|
|
16
|
+
[123, false],
|
|
17
|
+
],
|
|
15
18
|
],
|
|
16
|
-
],
|
|
17
|
-
[
|
|
18
|
-
"with allowed number type",
|
|
19
|
-
{ allowedTypes: [ContentValueTypeNames.NUMBER] },
|
|
20
19
|
[
|
|
21
|
-
|
|
22
|
-
[
|
|
20
|
+
"with allowed number type",
|
|
21
|
+
{ allowedTypes: [ContentValueTypeNames.NUMBER] },
|
|
22
|
+
[
|
|
23
|
+
[123, true],
|
|
24
|
+
["foo", false],
|
|
25
|
+
],
|
|
23
26
|
],
|
|
24
|
-
],
|
|
25
|
-
[
|
|
26
|
-
"with allowed boolean type",
|
|
27
|
-
{ allowedTypes: [ContentValueTypeNames.BOOLEAN] },
|
|
28
27
|
[
|
|
29
|
-
|
|
30
|
-
[
|
|
28
|
+
"with allowed boolean type",
|
|
29
|
+
{ allowedTypes: [ContentValueTypeNames.BOOLEAN] },
|
|
30
|
+
[
|
|
31
|
+
[true, true],
|
|
32
|
+
["foo", false],
|
|
33
|
+
],
|
|
31
34
|
],
|
|
32
|
-
],
|
|
33
|
-
[
|
|
34
|
-
"with allowed date type",
|
|
35
|
-
{ allowedTypes: [ContentValueTypeNames.DATE] },
|
|
36
35
|
[
|
|
37
|
-
|
|
38
|
-
[
|
|
36
|
+
"with allowed date type",
|
|
37
|
+
{ allowedTypes: [ContentValueTypeNames.DATE] },
|
|
38
|
+
[
|
|
39
|
+
[new Date(), true],
|
|
40
|
+
["foo", false],
|
|
41
|
+
],
|
|
39
42
|
],
|
|
40
|
-
],
|
|
41
|
-
[
|
|
42
|
-
"with allowed content item type",
|
|
43
|
-
{ allowedTypes: [ContentValueTypeNames.CONTENT_ITEM] },
|
|
44
43
|
[
|
|
45
|
-
|
|
46
|
-
[
|
|
44
|
+
"with allowed content item type",
|
|
45
|
+
{ allowedTypes: [ContentValueTypeNames.CONTENT_ITEM] },
|
|
46
|
+
[
|
|
47
|
+
[PRN.fromString("prn:plate:-1:cms:content-item:1"), true],
|
|
48
|
+
["foo", false],
|
|
49
|
+
],
|
|
47
50
|
],
|
|
48
|
-
],
|
|
49
|
-
[
|
|
50
|
-
"with allowed asset type",
|
|
51
|
-
{ allowedTypes: [ContentValueTypeNames.ASSET] },
|
|
52
51
|
[
|
|
53
|
-
|
|
54
|
-
[
|
|
52
|
+
"with allowed asset type",
|
|
53
|
+
{ allowedTypes: [ContentValueTypeNames.ASSET] },
|
|
54
|
+
[
|
|
55
|
+
[PRN.fromString("prn:plate:-1:ps:asset:1"), true],
|
|
56
|
+
["foo", false],
|
|
57
|
+
],
|
|
55
58
|
],
|
|
56
|
-
],
|
|
57
|
-
[
|
|
58
|
-
"with allowed path part type",
|
|
59
|
-
{ allowedTypes: [ContentValueTypeNames.PATH_PART] },
|
|
60
59
|
[
|
|
61
|
-
|
|
62
|
-
[
|
|
60
|
+
"with allowed path part type",
|
|
61
|
+
{ allowedTypes: [ContentValueTypeNames.PATH_PART] },
|
|
62
|
+
[
|
|
63
|
+
[PRN.fromString("prn:plate:-1:cms:path-part:1"), true],
|
|
64
|
+
["foo", false],
|
|
65
|
+
],
|
|
63
66
|
],
|
|
64
|
-
],
|
|
65
|
-
[
|
|
66
|
-
"with allowed grid placement type",
|
|
67
|
-
{ allowedTypes: [ContentValueTypeNames.GRID_PLACEMENT] },
|
|
68
67
|
[
|
|
69
|
-
|
|
70
|
-
[
|
|
68
|
+
"with allowed grid placement type",
|
|
69
|
+
{ allowedTypes: [ContentValueTypeNames.GRID_PLACEMENT] },
|
|
70
|
+
[
|
|
71
|
+
[PRN.fromString("prn:plate:-1:cms:grid-placement:1"), true],
|
|
72
|
+
["foo", false],
|
|
73
|
+
],
|
|
71
74
|
],
|
|
72
|
-
],
|
|
73
|
-
[
|
|
74
|
-
"with allowed smart text type",
|
|
75
|
-
{ allowedTypes: [ContentValueTypeNames.SMART_TEXT] },
|
|
76
75
|
[
|
|
77
|
-
|
|
78
|
-
[
|
|
76
|
+
"with allowed smart text type",
|
|
77
|
+
{ allowedTypes: [ContentValueTypeNames.SMART_TEXT] },
|
|
78
|
+
[
|
|
79
|
+
[{ type: "root", children: [] }, true],
|
|
80
|
+
[PRN.fromString("prn:plate:-1:cms:grid-placement:1"), false],
|
|
81
|
+
],
|
|
79
82
|
],
|
|
80
|
-
],
|
|
81
|
-
[
|
|
82
|
-
"with incorrect prn",
|
|
83
|
-
{ allowedTypes: [ContentValueTypeNames.CONTENT_ITEM] },
|
|
84
|
-
[[PRN.fromString("prn:plate:-1:am:asset:1"), false]],
|
|
85
|
-
],
|
|
86
|
-
[
|
|
87
|
-
"with multiple types",
|
|
88
|
-
{
|
|
89
|
-
allowedTypes: [ContentValueTypeNames.STRING, ContentValueTypeNames.CONTENT_ITEM],
|
|
90
|
-
},
|
|
91
83
|
[
|
|
92
|
-
|
|
93
|
-
[
|
|
94
|
-
[
|
|
84
|
+
"with incorrect prn",
|
|
85
|
+
{ allowedTypes: [ContentValueTypeNames.CONTENT_ITEM] },
|
|
86
|
+
[[PRN.fromString("prn:plate:-1:ps:asset:1"), false]],
|
|
95
87
|
],
|
|
96
|
-
|
|
97
|
-
|
|
88
|
+
[
|
|
89
|
+
"with multiple types",
|
|
90
|
+
{
|
|
91
|
+
allowedTypes: [ContentValueTypeNames.STRING, ContentValueTypeNames.CONTENT_ITEM],
|
|
92
|
+
},
|
|
93
|
+
[
|
|
94
|
+
["foo", true],
|
|
95
|
+
[PRN.fromString("prn:plate:-1:cms:content-item:1"), true],
|
|
96
|
+
[new Date(), false],
|
|
97
|
+
],
|
|
98
|
+
],
|
|
99
|
+
])("%s", (_, ruleConfig, testCases: unknown[]) => {
|
|
100
|
+
let rule: ValueTypeValidationRule;
|
|
101
|
+
|
|
102
|
+
beforeEach(() => {
|
|
103
|
+
rule = new ValueTypeValidationRule(rulePrn, ruleConfig as ValueTypeValidationRuleSettings);
|
|
104
|
+
});
|
|
105
|
+
|
|
106
|
+
it.each(testCases)("returns %s for the provided value", (value, expected) => {
|
|
107
|
+
expect(rule.validate([value as ContentValueType])).toBeContentValidationResult([expected as boolean]);
|
|
108
|
+
});
|
|
109
|
+
});
|
|
110
|
+
});
|
|
111
|
+
|
|
112
|
+
describe("classifyUpdate", () => {
|
|
98
113
|
let rule: ValueTypeValidationRule;
|
|
114
|
+
const allowedTypes: ContentValueTypeName<ContentValueType>[] = [
|
|
115
|
+
ContentValueTypeNames.STRING,
|
|
116
|
+
ContentValueTypeNames.NUMBER,
|
|
117
|
+
];
|
|
99
118
|
|
|
100
119
|
beforeEach(() => {
|
|
101
|
-
rule = new ValueTypeValidationRule(rulePrn,
|
|
120
|
+
rule = new ValueTypeValidationRule(rulePrn, { allowedTypes });
|
|
102
121
|
});
|
|
103
122
|
|
|
104
|
-
it.each(
|
|
105
|
-
|
|
123
|
+
it.each([
|
|
124
|
+
[ValidationRuleUpdateImpact.NONE, { allowedTypes: [...allowedTypes, ContentValueTypeNames.BOOLEAN] }], // extending
|
|
125
|
+
[ValidationRuleUpdateImpact.NONE, { allowedTypes: [...allowedTypes] }], // unchanged
|
|
126
|
+
[ValidationRuleUpdateImpact.BREAKS, { allowedTypes: [ContentValueTypeNames.BOOLEAN] }], // tightening
|
|
127
|
+
])("returns %s when the new allowed types are %s", (expected, newSettings) => {
|
|
128
|
+
expect(rule.classifyUpdate(newSettings as ValueTypeValidationRuleSettings)).toBe(expected);
|
|
129
|
+
});
|
|
130
|
+
});
|
|
131
|
+
|
|
132
|
+
describe("classifyCreate", () => {
|
|
133
|
+
it("returns BREAKS", () => {
|
|
134
|
+
const rule = new ValueTypeValidationRule(rulePrn, { allowedTypes: [ContentValueTypeNames.STRING] });
|
|
135
|
+
expect(rule.classifyCreate()).toBe(ValidationRuleUpdateImpact.BREAKS);
|
|
106
136
|
});
|
|
107
137
|
});
|
|
108
138
|
});
|
|
@@ -1,16 +1,18 @@
|
|
|
1
1
|
import { InvalidCastError, validateCast } from "@platecms/delta-cast";
|
|
2
2
|
import { PRN } from "@platecms/delta-plate-resource-notation";
|
|
3
3
|
import { ContentValueType, ContentValueTypeName, ContentValueTypeNames } from "@platecms/delta-types";
|
|
4
|
+
import { RuleType } from "../enums/rule-types.enum";
|
|
5
|
+
import { ValidationRuleUpdateImpact } from "../enums/validation-rule-update-impact.enum";
|
|
4
6
|
import { ValidationErrorDetails } from "../errors/validation-error-details";
|
|
7
|
+
import { isSuperset } from "../helpers/is-superset.helper";
|
|
5
8
|
import { RuleInstance } from "../types/rule-instance.interface";
|
|
6
|
-
import { RuleType } from "../enums/rule-types.enum";
|
|
7
9
|
import { BaseValidationRule, ContentValidationResultType } from "./base.validation-rule";
|
|
8
10
|
import { validationFunctionFromValidateValue } from "./validation-rule-function.factory";
|
|
9
11
|
|
|
10
12
|
/**
|
|
11
13
|
* Mapping of PRN resource type to Content Value Type Name.
|
|
12
14
|
*/
|
|
13
|
-
const prnResourceTypeToContentValueTypeNameMap: Record<string,
|
|
15
|
+
const prnResourceTypeToContentValueTypeNameMap: Record<string, ContentValueTypeName<PRN>> = {
|
|
14
16
|
/* eslint-disable @typescript-eslint/naming-convention */
|
|
15
17
|
"content-item": ContentValueTypeNames.CONTENT_ITEM,
|
|
16
18
|
asset: ContentValueTypeNames.ASSET,
|
|
@@ -68,6 +70,19 @@ export class ValueTypeValidationRule extends BaseValidationRule<ValueTypeValidat
|
|
|
68
70
|
public override validate(values: ContentValueType[]): ContentValidationResultType[] {
|
|
69
71
|
return validateValueType(values, this);
|
|
70
72
|
}
|
|
73
|
+
|
|
74
|
+
public override classifyCreate(): ValidationRuleUpdateImpact {
|
|
75
|
+
return ValidationRuleUpdateImpact.BREAKS;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
public override classifyUpdate(newSettings: ValueTypeValidationRuleSettings): ValidationRuleUpdateImpact {
|
|
79
|
+
const oldAllowedTypes = this.settings.allowedTypes;
|
|
80
|
+
const newAllowedTypes = newSettings.allowedTypes;
|
|
81
|
+
|
|
82
|
+
return isSuperset(newAllowedTypes, oldAllowedTypes)
|
|
83
|
+
? ValidationRuleUpdateImpact.NONE
|
|
84
|
+
: ValidationRuleUpdateImpact.BREAKS;
|
|
85
|
+
}
|
|
71
86
|
}
|
|
72
87
|
|
|
73
88
|
// The value type can be one or more of the types specified in the ContentValueType type
|