This repository has been archived by the owner on May 1, 2024. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathIAMPolicyDocumentValidator.ts
72 lines (64 loc) · 2.61 KB
/
IAMPolicyDocumentValidator.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
import * as _ from 'lodash';
import { Validator, ValidationFn } from '../validate';
import * as validate from '../validate';
import { Path, ErrorFn } from '../types';
const listOf = (fn: ValidationFn): ValidationFn => {
return (path: Path, value: any, addError: ErrorFn) => {
return validate.list(path, value, addError, fn);
}
}
const stringOf = (allowedValues: string[]): ValidationFn => {
return (path: Path, value: any, addError: ErrorFn) => {
return validate.string(path, value, addError, allowedValues);
}
}
const validatePrincipal = (path: Path, value: any, addError: ErrorFn) => {
if (_.isPlainObject(value)) {
const spec = {
AWS: [validate.optional, validate.or(validate.string, listOf(validate.string))],
Federated: [validate.optional, validate.string],
CanonicalUser: [validate.optional, validate.string],
Service: [validate.optional, validate.or(validate.string, listOf(validate.string))],
};
if (_.isEmpty(value)) {
addError(path, `you must provide one of ${_.join(_.keys(spec), ', ')}`);
return false;
} else {
return validate.object(path, value, addError, spec);
}
} else {
return validate.string(path, value, addError);
}
};
// https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements.html
const validateStatement = (path: Path, value: any, addError: ErrorFn): boolean => {
const spec = {
Sid: [validate.optional, validate.string],
Effect: [validate.required, stringOf(['Allow', 'Deny'])],
// Principal can not be specified for inline policies
Principal: [validate.optional, validatePrincipal],
NotPrincipal: [validate.optional, validatePrincipal],
Action: [validate.required, validate.or(validate.string, listOf(validate.string))],
Resource: [validate.optional, validate.or(validate.string, listOf(validate.string))],
Condition: [validate.optional, validate.object],
};
return validate.object(path, value, addError, spec);
}
export default class IAMPolicyDocumentValidator extends Validator {
ResourceProperty(path: Path, name: string, value: any) {
if (name === 'PolicyDocument') {
const spec = {
Id: [validate.optional, validate.string],
Version: [validate.optional, validate.string],
Statement: [validate.required, (path: Path, statement: any, addError: ErrorFn) => {
if(_.isArray(statement)) {
return listOf(validateStatement)(path, statement, addError);
} else {
return validateStatement(path, statement, addError);
}
}]
};
validate.object(path, value, this.addError, spec);
}
}
}