In the Documentation for Resource-Based Policies for Lambda, it mentions that it's best practice to include the source-account incase for example you specified a source-arn which referred to an s3 bucket which does not have the account id in the arn, so if you were unlucky and somebody deleted your bucket, and another account created a bucket with the same name they could indirectly access your Lambda function.
But then you also have the notation of a Principal, as in one of the examples they have:
"Principal":{"AWS":"arn:aws:iam::210987654321:root"}
What is the difference between Principal & source-account. Do you use the Principal in the case when you want to refine the permissions down to a particular role or user within an account? And if this isn't your situation and you only want to grant access to your Lambda from an entire account you would use source-account?
One reason of using the aws:SourceAccount is the mitigation of The Confused Deputy Problem.
Specifically, in the context of S3, it is used so that S3 is not considered as the confused deputy.
The principal is what has the permission to trigger the resource, for example in this case the principal is actually the S3 service. This is because S3 is not configured to assume IAM roles, the service is actually the caller of the Lambda function.
The conditions underneath then scope the permissions to only allow the S3 service to call when it is coming from the source account/bucket. Without this it would be an open scope to Amazon S3.
You're correct that principals can be used to reference IAM users/roles and in your example the entire AWS account (assuming the caller is actually an IAM user/role). You would use this method if the caller was an IAM entity vs another AWS service.
Related
I'm struggling to understand the practical differences between an execution role that can be assumed by API gateway to grant the permission to execute a lambda over a lambda resource-based policy.
For example, the documentation here provides an example of a policy that can be assumed by the API gateway to invoke a Lambda.
However, the API Gateway console will grant itself permission to access a Lambda via a lambda resource-based policy.
Both achieve the desired outcome of allowing the API Gateway to execute a Lambda. So is there a reason to choose one over the other?
Apart from the general use case / advantages of having resource-based policy that is explained pretty well here
does not have to give up his or her permissions to receive the role permissions
In this specific case, I have experienced 2 distintive advantages using Lambda's resource based policy over role
The creator of Lambda - API Gateway integration does not need to have access to IAM. No role created
Because no role is created, no role need to be cleaned up. The developer delete the Lambda function he created to play around and everyone can forget about it
I think one of the significant advantages of resource-based policies is that they can be applied to specific versions or aliases. This is unlike IAM roles, which cannot target a specific version or alias.
I am currently still learning IAM role. As an example, I was able to create EC2 type role and attach the S3 Full Access Control policy. In that case, my EC2 instances can access S3 once the role is attached. Fairly easy to understand.
What is a use case if we select S3 as the type of trusted entity? From my understanding, the access to S3 is usually controlled by the policy. How would S3 service as trusted entity assume the role and what kind of policies could be attached to this role? Just wondering if someone could give me a use case for this. Thanks.
When you add a trusted entity to an IAM role that service is granted the ability to assume the IAM role.
For S3 an example of when this needs to happen is when you want to enable replication, you grant the S3 service the ability to retrieve items from a bucket and put them in another bucket.
For more information on this specific use case take a look at the Setting up permissions for replication page.
I am trying to prevent access by valid principals in my account to buckets outside of my account, and am trying to use an S3 endpoint.
My account is in us-east-1 and my buckets are in the same region. When I configure an S3 endpoint and allow access through endpoint policy only to specific buckets, I see that access to other buckets in the same region is denied. While this seems intuitive, there is no explicit deny in either the principal's IAM policy or the bucket policy.
Therefore, question #1: is this the expected endpoint behavior?
Now, if I try to access bucket in us-west-1, I am able to access it, even though there's no Allow clause in endpoint policy and I have no other presence in us-west-1. This implies that an endpoint policy only applies to buckets defined in the same region as the endpoint.
Therefore, question #2: is my observation correct? If so, how do I prevent access to arbitrary buckets, definitely those outside my account, in regions other than current one (us-east-1)?
Thanks!
You can use IAM roles to restrict access to resources in other regions.
There is a write up on it here
I can't confirm the endpoint behavior but your logic seems sound.
I am deploying a server program in an ec2 instance which needs to be able to create pre-signed urls for s3. So far I've had my AWS credentials in environment variables for testing, but I would like to switch to the IAM Role strategy now. However, I am unsure as to which policies the role should have access too. My initial guess is to have AmazonS3FullAccess, but the description says "Provides full access to all buckets via the AWS Management Console" but the ec2 instance will be using the c++ sdk, not the management console. Or is the policy not important, just that it has a policy so it gets credentials somehow?
You're confusing policies and roles.
a policy grants permissions to a user or to a role or to a group.
the difference between a user and a role is subtle, but basically a role is something that's assumed by other services in AWS, like an EC2 instance, while a user is generally just an identity you've created for use in AWS.
The policy description for full access may make mention to the management console, but it grants full access to all buckets whether through the console, the api or an sdk, they're all really the same thing under the hood.
You should not use the fullaccess policy. You could use it as a base to build your real policy, but IAM should always use the least privilege principal, where you only give the permissions that are absolutely required, in this case the role only needs read and possibly list permissions on the specific bucket in question if generating urls for reading, or put permissions if allowing uploads.
I read https://aws.amazon.com/blogs/security/iam-policies-and-bucket-policies-and-acls-oh-my-controlling-access-to-s3-resources/, which to me answered the what and when, but not why.
I’m new to AWS and trying to learning it.
Why create two methods, and not just one? Based on the example in the article, why not just have IAM policy to handle both use cases, example like having IAM policy JSON include the ‘Principal’ entry as “base on association” or “??”, then it work like the Bucket policy. It look like for any services which require policy control will have another type of policy created. Example; YYY service policy will have a Principal and Action “YYY:”.
Reason I can think of is, S3 is where require lot of access control (like fine grain, grouping, etc..) and having a policy created specific S3 can ease management, and take less back-end resources?
S3 authorizes requests by testing all applicable authorities, in the "context" of user, bucket, and object.
See How Amazon S3 Authorizes a Request.
This document is confusing on first read, but it does give a better sense of what's happening with the multiple policies.
A few points to keep in mind:
Users do not own buckets. Accounts own buckets, and accounts own users.
If a user creates a bucket, the account that owns that user always owns that bucket.
If a user creates an object, the account that owns that user always owns that object -- even if the bucket where the object was created is owned by a different account.
Wait, what?
If my account gives your user permission to create an object in my bucket, you would actually own the object. Unless you give me permission to read it, I can't read it. Since it's in my bucket, and I am paying to store it, I can delete it, but that's absolutely all I can do to that object unless you give me access to it.
So there are three levels of permissions at play -- things users are allowed to do (IAM policies), things accounts allow to be done to their bucket and their objects in that bucket (bucket policies and ACLs) and things accounts allow to be done to objects they own (object ACLs).
The default action is implicit deny, but anything my account has the authority to allow can be allowed by allowing it in any one place, as long as it isn't explicitly denied, elsewhere. Explicit deny will always deny, without exception.
Implications of the model:
my user, my bucket, my object requires only one grant; access can be granted in any of the three places and only needs to be granted in one place, because my account owns all the resources... so I can do this in IAM policy, or bucket policy, or on the object.
my user, your bucket requires two grants -- I allow my user in IAM policy, and you must allow my user in yout bucket policy. I don't have authority to do things to your bucket without your consent, and you don't have authority to allow my user to do things without my consent.
it is possible to make my object in my bucket publicly readable via either the object ACL or via bucket policy, but not IAM policy, because IAM policies apply to users, and "everybody" is not one of my IAM users.
So, S3 needs multiple sources of grants becase of the permissions model. If you aren't doing anything cross-account, some of this would not be obvious since you would be unaware of some of the possible combinations.
My preference is for my bucket policies to require little attention. Users are given access in IAM, public objects are made public at the object level (you can do this in bucket policy, but I prefer it to be explicit at the object level), and so bucket policies have limited purpose -- sometimes there are bucket policy rules that deny access for all IP addresses except a list, usually the bucket policy denies uploads without AES-256 (so you can't "forget" to encrypt objects), and sometimes there are origin access identity rules for interoperating with CloudFront... but I do very little customization of bucket policies, because that's my design philosophy.
There are various reasons why there is IAM permission policy and resource-based policy such as S3 bucket policy.
Let's say you have a S3 bucket and you want to grant access to other account. It is not possible only using IAM policy. Hence you need the bucket policy to include the account or IAM entity as Principal.
Also, you cannot use Principal in the IAM permission policy since when you attach the policy to an IAM user, when the user makes request, it becomes the Principal.
Please have a look into the following for more details:
http://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements.html#Principal
http://docs.aws.amazon.com/AmazonS3/latest/dev/access-control-overview.html