Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Option to specify a custom JSON policy file #14

Closed
simonw opened this issue Nov 3, 2021 · 6 comments
Closed

Option to specify a custom JSON policy file #14

simonw opened this issue Nov 3, 2021 · 6 comments
Labels
enhancement New feature or request research

Comments

@simonw
Copy link
Owner

simonw commented Nov 3, 2021

Based on #11 I'm now thinking that there is value in applying custom policies - since that way people can tweak the policies used and share them with others.

Maybe a --policy policy.json option would be useful?

One challenge: the need to hard-code the name of the bucket into that policy. So perhaps it supports the absolute dumbest template system ever, like literally replacing $!BUCKET_NAME!$ in the JSON with the name of the bucket.

@simonw simonw added enhancement New feature or request research labels Nov 3, 2021
@simonw
Copy link
Owner Author

simonw commented Nov 3, 2021

I'm tempted to support three variants of this here:

# From a file
s3-credentials create mybucket --policy policy.json

# From stdin
cat policy.json | s3-credentials create mybucket --policy -

# Pass in the literal policy as a string

s3-credentials create mybucket --policy '{
        "Version": "2012-10-17"
        ...
}'

It's a little weird to have an option which can tell the difference between a file name and a literal string of JSON, but it's not hard to implement - check if the passed string starts with a { and is valid JSON - and I think I like it better than supporting two options of --policy filename and --policy-string policy-string.

@simonw
Copy link
Owner Author

simonw commented Nov 3, 2021

I can use click.open_file() in the implementation to handle -: https://github.com/pallets/click/blob/2996d3c11972ad1d71339481f2119495185e7d8d/src/click/utils.py#L335-L342

@simonw
Copy link
Owner Author

simonw commented Nov 3, 2021

Tested my work in progress like this:

% s3-credentials create static.niche-museums.com \
  --username custom-policy \
  --policy /tmp/custom-policy.json
Attached policy s3.read-write.static.niche-museums.com to user custom-policy
Created access key for user: custom-policy
{
    "UserName": "custom-policy",
    "AccessKeyId": "AKIAWXFXAIOZE56QRRHG",
    "Status": "Active",
    "SecretAccessKey": "...",
    "CreateDate": "2021-11-03 18:29:17+00:00"
}
% s3-credentials list-user-policies custom-policy
User: custom-policy
PolicyName: s3.read-write.static.niche-museums.com
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "ListObjectsInBucketIsMyCustomSid",
            "Effect": "Allow",
            "Action": [
                "s3:ListBucket"
            ],
            "Resource": [
                "arn:aws:s3:::static.niche-museums.com"
            ]
        },
        {
            "Sid": "AllObjectActions",
            "Effect": "Allow",
            "Action": "s3:*Object",
            "Resource": [
                "arn:aws:s3:::static.niche-museums.com/*"
            ]
        }
    ]
}

Where /tmp/custom-policy.json contained this:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "ListObjectsInBucketIsMyCustomSid",
            "Effect": "Allow",
            "Action": ["s3:ListBucket"],
            "Resource": ["arn:aws:s3:::$!BUCKET_NAME!$"]
        },
        {
            "Sid": "AllObjectActions",
            "Effect": "Allow",
            "Action": "s3:*Object",
            "Resource": ["arn:aws:s3:::$!BUCKET_NAME!$/*"]
        }
    ]
}

@simonw
Copy link
Owner Author

simonw commented Nov 3, 2021

Here's what happens if you feed it valid JSON that does not form a valid policy document:

% s3-credentials create static.niche-museums.com \
  --username custom-policy \
  --policy '{}'                   
Created user: custom-policy with permissions boundary: arn:aws:iam::aws:policy/AmazonS3FullAccess
Traceback (most recent call last):
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/bin/s3-credentials", line 33, in <module>
    sys.exit(load_entry_point('s3-credentials', 'console_scripts', 's3-credentials')())
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/click/core.py", line 1128, in __call__
    return self.main(*args, **kwargs)
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/click/core.py", line 1053, in main
    rv = self.invoke(ctx)
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/click/core.py", line 1659, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/click/core.py", line 1395, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/click/core.py", line 754, in invoke
    return __callback(*args, **kwargs)
  File "/Users/simon/Dropbox/Development/s3-credentials/s3_credentials/cli.py", line 190, in create
    iam.put_user_policy(
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/botocore/client.py", line 388, in _api_call
    return self._make_api_call(operation_name, kwargs)
  File "/Users/simon/.local/share/virtualenvs/s3-credentials-J8M1ChYK/lib/python3.10/site-packages/botocore/client.py", line 708, in _make_api_call
    raise error_class(parsed_response, operation_name)
botocore.errorfactory.MalformedPolicyDocumentException: An error occurred (MalformedPolicyDocument) when calling the PutUserPolicy operation: Syntax errors in policy.

I'm not going to bother catching that, I think the erro message is clear enough as it stands.

@simonw simonw closed this as completed in 34d0350 Nov 3, 2021
@simonw
Copy link
Owner Author

simonw commented Nov 3, 2021

@simonw
Copy link
Owner Author

simonw commented Nov 3, 2021

Realized I missed something here: the username and policy name generated still has read-write as part of it even when using a custom policy.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request research
Projects
None yet
Development

No branches or pull requests

1 participant