Search code examples
amazon-web-servicesaws-cloudformationamazon-iamaws-codecommit

AWS Cloudformation - CodeCommit - Deny Push to Master


So here is the situation: I have a Cloudformation that creates CodeCommit repositories with some extra resources for other devops processes to work.

I got the requeriment to block users from doing a push to a specific branch, in this case master, I have found the policy that does that. source: https://docs.aws.amazon.com/codecommit/latest/userguide/how-to-conditional-branch.html

So I write a role and policy with the following:

Resources:
  CodeCommitRepository:
    Type: AWS::CodeCommit::Repository
    Properties:
      RepositoryName: !Sub '${ProjectCode}-${ProjectName}-${ComponentName}'
      RepositoryDescription: !Ref CodeCommitRepositoryDescription
      Tags:
        - Key: fdr:general:project-code
          Value: !Ref ProjectCode
        - Key: fdr:general:project-name
          Value: !Ref ProjectName

  DenyPushRole:
    Type: AWS::IAM::Role
    Properties:
      RoleName: !Sub '${ProjectCode}-${ProjectName}-${ComponentName}-DenyPush-Role'
      ManagedPolicyArns:
        - !Ref DenyPushToMasterPolicy
      AssumeRolePolicyDocument:
        Version: '2012-10-17'
        Statement:
        - Action:
            - sts:AssumeRole
          Effect: Allow
          Principal:
            Service:
              - codecommit.amazonaws.com

  DenyPushToMasterPolicy:
    Type: AWS::IAM::ManagedPolicy
    Properties:
      ManagedPolicyName: !Sub '${ProjectCode}-${ProjectName}-${ComponentName}-DenyPush-Policy'
      Description: Policy to deny push to master
      PolicyDocument:
        Version: 2012-10-17
        Statement:
        - Action:
          - codecommit:GitPush
          - codecommit:PutFile
          - codecommit:DeleteBranch
          - codecommit:MergePullRequestByFastForward
          Effect: Deny
          Resource: !GetAtt CodeCommitRepository.Arn
          Condition:
            StringEqualsIfExists:
              codecommit:References: 
              - refs/heads/master
            'Null':
              codecommit:References: 'false'

As I understand which I wouldn't say is much, by creating the Role with the Policy and the sts:AssumeRole I thought that any user using that repository will assume that role that denys them the ability to push to master but that wasn't the case.

I guess that we may be overcomplicating things and we should put that policy unto all users directly on IAM but the idea is to have it done very granular. What am I doing wrong or is it even possible?.

Best regards


Solution

  • DenyPushRole is not for any users. You specified it to be only for codecommit.amazonaws.com which is incorrect.

    Users do not automatically assume any roles. They have to explicitly assume your DenyPushRole using AssumeRole API call. Your users must also have permission to sts:AssumeRole.

    Thus your role, in a general form, should be:

      DenyPushRole:
        Type: AWS::IAM::Role
        Properties:
          RoleName: !Sub '${ProjectCode}-${ProjectName}-${ComponentName}-DenyPush-Role'
          ManagedPolicyArns:
            - !Ref DenyPushToMasterPolicy
          AssumeRolePolicyDocument:
            Version: '2012-10-17'
            Statement:
            - Action:
                - sts:AssumeRole
              Effect: Allow
              Principal:
                AWS: 
                  - !Ref AWS::AccountId
    

    Once the role exist, and the users have sts:AssumeRole to assume it, they will use the AssumeRole command to actually assume the role. This will give then new, temporary AWS credentials to perform any actions specified by the role. In your case, the role only denies, so they will not be able to do anything anyway. You would need to add some allow statements to the role for your uses to be actually able to do something, not only deny.