2024-01-03 20:04:40 +00:00
import json
import boto3
import pytest
from botocore . exceptions import ClientError
2024-01-07 12:03:33 +00:00
from moto import mock_aws
2024-01-04 15:27:48 +00:00
from moto . iam . aws_managed_policies import aws_managed_policies_data
2024-01-03 20:04:40 +00:00
# See our Development Tips on writing tests for hints on how to write good tests:
# http://docs.getmoto.org/en/latest/docs/contributing/development_tips/tests.html
DUMMY_PERMISSIONSET_ID = (
" arn:aws:sso:::permissionSet/ins-eeeeffffgggghhhh/ps-hhhhkkkkppppoooo "
)
DUMMY_INSTANCE_ARN = " arn:aws:sso:::instance/ins-aaaabbbbccccdddd "
2024-01-04 15:27:48 +00:00
@pytest.fixture ( name = " managed_policies " )
def get_managed_policies ( ) :
return json . loads ( aws_managed_policies_data )
2024-01-03 20:04:40 +00:00
def create_permissionset ( client ) - > str :
""" Helper function to create a dummy permission set and returns the arn. """
response = client . create_permission_set (
Name = " test-permission-set " ,
InstanceArn = DUMMY_INSTANCE_ARN ,
Description = " test permission set " ,
)
return response [ " PermissionSet " ] [ " PermissionSetArn " ]
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-03 20:04:40 +00:00
def test_put_inline_policy_to_permission_set ( ) :
"""
Tests putting and getting an inline policy to a permission set .
"""
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
dummy_policy = {
" Version " : " 2012-10-17 " ,
" Statement " : [
{
" Effect " : " Allow " ,
" Action " : " s3:GetObject " ,
" Resource " : " arn:aws:s3:::your-bucket-name/* " ,
}
] ,
}
# Happy path
response = client . put_inline_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
InlinePolicy = json . dumps ( dummy_policy ) ,
)
response = client . get_inline_policy_for_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert response [ " InlinePolicy " ] == json . dumps ( dummy_policy )
# Invalid permission set arn
not_create_ps_arn = (
" arn:aws:sso:::permissionSet/ins-eeeeffffgggghhhh/ps-hhhhkkkkppppoxyz "
)
with pytest . raises ( ClientError ) as e :
client . put_inline_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = not_create_ps_arn ,
InlinePolicy = json . dumps ( dummy_policy ) ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ResourceNotFoundException "
assert err [ " Message " ] == " Could not find PermissionSet with id ps-hhhhkkkkppppoxyz "
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-03 20:04:40 +00:00
def test_get_inline_policy_to_permission_set_no_policy ( ) :
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
response = client . get_inline_policy_for_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert response [ " InlinePolicy " ] == " "
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-03 20:04:40 +00:00
def test_delete_inline_policy_to_permissionset ( ) :
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
dummy_policy = {
" Version " : " 2012-10-17 " ,
" Statement " : [
{
" Effect " : " Allow " ,
" Action " : " s3:GetObject " ,
" Resource " : " arn:aws:s3:::your-bucket-name/* " ,
}
] ,
}
client . put_inline_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
InlinePolicy = json . dumps ( dummy_policy ) ,
)
response = client . get_inline_policy_for_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert response [ " InlinePolicy " ] == json . dumps ( dummy_policy )
client . delete_inline_policy_from_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
response = client . get_inline_policy_for_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert response [ " InlinePolicy " ] == " "
2024-01-04 15:27:48 +00:00
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 15:27:48 +00:00
def test_attach_managed_policy_to_permission_set ( ) :
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
permissionset_id = permission_set_arn . split ( " / " ) [ - 1 ]
managed_policy_arn = " arn:aws:iam::aws:policy/AdministratorAccess "
client . attach_managed_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = managed_policy_arn ,
)
response = client . list_managed_policies_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert response [ " AttachedManagedPolicies " ] [ 0 ] [ " Name " ] == " AdministratorAccess "
assert (
response [ " AttachedManagedPolicies " ] [ 0 ] [ " Arn " ]
== " arn:aws:iam::aws:policy/AdministratorAccess "
)
# test for managed policy that is already attached
with pytest . raises ( ClientError ) as e :
client . attach_managed_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = managed_policy_arn ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ConflictException "
assert (
err [ " Message " ]
== f " Permission set with id { permissionset_id } already has a typed link attachment to a manged policy with { managed_policy_arn } "
)
# test for managed policy that does not exist
not_exist_managed_policy_arn = " arn:aws:iam::aws:policy/DoesNotExist "
with pytest . raises ( ClientError ) as e :
client . attach_managed_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = not_exist_managed_policy_arn ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ResourceNotFoundException "
assert (
err [ " Message " ]
== " Policy does not exist with ARN: arn:aws:iam::aws:policy/DoesNotExist "
)
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 15:27:48 +00:00
def test_list_managed_policies_quota_limit ( managed_policies ) :
"""
Tests exceeding the managed policy quota limit .
"""
managed_policies_to_attach = [ ]
policy_count = 0
for policy_name in managed_policies :
path = managed_policies [ policy_name ] [ " Path " ]
# only attach policies with path "/"
if path != " / " :
continue
managed_policies_to_attach . append ( policy_name )
policy_count + = 1
if policy_count > = 21 : # 20 is the quota limit
break
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
permission_set_id = permission_set_arn . split ( " / " ) [ - 1 ]
arn_string = " arn:aws:iam::aws:policy/ "
with pytest . raises ( ClientError ) as e :
# the 21st policy should exceed the quota limit
for managed_policy in managed_policies_to_attach :
client . attach_managed_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = arn_string + managed_policy ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ServiceQuotaExceededException "
assert (
err [ " Message " ]
== f " You have exceeded AWS SSO limits. Cannot create ManagedPolicy more than 20 for id { permission_set_id } . Please refer to https://docs.aws.amazon.com/singlesignon/latest/userguide/limits.html "
)
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 15:27:48 +00:00
def test_list_managed_policies_in_permission_set ( managed_policies ) :
"""
Tests functionality of listing aws managed policies attached to a permission set .
This also tests the pagination functionality .
"""
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
arn_string = " arn:aws:iam::aws:policy/ "
# create a dummy permission set
permission_set_arn = create_permissionset ( client )
managed_policies_names = list ( managed_policies . keys ( ) )
# attach 3 good managed policies
for idx in range ( 3 ) :
managed_policy_name = managed_policies_names [ idx ]
client . attach_managed_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = arn_string + managed_policy_name ,
)
response = client . list_managed_policies_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
MaxResults = 2 ,
)
managed_policies = [ ]
assert len ( response [ " AttachedManagedPolicies " ] ) == 2
managed_policies . extend ( response [ " AttachedManagedPolicies " ] )
next_token = response [ " NextToken " ]
response = client . list_managed_policies_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
MaxResults = 2 ,
NextToken = next_token ,
)
assert len ( response [ " AttachedManagedPolicies " ] ) == 1
managed_policies . extend ( response [ " AttachedManagedPolicies " ] )
# ensure the 3 unique managed policies were returned
actual_managed_policy_names = [
managed_policy [ " Name " ] for managed_policy in managed_policies
]
expected_managed_policy_names = managed_policies_names [ : 3 ]
assert all (
name in actual_managed_policy_names for name in expected_managed_policy_names
)
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 15:27:48 +00:00
def test_detach_managed_policy_from_permission_set ( ) :
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
managed_policy_arn = " arn:aws:iam::aws:policy/AdministratorAccess "
# test for managed policy that is not attached
with pytest . raises ( ClientError ) as e :
client . detach_managed_policy_from_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = managed_policy_arn ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ResourceNotFoundException "
assert (
err [ " Message " ] == f " Could not find ManagedPolicy with arn { managed_policy_arn } "
)
# attach managed policy
client . attach_managed_policy_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = managed_policy_arn ,
)
# detach managed policy
client . detach_managed_policy_from_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
ManagedPolicyArn = managed_policy_arn ,
)
# ensure managed policy is detached
response = client . list_managed_policies_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert len ( response [ " AttachedManagedPolicies " ] ) == 0
2024-01-04 23:05:26 +00:00
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 23:05:26 +00:00
def test_attach_customer_managed_policy_reference_to_permission_set ( ) :
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
policy_name = " test-policy "
policy_path = " /test-path/ "
client . attach_customer_managed_policy_reference_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = {
" Name " : policy_name ,
" Path " : policy_path ,
} ,
)
response = client . list_customer_managed_policy_references_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert len ( response [ " CustomerManagedPolicyReferences " ] ) == 1
assert response [ " CustomerManagedPolicyReferences " ] [ 0 ] [ " Name " ] == policy_name
assert response [ " CustomerManagedPolicyReferences " ] [ 0 ] [ " Path " ] == policy_path
# test for customer managed policy that is already attached
with pytest . raises ( ClientError ) as e :
client . attach_customer_managed_policy_reference_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = {
" Name " : policy_name ,
" Path " : policy_path ,
} ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ConflictException "
assert (
err [ " Message " ]
== f " Given customer managed policy with name: { policy_name } and path { policy_path } already attached "
)
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 23:05:26 +00:00
def test_list_customer_managed_policy_references_in_permission_set ( ) :
"""
Tests listing customer managed policies including pagination .
"""
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
policy_name = " test-policy- "
# attach 3 customer managed policies
for idx in range ( 3 ) :
client . attach_customer_managed_policy_reference_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = { " Name " : f " { policy_name } { idx } " } ,
)
response = client . list_customer_managed_policy_references_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
MaxResults = 2 ,
)
customer_managed_policy_names = [ ]
assert len ( response [ " CustomerManagedPolicyReferences " ] ) == 2
next_token = response [ " NextToken " ]
for name in response [ " CustomerManagedPolicyReferences " ] :
customer_managed_policy_names . append ( name [ " Name " ] )
response = client . list_customer_managed_policy_references_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
MaxResults = 2 ,
NextToken = next_token ,
)
for name in response [ " CustomerManagedPolicyReferences " ] :
customer_managed_policy_names . append ( name [ " Name " ] )
assert len ( response [ " CustomerManagedPolicyReferences " ] ) == 1
# ensure the 3 unique customer managed policies were returned
assert len ( set ( customer_managed_policy_names ) ) == 3
2024-01-07 12:03:33 +00:00
@mock_aws
2024-01-04 23:05:26 +00:00
def test_detach_customer_managed_policy_reference_from_permission_set ( ) :
client = boto3 . client ( " sso-admin " , region_name = " us-east-1 " )
permission_set_arn = create_permissionset ( client )
# trying to detach a policy that doesn't exist yet
with pytest . raises ( ClientError ) as e :
client . detach_customer_managed_policy_reference_from_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = {
" Name " : " test-policy " ,
} ,
)
err = e . value . response [ " Error " ]
assert err [ " Code " ] == " ResourceNotFoundException "
assert (
err [ " Message " ]
== " Given managed policy with name: test-policy and path / does not exist on PermissionSet "
)
# attach a policy
client . attach_customer_managed_policy_reference_to_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = {
" Name " : " test-policy " ,
" Path " : " /some-path/ " ,
} ,
)
# try to detach the policy but default path (should fail)
with pytest . raises ( ClientError ) as e :
client . detach_customer_managed_policy_reference_from_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = {
" Name " : " test-policy " ,
} ,
)
# detach the policy
client . detach_customer_managed_policy_reference_from_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
CustomerManagedPolicyReference = {
" Name " : " test-policy " ,
" Path " : " /some-path/ " ,
} ,
)
# ensure policy is detached
response = client . list_customer_managed_policy_references_in_permission_set (
InstanceArn = DUMMY_INSTANCE_ARN ,
PermissionSetArn = permission_set_arn ,
)
assert len ( response [ " CustomerManagedPolicyReferences " ] ) == 0