0

I'm using Amazon S3 in a Flask Python application, however, I don't want to hardcode my access keys as Amazon has problems with making the keys publicly available. Is there a way to get the keys into the application without exposing them. I saw a suggestion about using environment variables and another about IAM User roles but the documentation isn't helping.

Edit: I forgot to mention that I'm deploying this application on Docker and want to allow it so that if another user pulls the image from docker, my access keys won't be compromised. I'm not using AWS EC2

Paolo
  • 21,270
  • 6
  • 38
  • 69
  • 1
    You usually specify those credentials via environment variables. If you're using the AWS SDK, it may also be able to pick up the credentials automatically from the IAM role assigned to the instance or container if you run it on AWS infrastructure. To get the best answer for you, you need to tell us more about how exactly you're going to run your app. – deceze Feb 21 '20 at 08:34
  • I'm going to use docker build to create a docker image of the application to share with other members of my team so that they can use the application in their various regions. The application downloads files from a S3 bucket as well as uploads files to it. – GigabyteRebirth Feb 21 '20 at 08:52
  • Does this answer your question? https://stackoverflow.com/questions/36354423/which-is-the-best-way-to-pass-aws-credentials-to-docker-container – N.Moudgil Feb 21 '20 at 08:55
  • Not using EC2, my Flask application just uses S3 as a file storage option. I just need the keys to be available in the application not only for my local system but any other user without compromising the keys – GigabyteRebirth Feb 21 '20 at 08:58
  • This is what you should use for AWS. https://docs.aws.amazon.com/systems-manager/latest/userguide/systems-manager-parameter-store.html – gsb22 Feb 21 '20 at 09:06
  • If the image will be run outside of AWS, then you need to create and distribute IAM user credentials to those teams. Those can be set as environment variables when running the image. – deceze Feb 21 '20 at 09:19

2 Answers2

0

Following could be of help:

  • IAM Roles (If your application is already running in AWS, Instance Roles can help you fetch temporary tokens to access resources like S3. AWS CLIs OR official SDKs are already built with these capabilities and you need not implement any custom code. For this to work, you assign a Role 'X' to the EC2 instance, Role 'X' then needs to have a policy mapping, where you define the permissions)

A sample policy could be something like:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "AllowAccessToObjects",
            "Action": [
                "s3:PutObject",
                "s3:PutObjectAcl",
                "s3:GetObject",
                "s3:GetObjectAcl",
                "s3:GetObjectVersion",
                "s3:GetObjectVersionAcl",
                "s3:ListMultipartUploadParts"
            ],
            "Effect": "Allow",
            "Resource": [
                "arn:aws:s3:::<Bucket_Name>/*"
            ],
            "Condition": {
                "IpAddress": {
                    "aws:SourceIp": [
                        "w.x.y.z/32"
                    ]
                }
            }
        },
        {
            "Sid": "AllowAccessToBucket",
            "Action": [
                "s3:PutObject",
                "s3:ListBucket",
                "s3:GetBucketVersioning",
                "s3:ListBucketVersions"
            ],
            "Effect": "Allow",
            "Resource": [
                "arn:aws:s3:::<Bucket_Name>"
            ],
            "Condition": {
                "IpAddress": {
                    "aws:SourceIp": [
                        "a.b.c.d/32"
                    ]
                }
            }
        }
    ]
}

Usually the best approach is to never have any statically provisioned credentials at all. In case implementing something like that is not possible at all, then :

  • Other options could be storing the secrets in an external secret store like Vault etc., and when the container starts, the secrets can be fetched and injected before bootstrapping the application. These are then available as ENVs
akskap
  • 803
  • 6
  • 12
0

The Python AWS SDK looks at several possible locations for credentials. The most pertinent here would be environment variables:

Boto3 will check these environment variables for credentials:

AWS_ACCESS_KEY_ID
The access key for your AWS account.

AWS_SECRET_ACCESS_KEY
The secret key for your AWS account.

You should create separate IAM users with appropriate permissions for each user or team you're going to distribute your docker image to, and they can set those environment variables via docker when running your image.

Community
  • 1
  • 1
deceze
  • 510,633
  • 85
  • 743
  • 889