Merge pull request #2268 from acsbendi/policy-version-fixes
IAM policy version fixes
This commit is contained in:
		
						commit
						3bafc89b40
					
				| @ -26,6 +26,14 @@ class IAMReportNotPresentException(RESTError): | |||||||
|             "ReportNotPresent", message) |             "ReportNotPresent", message) | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
|  | class IAMLimitExceededException(RESTError): | ||||||
|  |     code = 400 | ||||||
|  | 
 | ||||||
|  |     def __init__(self, message): | ||||||
|  |         super(IAMLimitExceededException, self).__init__( | ||||||
|  |             "LimitExceeded", message) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
| class MalformedCertificate(RESTError): | class MalformedCertificate(RESTError): | ||||||
|     code = 400 |     code = 400 | ||||||
| 
 | 
 | ||||||
|  | |||||||
| @ -14,8 +14,8 @@ from moto.core.utils import iso_8601_datetime_without_milliseconds, iso_8601_dat | |||||||
| from moto.iam.policy_validation import IAMPolicyDocumentValidator | from moto.iam.policy_validation import IAMPolicyDocumentValidator | ||||||
| 
 | 
 | ||||||
| from .aws_managed_policies import aws_managed_policies_data | from .aws_managed_policies import aws_managed_policies_data | ||||||
| from .exceptions import IAMNotFoundException, IAMConflictException, IAMReportNotPresentException, MalformedCertificate, \ | from .exceptions import IAMNotFoundException, IAMConflictException, IAMReportNotPresentException, IAMLimitExceededException, \ | ||||||
|     DuplicateTags, TagKeyTooBig, InvalidTagCharacters, TooManyTags, TagValueTooBig |     MalformedCertificate, DuplicateTags, TagKeyTooBig, InvalidTagCharacters, TooManyTags, TagValueTooBig | ||||||
| from .utils import random_access_key, random_alphanumeric, random_resource_id, random_policy_id | from .utils import random_access_key, random_alphanumeric, random_resource_id, random_policy_id | ||||||
| 
 | 
 | ||||||
| ACCOUNT_ID = 123456789012 | ACCOUNT_ID = 123456789012 | ||||||
| @ -67,6 +67,13 @@ class Policy(BaseModel): | |||||||
|         self.create_date = create_date if create_date is not None else datetime.utcnow() |         self.create_date = create_date if create_date is not None else datetime.utcnow() | ||||||
|         self.update_date = update_date if update_date is not None else datetime.utcnow() |         self.update_date = update_date if update_date is not None else datetime.utcnow() | ||||||
| 
 | 
 | ||||||
|  |     def update_default_version(self, new_default_version_id): | ||||||
|  |         for version in self.versions: | ||||||
|  |             if version.version_id == self.default_version_id: | ||||||
|  |                 version.is_default = False | ||||||
|  |                 break | ||||||
|  |         self.default_version_id = new_default_version_id | ||||||
|  | 
 | ||||||
|     @property |     @property | ||||||
|     def created_iso_8601(self): |     def created_iso_8601(self): | ||||||
|         return iso_8601_datetime_with_milliseconds(self.create_date) |         return iso_8601_datetime_with_milliseconds(self.create_date) | ||||||
| @ -770,13 +777,15 @@ class IAMBackend(BaseBackend): | |||||||
|         policy = self.get_policy(policy_arn) |         policy = self.get_policy(policy_arn) | ||||||
|         if not policy: |         if not policy: | ||||||
|             raise IAMNotFoundException("Policy not found") |             raise IAMNotFoundException("Policy not found") | ||||||
| 
 |         if len(policy.versions) >= 5: | ||||||
|  |             raise IAMLimitExceededException("A managed policy can have up to 5 versions. Before you create a new version, you must delete an existing version.") | ||||||
|  |         set_as_default = (set_as_default == "true")  # convert it to python bool | ||||||
|         version = PolicyVersion(policy_arn, policy_document, set_as_default) |         version = PolicyVersion(policy_arn, policy_document, set_as_default) | ||||||
|         policy.versions.append(version) |         policy.versions.append(version) | ||||||
|         version.version_id = 'v{0}'.format(policy.next_version_num) |         version.version_id = 'v{0}'.format(policy.next_version_num) | ||||||
|         policy.next_version_num += 1 |         policy.next_version_num += 1 | ||||||
|         if set_as_default: |         if set_as_default: | ||||||
|             policy.default_version_id = version.version_id |             policy.update_default_version(version.version_id) | ||||||
|         return version |         return version | ||||||
| 
 | 
 | ||||||
|     def get_policy_version(self, policy_arn, version_id): |     def get_policy_version(self, policy_arn, version_id): | ||||||
| @ -799,8 +808,8 @@ class IAMBackend(BaseBackend): | |||||||
|         if not policy: |         if not policy: | ||||||
|             raise IAMNotFoundException("Policy not found") |             raise IAMNotFoundException("Policy not found") | ||||||
|         if version_id == policy.default_version_id: |         if version_id == policy.default_version_id: | ||||||
|             raise IAMConflictException( |             raise IAMConflictException(code="DeleteConflict", | ||||||
|                 "Cannot delete the default version of a policy") |                                        message="Cannot delete the default version of a policy.") | ||||||
|         for i, v in enumerate(policy.versions): |         for i, v in enumerate(policy.versions): | ||||||
|             if v.version_id == version_id: |             if v.version_id == version_id: | ||||||
|                 del policy.versions[i] |                 del policy.versions[i] | ||||||
|  | |||||||
| @ -1144,7 +1144,7 @@ CREATE_POLICY_VERSION_TEMPLATE = """<CreatePolicyVersionResponse xmlns="https:// | |||||||
|     <PolicyVersion> |     <PolicyVersion> | ||||||
|       <Document>{{ policy_version.document }}</Document> |       <Document>{{ policy_version.document }}</Document> | ||||||
|       <VersionId>{{ policy_version.version_id }}</VersionId> |       <VersionId>{{ policy_version.version_id }}</VersionId> | ||||||
|       <IsDefaultVersion>{{ policy_version.is_default }}</IsDefaultVersion> |       <IsDefaultVersion>{{ policy_version.is_default | lower }}</IsDefaultVersion> | ||||||
|       <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> |       <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> | ||||||
|     </PolicyVersion> |     </PolicyVersion> | ||||||
|   </CreatePolicyVersionResult> |   </CreatePolicyVersionResult> | ||||||
| @ -1158,7 +1158,7 @@ GET_POLICY_VERSION_TEMPLATE = """<GetPolicyVersionResponse xmlns="https://iam.am | |||||||
|     <PolicyVersion> |     <PolicyVersion> | ||||||
|       <Document>{{ policy_version.document }}</Document> |       <Document>{{ policy_version.document }}</Document> | ||||||
|       <VersionId>{{ policy_version.version_id }}</VersionId> |       <VersionId>{{ policy_version.version_id }}</VersionId> | ||||||
|       <IsDefaultVersion>{{ policy_version.is_default }}</IsDefaultVersion> |       <IsDefaultVersion>{{ policy_version.is_default | lower }}</IsDefaultVersion> | ||||||
|       <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> |       <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> | ||||||
|     </PolicyVersion> |     </PolicyVersion> | ||||||
|   </GetPolicyVersionResult> |   </GetPolicyVersionResult> | ||||||
| @ -1175,7 +1175,7 @@ LIST_POLICY_VERSIONS_TEMPLATE = """<ListPolicyVersionsResponse xmlns="https://ia | |||||||
|       <member> |       <member> | ||||||
|         <Document>{{ policy_version.document }}</Document> |         <Document>{{ policy_version.document }}</Document> | ||||||
|         <VersionId>{{ policy_version.version_id }}</VersionId> |         <VersionId>{{ policy_version.version_id }}</VersionId> | ||||||
|         <IsDefaultVersion>{{ policy_version.is_default }}</IsDefaultVersion> |         <IsDefaultVersion>{{ policy_version.is_default | lower }}</IsDefaultVersion> | ||||||
|         <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> |         <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> | ||||||
|       </member> |       </member> | ||||||
|       {% endfor %} |       {% endfor %} | ||||||
| @ -1787,7 +1787,7 @@ GET_ACCOUNT_AUTHORIZATION_DETAILS_TEMPLATE = """<GetAccountAuthorizationDetailsR | |||||||
|         {% for policy_version in policy.versions %} |         {% for policy_version in policy.versions %} | ||||||
|           <member> |           <member> | ||||||
|             <Document>{{ policy_version.document }}</Document> |             <Document>{{ policy_version.document }}</Document> | ||||||
|             <IsDefaultVersion>{{ policy_version.is_default }}</IsDefaultVersion> |             <IsDefaultVersion>{{ policy_version.is_default | lower }}</IsDefaultVersion> | ||||||
|             <VersionId>{{ policy_version.version_id }}</VersionId> |             <VersionId>{{ policy_version.version_id }}</VersionId> | ||||||
|             <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> |             <CreateDate>{{ policy_version.created_iso_8601 }}</CreateDate> | ||||||
|           </member> |           </member> | ||||||
|  | |||||||
| @ -345,6 +345,7 @@ def test_create_policy_versions(): | |||||||
|         SetAsDefault=True) |         SetAsDefault=True) | ||||||
|     version.get('PolicyVersion').get('Document').should.equal(json.loads(MOCK_POLICY)) |     version.get('PolicyVersion').get('Document').should.equal(json.loads(MOCK_POLICY)) | ||||||
|     version.get('PolicyVersion').get('VersionId').should.equal("v2") |     version.get('PolicyVersion').get('VersionId').should.equal("v2") | ||||||
|  |     version.get('PolicyVersion').get('IsDefaultVersion').should.be.ok | ||||||
|     conn.delete_policy_version( |     conn.delete_policy_version( | ||||||
|         PolicyArn="arn:aws:iam::123456789012:policy/TestCreatePolicyVersion", |         PolicyArn="arn:aws:iam::123456789012:policy/TestCreatePolicyVersion", | ||||||
|         VersionId="v1") |         VersionId="v1") | ||||||
| @ -352,6 +353,47 @@ def test_create_policy_versions(): | |||||||
|         PolicyArn="arn:aws:iam::123456789012:policy/TestCreatePolicyVersion", |         PolicyArn="arn:aws:iam::123456789012:policy/TestCreatePolicyVersion", | ||||||
|         PolicyDocument=MOCK_POLICY) |         PolicyDocument=MOCK_POLICY) | ||||||
|     version.get('PolicyVersion').get('VersionId').should.equal("v3") |     version.get('PolicyVersion').get('VersionId').should.equal("v3") | ||||||
|  |     version.get('PolicyVersion').get('IsDefaultVersion').shouldnt.be.ok | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | @mock_iam | ||||||
|  | def test_create_many_policy_versions(): | ||||||
|  |     conn = boto3.client('iam', region_name='us-east-1') | ||||||
|  |     conn.create_policy( | ||||||
|  |         PolicyName="TestCreateManyPolicyVersions", | ||||||
|  |         PolicyDocument=MOCK_POLICY) | ||||||
|  |     for _ in range(0, 4): | ||||||
|  |         conn.create_policy_version( | ||||||
|  |             PolicyArn="arn:aws:iam::123456789012:policy/TestCreateManyPolicyVersions", | ||||||
|  |             PolicyDocument=MOCK_POLICY) | ||||||
|  |     with assert_raises(ClientError): | ||||||
|  |         conn.create_policy_version( | ||||||
|  |             PolicyArn="arn:aws:iam::123456789012:policy/TestCreateManyPolicyVersions", | ||||||
|  |             PolicyDocument=MOCK_POLICY) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | @mock_iam | ||||||
|  | def test_set_default_policy_version(): | ||||||
|  |     conn = boto3.client('iam', region_name='us-east-1') | ||||||
|  |     conn.create_policy( | ||||||
|  |         PolicyName="TestSetDefaultPolicyVersion", | ||||||
|  |         PolicyDocument=MOCK_POLICY) | ||||||
|  |     conn.create_policy_version( | ||||||
|  |         PolicyArn="arn:aws:iam::123456789012:policy/TestSetDefaultPolicyVersion", | ||||||
|  |         PolicyDocument=MOCK_POLICY_2, | ||||||
|  |         SetAsDefault=True) | ||||||
|  |     conn.create_policy_version( | ||||||
|  |         PolicyArn="arn:aws:iam::123456789012:policy/TestSetDefaultPolicyVersion", | ||||||
|  |         PolicyDocument=MOCK_POLICY_3, | ||||||
|  |         SetAsDefault=True) | ||||||
|  |     versions = conn.list_policy_versions( | ||||||
|  |         PolicyArn="arn:aws:iam::123456789012:policy/TestSetDefaultPolicyVersion") | ||||||
|  |     versions.get('Versions')[0].get('Document').should.equal(json.loads(MOCK_POLICY)) | ||||||
|  |     versions.get('Versions')[0].get('IsDefaultVersion').shouldnt.be.ok | ||||||
|  |     versions.get('Versions')[1].get('Document').should.equal(json.loads(MOCK_POLICY_2)) | ||||||
|  |     versions.get('Versions')[1].get('IsDefaultVersion').shouldnt.be.ok | ||||||
|  |     versions.get('Versions')[2].get('Document').should.equal(json.loads(MOCK_POLICY_3)) | ||||||
|  |     versions.get('Versions')[2].get('IsDefaultVersion').should.be.ok | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| @mock_iam | @mock_iam | ||||||
| @ -393,6 +435,7 @@ def test_get_policy_version(): | |||||||
|         PolicyArn="arn:aws:iam::123456789012:policy/TestGetPolicyVersion", |         PolicyArn="arn:aws:iam::123456789012:policy/TestGetPolicyVersion", | ||||||
|         VersionId=version.get('PolicyVersion').get('VersionId')) |         VersionId=version.get('PolicyVersion').get('VersionId')) | ||||||
|     retrieved.get('PolicyVersion').get('Document').should.equal(json.loads(MOCK_POLICY)) |     retrieved.get('PolicyVersion').get('Document').should.equal(json.loads(MOCK_POLICY)) | ||||||
|  |     retrieved.get('PolicyVersion').get('IsDefaultVersion').shouldnt.be.ok | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| @mock_iam | @mock_iam | ||||||
| @ -439,6 +482,7 @@ def test_list_policy_versions(): | |||||||
|     versions = conn.list_policy_versions( |     versions = conn.list_policy_versions( | ||||||
|         PolicyArn="arn:aws:iam::123456789012:policy/TestListPolicyVersions") |         PolicyArn="arn:aws:iam::123456789012:policy/TestListPolicyVersions") | ||||||
|     versions.get('Versions')[0].get('VersionId').should.equal('v1') |     versions.get('Versions')[0].get('VersionId').should.equal('v1') | ||||||
|  |     versions.get('Versions')[0].get('IsDefaultVersion').should.be.ok | ||||||
| 
 | 
 | ||||||
|     conn.create_policy_version( |     conn.create_policy_version( | ||||||
|         PolicyArn="arn:aws:iam::123456789012:policy/TestListPolicyVersions", |         PolicyArn="arn:aws:iam::123456789012:policy/TestListPolicyVersions", | ||||||
| @ -448,9 +492,10 @@ def test_list_policy_versions(): | |||||||
|         PolicyDocument=MOCK_POLICY_3) |         PolicyDocument=MOCK_POLICY_3) | ||||||
|     versions = conn.list_policy_versions( |     versions = conn.list_policy_versions( | ||||||
|         PolicyArn="arn:aws:iam::123456789012:policy/TestListPolicyVersions") |         PolicyArn="arn:aws:iam::123456789012:policy/TestListPolicyVersions") | ||||||
|     print(versions.get('Versions')) |  | ||||||
|     versions.get('Versions')[1].get('Document').should.equal(json.loads(MOCK_POLICY_2)) |     versions.get('Versions')[1].get('Document').should.equal(json.loads(MOCK_POLICY_2)) | ||||||
|  |     versions.get('Versions')[1].get('IsDefaultVersion').shouldnt.be.ok | ||||||
|     versions.get('Versions')[2].get('Document').should.equal(json.loads(MOCK_POLICY_3)) |     versions.get('Versions')[2].get('Document').should.equal(json.loads(MOCK_POLICY_3)) | ||||||
|  |     versions.get('Versions')[2].get('IsDefaultVersion').shouldnt.be.ok | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| @mock_iam | @mock_iam | ||||||
| @ -474,6 +519,21 @@ def test_delete_policy_version(): | |||||||
|     len(versions.get('Versions')).should.equal(1) |     len(versions.get('Versions')).should.equal(1) | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
|  | @mock_iam | ||||||
|  | def test_delete_default_policy_version(): | ||||||
|  |     conn = boto3.client('iam', region_name='us-east-1') | ||||||
|  |     conn.create_policy( | ||||||
|  |         PolicyName="TestDeletePolicyVersion", | ||||||
|  |         PolicyDocument=MOCK_POLICY) | ||||||
|  |     conn.create_policy_version( | ||||||
|  |         PolicyArn="arn:aws:iam::123456789012:policy/TestDeletePolicyVersion", | ||||||
|  |         PolicyDocument=MOCK_POLICY_2) | ||||||
|  |     with assert_raises(ClientError): | ||||||
|  |         conn.delete_policy_version( | ||||||
|  |             PolicyArn="arn:aws:iam::123456789012:policy/TestDeletePolicyVersion", | ||||||
|  |             VersionId='v1') | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
| @mock_iam_deprecated() | @mock_iam_deprecated() | ||||||
| def test_create_user(): | def test_create_user(): | ||||||
|     conn = boto.connect_iam() |     conn = boto.connect_iam() | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user