Skip to content
This repository was archived by the owner on Oct 20, 2021. It is now read-only.

Commit 43f53a9

Browse files
feat(rules): Added KeySet rule
1 parent bbc7ae5 commit 43f53a9

File tree

6 files changed

+102
-3
lines changed

6 files changed

+102
-3
lines changed

README.md

+1
Original file line numberDiff line numberDiff line change
@@ -146,6 +146,7 @@ The library can be loaded either as a standalone script, or through an [AMD](htt
146146
- [Iterable](docs/iterable.md)
147147
- [Json](docs/json.md)
148148
- [KeyNested](docs/key-nested.md)
149+
- [KeySet](docs/key-set.md)
149150
- [KeyValue](docs/key-value.md)
150151
- [Key](docs/key.md)
151152
- [Label](docs/label.md)

awesome-validator.min.js

+3-3
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

docs/key-set.md

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
# KeySet
2+
3+
Validates a keys in a defined structure.
4+
5+
Valid values:
6+
7+
```js
8+
validator.keySet(new Key('foo')).validate({foo: 'foobar'});
9+
validator.keySet(validtor.key('foo')).validate(new Map<string, string>([['foo', 'bar']]));
10+
```
11+
12+
Invalid values:
13+
14+
```js
15+
validator.keySet(validator.key('foo')).validate({bar: 'foobar'});
16+
validator.keySet(new Key('foo')).validate(new Map<string, string>());
17+
```

src/rules/index.ts

+1
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,7 @@ export * from './ip';
6767
export * from './iterable';
6868
export * from './json';
6969
export * from './key-nested';
70+
export * from './key-set';
7071
export * from './key-value';
7172
export * from './key';
7273
export * from './label';

src/rules/key-set.ts

+51
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
import { Validatable } from './../validatable';
2+
import { AllOf } from './all-of';
3+
import { Key } from './key';
4+
5+
export class KeySet extends AllOf {
6+
7+
/**
8+
* Add rule.
9+
*/
10+
public addRule(rule: Validatable): this {
11+
let r: Validatable | undefined = rule;
12+
13+
if (rule instanceof AllOf && rule.getRules().length === 1) {
14+
r = rule.getRules().shift();
15+
}
16+
17+
if (r instanceof Key) {
18+
this.rules.add(r);
19+
}
20+
21+
return this;
22+
}
23+
24+
/**
25+
* Validate.
26+
*/
27+
public validate(input: any): boolean {
28+
return this.hasValidStructure(input) && super.validate(input);
29+
}
30+
31+
/**
32+
* Has valid structure.
33+
*/
34+
protected hasValidStructure(input: any): boolean {
35+
let i: number = 0;
36+
37+
for (const rule of this.getRules()) {
38+
if (!(rule instanceof Key) || (!new Key(rule.reference).validate(input) && rule.mandatory)) {
39+
return false;
40+
}
41+
42+
i++;
43+
}
44+
45+
if (input instanceof Map) {
46+
return i === input.size;
47+
}
48+
49+
return i === Object.keys(input).length;
50+
}
51+
}

test/rules/key-set.ts

+29
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
import { assert } from 'chai';
2+
3+
import { AbstractRule } from '../../src/rules/abstract-rule';
4+
import { AllOf } from '../../src/rules/all-of';
5+
import { Key } from '../../src/rules/key';
6+
import { KeySet } from '../../src/rules/key-set';
7+
import { StringType } from '../../src/rules/string-type';
8+
9+
describe('KeySet', () => {
10+
11+
it('is rule', () => {
12+
assert.instanceOf(new KeySet(), AbstractRule);
13+
});
14+
15+
it('values is valid', () => {
16+
assert.isTrue(new KeySet(new Key('foo')).validate({foo: 'foobar'}));
17+
assert.isTrue(new KeySet(new AllOf(new Key('foo'))).validate({foo: 'foobar'}));
18+
assert.isTrue(new KeySet(new Key('foo')).validate(new Map<string, string>([['foo', 'bar']])));
19+
assert.isTrue(new KeySet(new Key('bar', undefined, false)).validate({foo: 'foobar'}));
20+
});
21+
22+
it('values is not valid', () => {
23+
assert.isFalse(new KeySet(new Key('foo')).validate({bar: 'foobar'}));
24+
assert.isFalse(new KeySet(new StringType()).validate({bar: 'foobar'}));
25+
assert.isFalse(new KeySet(new Key('foo')).validate(new Map<string, string>()));
26+
assert.isFalse(new KeySet().validate({bar: 'foobar'}));
27+
});
28+
29+
});

0 commit comments

Comments
 (0)