Esempio n. 1
0
 def test_condition_is_a_restricted_action(self):
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect": "Allow",
             "Action": "cloudwatch:PutMetricData",
             "Resource": "*",
             "Condition": {
                 "StringEquals": {
                     "cloudwatch:namespace": "Namespace"
                 }
             }
         }]
     }
     policy_document = PolicyDocument(test_policy)
     self.assertListEqual(
         policy_document.all_allowed_unrestrictable_actions, [])
     test_policy_without_condition = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect": "Allow",
             "Action": "cloudwatch:PutMetricData",
             "Resource": "*",
         }]
     }
     policy_document_without_condition = PolicyDocument(
         test_policy_without_condition)
     self.assertListEqual(
         policy_document_without_condition.
         all_allowed_unrestrictable_actions, ["cloudwatch:PutMetricData"])
 def test_gh_254_flag_risky_actions_with_resource_constraints_privilege_escalation(
         self):
     # Privilege Escalation: https://cloudsplaining.readthedocs.io/en/latest/glossary/privilege-escalation/#updating-an-assumerole-policy
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect":
             "Allow",
             "Action": ["iam:UpdateAssumeRolePolicy", "sts:AssumeRole"],
             "Resource":
             "arn:aws:iam::111122223333:role/MyRole"
         }]
     }
     policy_document = PolicyDocument(test_policy,
                                      flag_resource_arn_statements=True)
     expected_result = [{
         'type':
         'UpdateRolePolicyToAssumeIt',
         'actions': ['iam:updateassumerolepolicy', 'sts:assumerole']
     }]
     self.assertDictEqual(policy_document.allows_privilege_escalation[0],
                          expected_result[0])
     policy_document = PolicyDocument(test_policy,
                                      flag_resource_arn_statements=False)
     self.assertListEqual(policy_document.allows_privilege_escalation, [])
Esempio n. 3
0
    def test_gh_106_excluded_actions_should_not_show_in_results(self):
        """test_gh_106_excluded_actions_should_not_show_in_results: Make sure that autoscaling:SetDesiredCapacity does not show in results when it is excluded"""
        test_policy = {
            "Version":
            "2012-10-17",
            "Statement": [{
                "Sid":
                "Something",
                "Effect":
                "Allow",
                "Action": [
                    "autoscaling:SetDesiredCapacity",
                    "autoscaling:TerminateInstanceInAutoScalingGroup",
                    "autoscaling:UpdateAutoScalingGroup"
                ],
                "Resource":
                "*",
            }]
        }
        exclusions_cfg = {
            "policies": ["aws-service-role*"],
            "roles": ["aws-service-role*"],
            "users": [""],
            "include-actions": ["s3:GetObject"],
            "exclude-actions": [
                "autoscaling:SetDesiredCapacity",
                "autoscaling:TerminateInstanceInAutoScalingGroup",
                "autoscaling:UpdateAutoScalingGroup"
            ]
        }
        exclusions = Exclusions(exclusions_cfg)
        policy_document = PolicyDocument(test_policy, exclusions)
        print(policy_document.infrastructure_modification)
        self.assertEqual(policy_document.infrastructure_modification, [])

        exclusions_cfg_2 = {
            "policies": ["aws-service-role*"],
            "roles": ["aws-service-role*"],
            "users": [""],
            "include-actions": ["s3:GetObject"],
            "exclude-actions": [
                "autoscaling:SetDesiredCapacity",
                "autoscaling:TerminateInstanceInAutoScalingGroup",
            ]
        }
        exclusions_2 = Exclusions(exclusions_cfg_2)
        policy_document_2 = PolicyDocument(test_policy, exclusions_2)
        # Should still include one result
        print(policy_document_2.infrastructure_modification)
        self.assertEqual(policy_document_2.infrastructure_modification,
                         ["autoscaling:UpdateAutoScalingGroup"])
Esempio n. 4
0
    def scan_resource_conf(self, conf):
        if 'Properties' in conf.keys():
            props_conf = conf['Properties']
            policies_key = 'Policies'

            # Obtain a list of 1 or more policies regardless of resource schema
            if policies_key in props_conf.keys():
                policy_conf = props_conf[policies_key]
            else:
                policy_conf = [props_conf]

            # Scan all policies
            for policy in policy_conf:
                policy_doc_key = 'PolicyDocument'
                if isinstance(policy, dict) and policy_doc_key in policy.keys():
                    # When using unresolved Cfn functions, policy is an str
                    policy_doc = policy[policy_doc_key]
                    try:
                        converted_policy_doc = convert_cloudformation_conf_to_iam_policy(policy_doc)
                        statement_key = 'Statement'
                        if statement_key in converted_policy_doc:
                            policy_statement = PolicyDocument(converted_policy_doc)
                            violations = self.cloudsplaining_analysis(policy_statement)
                            if violations:
                                logging.debug("detailed cloudsplainging finding: {}",json.dumps(violations))
                                return CheckResult.FAILED
                    except Exception as e:
                        # this might occur with templated iam policies where ARN is not in place or similar
                        logging.debug("could not run cloudsplaining analysis on policy {}", conf)
                        return CheckResult.UNKNOWN
            return CheckResult.PASSED
Esempio n. 5
0
 def scan_resource_conf(self, conf):
     if 'Properties' in conf.keys():
         props_conf = conf['Properties']
         key = 'PolicyDocument'
         if key in props_conf.keys():
             converted_conf = props_conf[key]
             try:
                 converted_conf = convert_cloudformation_conf_to_iam_policy(
                     converted_conf)
                 key = 'Statement'
                 if key in converted_conf:
                     policy = PolicyDocument(converted_conf)
                     violations = self.cloudsplaining_analysis(policy)
                     if violations:
                         logging.debug(
                             "detailed cloudsplainging finding: {}",
                             json.dumps(violations))
                         return CheckResult.FAILED
             except Exception as e:
                 # this might occur with templated iam policies where ARN is not in place or similar
                 logging.debug(
                     "could not run cloudsplaining analysis on policy {}",
                     conf)
                 return CheckResult.UNKNOWN
     return CheckResult.PASSED
Esempio n. 6
0
    def test_allows_specific_actions(self):
        test_policy = {
            "Version":
            "2012-10-17",
            "Statement": [{
                "Effect":
                "Allow",
                "Action": [
                    "iam:PassRole", "ssm:GetParameter", "s3:GetObject",
                    "ssm:GetParameter", "ssm:GetParameters",
                    "ssm:GetParametersByPath", "secretsmanager:GetSecretValue"
                ],
                "Resource":
                "*"
            }]
        }
        policy_document = PolicyDocument(test_policy)
        results = policy_document.allows_specific_actions_without_constraints(
            ["iam:PassRole"])
        self.assertListEqual(results, ["iam:PassRole"])
        # Input should be case insensitive, but give the pretty CamelCase action name result
        results = policy_document.allows_specific_actions_without_constraints(
            ["iam:passrole"])
        self.assertListEqual(results, ["iam:PassRole"])

        # Verify that it will find the high priority read-only actions that we care about
        high_priority_read_only_actions = [
            "s3:GetObject", "ssm:GetParameter", "ssm:GetParameters",
            "ssm:GetParametersByPath", "secretsmanager:GetSecretValue"
        ]
        results = policy_document.allows_specific_actions_without_constraints(
            high_priority_read_only_actions)
        self.assertListEqual(results, high_priority_read_only_actions)
Esempio n. 7
0
 def _policy_document(self):
     """Return the policy document object"""
     policy_document = {}
     for policy_version in self.policy_version_list:
         if policy_version.get("IsDefaultVersion") is True:
             policy_document = PolicyDocument(policy_version.get("Document"), exclusions=self.exclusions)
     return policy_document
Esempio n. 8
0
 def test_finding_actions_excluded(self):
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect":
             "Allow",
             "Action":
             ["s3:GetObject", "logs:CreateLogStream", "logs:PutLogEvents"],
             "Resource":
             "*"
         }]
     }
     policy_document = PolicyDocument(test_policy)
     # (1) EXCLUDE actions
     exclusions_cfg = {
         "users": ["obama"],
         "groups": ["admin"],
         "roles": ["MyRole"],
         "policies": ["someOtherName"],
         "exclude-actions": ["logs:CreateLogStream", "logs:PutLogEvents"]
     }
     exclusions = Exclusions(exclusions_cfg)
     finding = Finding(
         policy_name="MyPolicy",
         arn="arn:aws:iam::123456789012:group/SNSNotifications",
         actions=["s3:GetObject"],
         policy_document=policy_document,
         exclusions=exclusions)
     # print(finding.actions)
     self.assertListEqual(finding.actions, ["s3:GetObject"])
Esempio n. 9
0
    def test_group_membership_finding(self):
        test_policy = {
            "Version":
            "2012-10-17",
            "Statement": [{
                "Effect": "Allow",
                "Action": ["s3:GetObject"],
                "Resource": "*"
            }]
        }
        policy_document = PolicyDocument(test_policy)

        exclusions_cfg = dict(users=["obama"],
                              groups=["admin"],
                              roles=["MyRole"],
                              policies=["AWSLambdaFullAccess"])
        exclusions = Exclusions(exclusions_cfg)
        group_finding = GroupFinding(
            policy_name="MyPolicy",
            arn="arn:aws:iam::123456789012:group/GroupShouldBeEmpty",
            actions=["s3:GetObject"],
            policy_document=policy_document,
            exclusions=exclusions,
            members=["obama"])
        result = group_finding.is_excluded(exclusions)
        self.assertListEqual(result, [])
        group_finding = GroupFinding(
            policy_name="MyPolicy",
            arn="arn:aws:iam::123456789012:group/GroupShouldBeEmpty",
            actions=["s3:GetObject"],
            policy_document=policy_document,
            exclusions=exclusions,
            members=["yolo"])
        self.assertFalse(group_finding.is_excluded(exclusions))
Esempio n. 10
0
    def test_actions_without_constraints_deny(self):
        test_policy = {
            "Version":
            "2012-10-17",
            "Statement": [{
                "Effect":
                "Deny",
                "Action": [
                    "iam:UpdateUser", "iam:TagRole", "iam:UntagRole",
                    "s3:PutBucketAcl", "s3:GetObject", "s3:PutObject",
                    "s3:CreateBucket"
                ],
                "Resource":
                "*"
            }]
        }
        policy_document = PolicyDocument(test_policy)
        results = policy_document.permissions_management_without_constraints
        self.assertListEqual(results, [])

        results = policy_document.write_actions_without_constraints
        self.assertListEqual(results, [])

        results = policy_document.tagging_actions_without_constraints
        self.assertListEqual(results, [])
Esempio n. 11
0
    def __init__(
        self,
        policy_detail: Dict[str, Any],
        exclusions: Exclusions = DEFAULT_EXCLUSIONS,
        flag_conditional_statements: bool = False,
        flag_resource_arn_statements: bool = False,
    ) -> None:
        """
        Initialize the InlinePolicy object.

        :param policy_detail: The JSON containing the PolicyName and PolicyDocument
        """
        if not isinstance(exclusions, Exclusions):
            raise Exception(
                "The exclusions provided is not an Exclusions type object. "
                "Please supply an Exclusions object and try again.")
        # Fix Issue #254 - Allow flagging risky actions even when there are resource constraints
        self.flag_conditional_statements = flag_conditional_statements
        self.flag_resource_arn_statements = flag_resource_arn_statements

        self.policy_name = policy_detail.get("PolicyName", "")
        self.policy_document = PolicyDocument(
            cast(Dict[str, Any], policy_detail.get("PolicyDocument")),
            exclusions=exclusions,
            flag_conditional_statements=flag_conditional_statements,
            flag_resource_arn_statements=flag_resource_arn_statements)
        # Generating the provider ID based on a string representation of the Policy Document,
        # to avoid collisions where there are inline policies with the same name but different contents
        # self.policy_id = get_non_provider_id(self.policy_name)
        self.policy_id = get_non_provider_id(
            json.dumps(self.policy_document.json))

        self.exclusions = exclusions
        self.is_excluded = self._is_excluded(exclusions)
Esempio n. 12
0
 def test_policy_document_not_action_deny_gh_23(self):
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Sid": "DenyAllUsersNotUsingMFA",
             "Effect": "Deny",
             "NotAction": "iam:*",
             "Resource": "*",
             "Condition": {
                 "BoolIfExists": {
                     "aws:MultiFactorAuthPresent": "false"
                 }
             }
         }]
     }
     policy_document = PolicyDocument(test_policy)
     allowed_actions = []
     for statement in policy_document.statements:
         if not statement.has_resource_constraints:
             if statement.expanded_actions:
                 allowed_actions.extend(
                     statement.expanded_actions)  # pragma: no cover
     self.assertListEqual(allowed_actions, [])
     self.assertListEqual(policy_document.all_allowed_unrestricted_actions,
                          [])
     # print(json.dumps(policy_document.contains_statement_using_not_action, indent=4))
     self.assertListEqual(
         policy_document.contains_statement_using_not_action,
         test_policy["Statement"])
Esempio n. 13
0
 def test_gh_193_AmazonEC2ContainerRegistryReadOnly(self):
     # https://docs.aws.amazon.com/AmazonECR/latest/userguide/ecr_managed_policies.html#AmazonEC2ContainerRegistryReadOnly
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect":
             "Allow",
             "Action": [
                 "ecr:GetAuthorizationToken",
                 "ecr:BatchCheckLayerAvailability",
                 "ecr:GetDownloadUrlForLayer", "ecr:GetRepositoryPolicy",
                 "ecr:DescribeRepositories", "ecr:ListImages",
                 "ecr:DescribeImages", "ecr:BatchGetImage",
                 "ecr:GetLifecyclePolicy", "ecr:GetLifecyclePolicyPreview",
                 "ecr:ListTagsForResource", "ecr:DescribeImageScanFindings"
             ],
             "Resource":
             "*"
         }]
     }
     policy_document = PolicyDocument(test_policy)
     self.assertTrue("ecr:GetAuthorizationToken" not in
                     policy_document.all_allowed_unrestricted_actions)
     self.assertListEqual(policy_document.write_actions_without_constraints,
                          [])
     self.assertListEqual(policy_document.credentials_exposure,
                          ['ecr:GetAuthorizationToken'])
 def test_findings_excluded(self):
     test_policy = {
         "Version": "2012-10-17",
         "Statement": [
             {
                 "Effect": "Allow",
                 "Action": [
                     "s3:GetObject",
                     "logs:CreateLogStream",
                     "logs:PutLogEvents"
                 ],
                 "Resource": "*"
             }
         ]
     }
     policy_document = PolicyDocument(test_policy)
     always_exclude_actions = [
         "logs:CreateLogStream",
         "logs:PutLogEvents"
     ]
     finding = Finding(
         policy_name="MyPolicy",
         arn="arn:aws:iam::123456789012:group/SNSNotifications",
         actions=["s3:GetObject"],
         policy_document=policy_document,
         always_exclude_actions=always_exclude_actions
     )
     print(finding.actions)
     self.assertListEqual(finding.actions, ["s3:GetObject"])
Esempio n. 15
0
    def __init__(self, group_detail, policy_details):
        """
        Initialize the GroupDetail object.

        :param group_detail: Details about a particular group
        :param policy_details: The PolicyDetails object - i.e., details about all managed policies in the account so the group can inherit those attributes
        """
        self.create_date = group_detail.get("CreateDate")
        self.arn = group_detail.get("Arn")
        self.path = group_detail.get("Path")
        self.group_id = group_detail.get("GroupId")
        self.group_name = group_detail.get("GroupName")

        # Inline Policies
        self.inline_policies = {}
        if group_detail.get("GroupPolicyList"):
            for inline_policy in group_detail.get("GroupPolicyList"):
                non_provider_id = get_non_provider_id(
                    inline_policy.get("PolicyName"))
                self.inline_policies[non_provider_id] = dict(
                    PolicyName=inline_policy.get("PolicyName"),
                    PolicyDocument=PolicyDocument(
                        inline_policy.get("PolicyDocument")),
                )

        # Managed Policies (either AWS-managed or Customer managed)
        self.attached_managed_policies = []
        if group_detail.get("AttachedManagedPolicies"):
            self._attached_managed_policies_details(
                group_detail.get("AttachedManagedPolicies"), policy_details)
        else:
            self.attached_managed_policies = []
Esempio n. 16
0
    def test_findings_add_list(self):
        """output.findings.findings.add: Make sure the add function works with adding it as a list"""
        test_policy = {
            "Version":
            "2012-10-17",
            "Statement": [{
                "Effect": "Allow",
                "Action": ["s3:GetObject"],
                "Resource": "*"
            }]
        }
        policy_document = PolicyDocument(test_policy)
        finding_1 = Finding(
            policy_name="MyPolicy",
            arn="arn:aws:iam::123456789012:group/SNSNotifications",
            actions=["s3:GetObject"],
            policy_document=policy_document)
        finding_2 = Finding(policy_name="MyPolicy",
                            arn="arn:aws:iam::aws:policy/BadAWSManagedPolicy",
                            actions=["s3:GetObject"],
                            policy_document=policy_document)

        findings = Findings()
        findings.add([finding_1, finding_2])
        result = findings.json
        self.assertTrue(len(result) == 2)
    def test_policy_document_all_allowed_actions(self):
        """scan.policy_document.all_allowed_actions"""
        test_policy = {
            "Version": "2012-10-17",
            "Statement": [
                {
                    "Effect": "Allow",
                    "Action": [
                        "ssm:GetParameters",
                        "ecr:PutImage"
                    ],
                    "Resource": "*"
                },
                {
                    "Sid": "AllowManageOwnAccessKeys",
                    "Effect": "Allow",
                    "Action": [
                        "iam:CreateAccessKey"
                    ],
                    "Resource": "arn:aws:iam::*:user/${aws:username}"
                }
            ]
        }
        policy_document = PolicyDocument(test_policy)
        result = policy_document.all_allowed_actions

        expected_result = [
            "ecr:PutImage",
            "ssm:GetParameters",
            "iam:CreateAccessKey"
        ]
        self.assertListEqual(result, expected_result)
 def test_policy_document_return_json(self):
     test_policy = {
         "Version": "2012-10-17",
         "Statement": [
             {
                 "Effect": "Allow",
                 "Action": [
                     "ecr:PutImage"
                 ],
                 "Resource": "*"
             },
           {
                 "Sid": "AllowManageOwnAccessKeys",
                 "Effect": "Allow",
                 "Action": [
                     "iam:CreateAccessKey"
                 ],
                 "Resource": "arn:aws:iam::*:user/${aws:username}"
             }
         ]
     }
     policy_document = PolicyDocument(test_policy)
     result = policy_document.json
     # That function returns the Policy as JSON
     self.assertEqual(result, test_policy)
    def test_policy_document_contains_statement_using_not_action(self):
        test_policy = {
            "Version": "2012-10-17",
            "Statement": [
                {
                    "Sid": "Something",
                    "Effect": "Allow",
                    "NotAction": "iam:*",
                    "Resource": "*",
                }
            ]
        }
        policy_document = PolicyDocument(test_policy)

        results = policy_document.contains_statement_using_not_action
        expected_results = [
            {
                "Sid": "Something",
                "Effect": "Allow",
                "NotAction": "iam:*",
                "Resource": "*"
            }
        ]
        # print(json.dumps(results, indent=4))
        self.assertListEqual(results, expected_results)
Esempio n. 20
0
    def test_policy_finding_for_resource_exposure(self):
        test_policy = {
            "Version": "2012-10-17",
            "Statement": [
                {
                    "Effect": "Allow",
                    "Action": [
                        "s3:PutObjectAcl"
                    ],
                    "Resource": "*"
                }
            ]
        }
        policy_document = PolicyDocument(test_policy)

        exclusions_cfg = dict()
        exclusions = Exclusions(exclusions_cfg)

        policy_finding = PolicyFinding(policy_document, exclusions)
        results = policy_finding.results
        expected_results = {
            "ServicesAffected": ["s3"],
            "PrivilegeEscalation": [],
            "ResourceExposure": ["s3:PutObjectAcl"],
            "DataExfiltration": [],
            "ServiceWildcard": [],
            "CredentialsExposure": [],
            "InfrastructureModification": ["s3:PutObjectAcl"],
        }
        # print(json.dumps(results, indent=4))
        self.assertDictEqual(results, expected_results)
 def _policy_document(self) -> PolicyDocument:
     """Return the policy document object"""
     for policy_version in self.policy_version_list:
         if policy_version.get("IsDefaultVersion") is True:
             return PolicyDocument(policy_version.get("Document"),
                                   exclusions=self.exclusions)
     raise Exception(
         "Managed Policy ARN %s has no default Policy Document version",
         self.arn)
Esempio n. 22
0
    def __init__(self, policy_detail):
        """
        Initialize the InlinePolicy object.

        :param policy_detail: The JSON containing the PolicyName and PolicyDocument
        """
        self.policy_name = policy_detail.get("PolicyName")
        self.policy_document = PolicyDocument(
            policy_detail.get("PolicyDocument"))
        self.policy_id = get_non_provider_id(self.policy_name)
Esempio n. 23
0
    def test_principal_findings(self):
        """output.new_findings.UserFinding"""
        test_policy = {
            "Version":
            "2012-10-17",
            "Statement": [{
                "Effect": "Allow",
                "Action": ["s3:GetObject"],
                "Resource": "*"
            }]
        }
        policy_document = PolicyDocument(test_policy)
        # (1) If the user is a member of an excluded group, return True

        exclusions_cfg = dict(users=["obama"],
                              groups=["admin"],
                              roles=["MyRole"],
                              policies=["AWSLambdaFullAccess"])
        exclusions = Exclusions(exclusions_cfg)
        user_finding = UserFinding(
            policy_name="MyPolicy",
            arn="arn:aws:iam::123456789012:user/SomeUser",
            actions=["s3:GetObject"],
            policy_document=policy_document,
            group_membership=["admin"],
            exclusions=exclusions)
        result = user_finding.is_excluded(exclusions)
        expected_result = ["admin"]
        self.assertListEqual(result, expected_result)

        # (2) If the user is explicitly excluded, return True
        exclusions = Exclusions(exclusions_cfg)
        user_finding = UserFinding(
            policy_name="MyPolicy",
            arn="arn:aws:iam::123456789012:user/obama",  # Obama is excluded
            actions=["s3:GetObject"],
            policy_document=policy_document,
            group_membership=["not-excluded-group"],
            exclusions=exclusions)
        result = user_finding.is_excluded(exclusions)
        expected_result = ["obama"]
        self.assertListEqual(result, expected_result)

        # (3) If the policy attached is excluded
        user_finding = UserFinding(
            policy_name="AWSLambdaFullAccess",
            arn=
            "arn:aws:iam::123456789012:user/not-excluded-user",  # Obama is excluded
            actions=["s3:GetObject"],
            policy_document=policy_document,
            group_membership=["not-excluded-group"],
            exclusions=exclusions)
        result = user_finding.is_excluded(exclusions)
        expected_result = ["AWSLambdaFullAccess"]
        self.assertListEqual(result, expected_result)
 def scan_data_conf(self, conf):
     key = 'statement'
     if key in conf.keys():
         converted_conf = convert_terraform_conf_to_iam_policy(conf)
         policy = PolicyDocument(converted_conf)
         violations = self.cloudsplaining_analysis(policy)
         if violations:
             logging.debug("detailed cloudsplainging finding: {}",
                           json.dumps(violations))
             return CheckResult.FAILED
     return CheckResult.PASSED
Esempio n. 25
0
def scan_policy(policy_json, exclusions_config=DEFAULT_EXCLUSIONS_CONFIG):
    """
    Scan a policy document for missing resource constraints.

    :param policy_json: Dictionary containing the IAM policy.
    :param exclusions_config: Exclusions configuration. If none, just send an empty dictionary. Defaults to the contents of cloudsplaining.shared.default-exclusions.yml
    :return:
    """
    policy_document = PolicyDocument(policy_json)
    exclusions = Exclusions(exclusions_config)
    policy_finding = PolicyFinding(policy_document, exclusions)
    return policy_finding.results
 def test_gh_254_flag_risky_actions_with_resource_constraints_credentials_exposure(
         self):
     # Credentials Exposure: https://cloudsplaining.readthedocs.io/en/latest/glossary/credentials-exposure/
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect": "Allow",
             "Action": [
                 "iam:UpdateAccessKey",
             ],
             "Resource": "arn:aws:iam::111122223333:user/MyUser"
         }]
     }
     policy_document = PolicyDocument(test_policy,
                                      flag_resource_arn_statements=True)
     self.assertListEqual(policy_document.credentials_exposure,
                          ['iam:UpdateAccessKey'])
     policy_document = PolicyDocument(test_policy,
                                      flag_resource_arn_statements=False)
     self.assertListEqual(policy_document.credentials_exposure, [])
Esempio n. 27
0
 def test_finding_attributes(self):
     """scan.findings.new_finding"""
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect": "Allow",
             "Action": ["s3:GetObject"],
             "Resource": "*"
         }]
     }
     policy_document = PolicyDocument(test_policy)
     finding = Finding(
         policy_name="MyPolicy",
         arn="arn:aws:iam::123456789012:group/SNSNotifications",
         actions=["s3:GetObject"],
         policy_document=policy_document)
     self.assertEqual(finding.account_id, "123456789012")
     self.assertEqual(finding.managed_by, "Customer")
     self.assertEqual(len(finding.services_affected), 1)
     self.assertEqual(len(finding.actions), 1)
     self.assertDictEqual(finding.policy_document.json,
                          policy_document.json)
     expected_finding_json = {
         "AccountID": "123456789012",
         "ManagedBy": "Customer",
         "Name": "SNSNotifications",
         "PolicyName": "MyPolicy",
         "Type": "Group",
         "Arn": "arn:aws:iam::123456789012:group/SNSNotifications",
         "ActionsCount": 1,
         "ServicesCount": 1,
         "Services": ["s3"],
         "Actions": ["s3:GetObject"],
         "PolicyDocument": {
             "Version":
             "2012-10-17",
             "Statement": [{
                 "Effect": "Allow",
                 "Action": ["s3:GetObject"],
                 "Resource": "*"
             }]
         },
         "AssumableByComputeService": [],
         "AssumeRolePolicyDocument": None,
         "PrivilegeEscalation": [],
         "DataExfiltrationActions": ["s3:GetObject"],
         "PermissionsManagementActions": [],
     }
     # print(json.dumps(finding.json, indent=4))
     self.maxDiff = None
     self.assertDictEqual(finding.json, expected_finding_json)
def scan_policy(policy_json, policy_name, exclusions_cfg=DEFAULT_EXCLUSIONS_CONFIG):
    """
    Scan a policy document for missing resource constraints.

    :param policy_json: The AWS IAM policy document.
    :param exclusions_cfg: Defaults to the embedded exclusions file, which has no effect here.
    :param policy_name: The name of the IAM policy. Defaults to the filename when used from command line.
    :return:
    """
    policy_document = PolicyDocument(policy_json)
    actions_missing_resource_constraints = []

    # EXCLUDED ACTIONS - actions to exclude if they are false positives
    excluded_actions = exclusions_cfg.get("exclude-actions", None)
    if excluded_actions == [""]:
        excluded_actions = None

    # convert to lowercase for comparison purposes
    # some weird if/else logic to reduce loops and improve performance slightly
    if excluded_actions:
        excluded_actions = [x.lower() for x in excluded_actions]

    always_include_actions = exclusions_cfg.get("include-actions")
    findings = Findings()

    for statement in policy_document.statements:
        if statement.effect == "Allow":
            actions_missing_resource_constraints.extend(
                statement.missing_resource_constraints_for_modify_actions(
                    always_include_actions
                )
            )
    if actions_missing_resource_constraints:
        results_placeholder = []
        for action in actions_missing_resource_constraints:
            if excluded_actions:
                if not is_name_excluded(action.lower(), excluded_actions):
                    results_placeholder.append(action)  # pragma: no cover
            else:
                results_placeholder.append(action)
        actions_missing_resource_constraints = list(
            dict.fromkeys(results_placeholder)
        )  # remove duplicates
        actions_missing_resource_constraints.sort()
        finding = Finding(
            policy_name=policy_name,
            arn=policy_name,
            actions=actions_missing_resource_constraints,
            policy_document=policy_document,
        )
        findings.add(finding)
    return findings.json
Esempio n. 29
0
 def test_all_allowed_unrestriced_deny(self):
     """scan.policy_document.all_allowed_unrestricted_actions"""
     test_policy = {
         "Version": "2012-10-17",
         "Statement": [{
             "Effect": "Deny",
             "Action": "*",
             "Resource": "*",
         }]
     }
     policy_document = PolicyDocument(test_policy)
     result = policy_document.all_allowed_unrestricted_actions
     self.assertEquals([], result)
 def test_gh_254_flag_risky_actions_with_resource_constraints_data_exfiltration(
         self):
     # Data Exfiltration: https://cloudsplaining.readthedocs.io/en/latest/glossary/data-exfiltration/
     test_policy = {
         "Version":
         "2012-10-17",
         "Statement": [{
             "Effect": "Allow",
             "Action": [
                 "s3:GetObject",
             ],
             "Resource": "arn:aws:s3:::mybucket/*"
         }]
     }
     policy_document = PolicyDocument(test_policy,
                                      flag_resource_arn_statements=True)
     self.assertListEqual(policy_document.allows_data_exfiltration_actions,
                          ['s3:GetObject'])
     policy_document = PolicyDocument(test_policy,
                                      flag_resource_arn_statements=False)
     self.assertListEqual(policy_document.allows_data_exfiltration_actions,
                          [])