Compare commits
2 Commits
developmen
...
improvemen
Author | SHA1 | Date |
---|---|---|
Will Toozs | 227b869869 | |
Will Toozs | ca00292dd9 |
|
@ -310,6 +310,7 @@ export function evaluatePolicy(
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* @deprecated Upgrade to evaluateAllPoliciesV2
|
||||||
* Evaluate whether a request is permitted under a policy.
|
* Evaluate whether a request is permitted under a policy.
|
||||||
* @param requestContext - Info necessary to
|
* @param requestContext - Info necessary to
|
||||||
* evaluate permission
|
* evaluate permission
|
||||||
|
@ -325,6 +326,16 @@ export function evaluateAllPolicies(
|
||||||
allPolicies: any[],
|
allPolicies: any[],
|
||||||
log: Logger,
|
log: Logger,
|
||||||
): string {
|
): string {
|
||||||
|
return evaluateAllPoliciesV2(requestContext, allPolicies, log).verdict;
|
||||||
|
}
|
||||||
|
export function evaluateAllPoliciesV2(
|
||||||
|
requestContext: RequestContext,
|
||||||
|
allPolicies: any[],
|
||||||
|
log: Logger,
|
||||||
|
): {
|
||||||
|
verdict: string;
|
||||||
|
isImplicit: boolean;
|
||||||
|
} {
|
||||||
log.trace('evaluating all policies');
|
log.trace('evaluating all policies');
|
||||||
let allow = false;
|
let allow = false;
|
||||||
let allowWithTagCondition = false;
|
let allowWithTagCondition = false;
|
||||||
|
@ -333,7 +344,10 @@ export function evaluateAllPolicies(
|
||||||
const singlePolicyVerdict = evaluatePolicy(requestContext, allPolicies[i], log);
|
const singlePolicyVerdict = evaluatePolicy(requestContext, allPolicies[i], log);
|
||||||
// If there is any Deny, just return Deny
|
// If there is any Deny, just return Deny
|
||||||
if (singlePolicyVerdict === 'Deny') {
|
if (singlePolicyVerdict === 'Deny') {
|
||||||
return 'Deny';
|
return {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: false,
|
||||||
|
};
|
||||||
}
|
}
|
||||||
if (singlePolicyVerdict === 'Allow') {
|
if (singlePolicyVerdict === 'Allow') {
|
||||||
allow = true;
|
allow = true;
|
||||||
|
@ -344,6 +358,7 @@ export function evaluateAllPolicies(
|
||||||
} // else 'Neutral'
|
} // else 'Neutral'
|
||||||
}
|
}
|
||||||
let verdict;
|
let verdict;
|
||||||
|
let isImplicit = false;
|
||||||
if (allow) {
|
if (allow) {
|
||||||
if (denyWithTagCondition) {
|
if (denyWithTagCondition) {
|
||||||
verdict = 'NeedTagConditionEval';
|
verdict = 'NeedTagConditionEval';
|
||||||
|
@ -355,8 +370,9 @@ export function evaluateAllPolicies(
|
||||||
verdict = 'NeedTagConditionEval';
|
verdict = 'NeedTagConditionEval';
|
||||||
} else {
|
} else {
|
||||||
verdict = 'Deny';
|
verdict = 'Deny';
|
||||||
|
isImplicit = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
log.trace('result of evaluating all policies', { verdict });
|
log.trace('result of evaluating all policies', { verdict, isImplicit });
|
||||||
return verdict;
|
return { verdict, isImplicit };
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,6 +6,7 @@ const fakeTimers = require('@sinonjs/fake-timers');
|
||||||
const evaluator = require('../../lib/policyEvaluator/evaluator');
|
const evaluator = require('../../lib/policyEvaluator/evaluator');
|
||||||
const evaluatePolicy = evaluator.evaluatePolicy;
|
const evaluatePolicy = evaluator.evaluatePolicy;
|
||||||
const evaluateAllPolicies = evaluator.evaluateAllPolicies;
|
const evaluateAllPolicies = evaluator.evaluateAllPolicies;
|
||||||
|
const evaluateAllPoliciesV2 = evaluator.evaluateAllPoliciesV2;
|
||||||
const handleWildcards =
|
const handleWildcards =
|
||||||
require('../../lib/policyEvaluator/utils/wildcards').handleWildcards;
|
require('../../lib/policyEvaluator/utils/wildcards').handleWildcards;
|
||||||
const substituteVariables =
|
const substituteVariables =
|
||||||
|
@ -1451,6 +1452,49 @@ describe('policyEvaluator', () => {
|
||||||
assert.strictEqual(result, 'Deny');
|
assert.strictEqual(result, 'Deny');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should deny access if any policy results in a Deny', () => {
|
||||||
|
requestContext = new RequestContext({}, {},
|
||||||
|
'my_favorite_bucket', undefined,
|
||||||
|
undefined, undefined, 'bucketDelete', 's3');
|
||||||
|
requestContext.setRequesterInfo({});
|
||||||
|
const result = evaluateAllPoliciesV2(requestContext,
|
||||||
|
[samples['arn:aws:iam::aws:policy/AmazonS3FullAccess'],
|
||||||
|
samples['Deny Bucket Policy']], log);
|
||||||
|
assert.deepStrictEqual(result, {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: false,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should deny access if request action is not in any policy', () => {
|
||||||
|
requestContext = new RequestContext({}, {},
|
||||||
|
'notVeryPrivate', undefined,
|
||||||
|
undefined, undefined, 'bucketDelete', 's3');
|
||||||
|
requestContext.setRequesterInfo({});
|
||||||
|
const result = evaluateAllPoliciesV2(requestContext,
|
||||||
|
[samples['Multi-Statement Policy'],
|
||||||
|
samples['Variable Bucket Policy']], log);
|
||||||
|
assert.deepStrictEqual(result, {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: true,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should deny access if request resource is not in any policy', () => {
|
||||||
|
requestContext = new RequestContext({}, {},
|
||||||
|
'notbucket', undefined,
|
||||||
|
undefined, undefined, 'objectGet', 's3');
|
||||||
|
requestContext.setRequesterInfo({});
|
||||||
|
const result = evaluateAllPoliciesV2(requestContext, [
|
||||||
|
samples['Multi-Statement Policy'],
|
||||||
|
samples['Variable Bucket Policy'],
|
||||||
|
], log);
|
||||||
|
assert.deepStrictEqual(result, {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: true,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
const TestMatrixPolicies = {
|
const TestMatrixPolicies = {
|
||||||
Allow: {
|
Allow: {
|
||||||
Version: '2012-10-17',
|
Version: '2012-10-17',
|
||||||
|
@ -1504,6 +1548,136 @@ describe('policyEvaluator', () => {
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const TestMatrixV2 = [
|
||||||
|
{
|
||||||
|
policiesToEvaluate: [],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Allow'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Allow',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Neutral'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Deny'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Allow', 'Allow'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Allow',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Allow', 'Neutral'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Allow',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Neutral', 'Allow'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Allow',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Neutral', 'Neutral'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Allow', 'Deny'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['AllowWithTagCondition'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'NeedTagConditionEval',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Allow', 'AllowWithTagCondition'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Allow',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['DenyWithTagCondition'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['Allow', 'DenyWithTagCondition'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'NeedTagConditionEval',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['AllowWithTagCondition', 'DenyWithTagCondition'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'NeedTagConditionEval',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['AllowWithTagCondition', 'DenyWithTagCondition', 'Deny'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'Deny',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
policiesToEvaluate: ['DenyWithTagCondition', 'AllowWithTagCondition', 'Allow'],
|
||||||
|
expectedPolicyEvaluation: {
|
||||||
|
verdict: 'NeedTagConditionEval',
|
||||||
|
isImplicit: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
TestMatrixV2.forEach(testCase => {
|
||||||
|
it(`policies evaluating individually to [${testCase.policiesToEvaluate.join(', ')}] `
|
||||||
|
+ `should return ${testCase.expectedPolicyEvaluation}`, () => {
|
||||||
|
requestContext = new RequestContext({}, {},
|
||||||
|
'my_favorite_bucket', undefined,
|
||||||
|
undefined, undefined, 'objectGet', 's3');
|
||||||
|
requestContext.setRequesterInfo({});
|
||||||
|
const result = evaluateAllPoliciesV2(
|
||||||
|
requestContext,
|
||||||
|
testCase.policiesToEvaluate.map(policyName => TestMatrixPolicies[policyName]),
|
||||||
|
log);
|
||||||
|
assert.deepStrictEqual(result, testCase.expectedPolicyEvaluation);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
const TestMatrix = [
|
const TestMatrix = [
|
||||||
{
|
{
|
||||||
policiesToEvaluate: [],
|
policiesToEvaluate: [],
|
||||||
|
|
Loading…
Reference in New Issue