REW
REW

Reputation: 776

Deploying an AWS Lambda from a different account

I have a Lambda .jar that I build from a Jenkins box in an AWS account ("Account_Bld"). Once built, I copy the .jar over to an S3 bucket in a different AWS account ("Account_Dst"), and I attempt to update the Lambda in Account_Dst based on the newly copied .jar in S3.

I'm using this command as part of my deploy script, which is a slight modification of another version that works when everything is located in the same account:

aws lambda update-function-code --function-name arn:aws:lambda:us-east-1:{Account_Dst_Id}:function:{lambda_function_name} --zip-file fileb://{jar_file_relative_path} --region us-east-1

Not surprisingly, I get this error:

An error occurred (AccessDeniedException) when calling the UpdateFunctionCode operation: User: arn:aws:sts::{Account_Bld_Id}:assumed-role/{jenkins_ec2_role}/{jenkins_ec2_instance_id} is not authorized to perform: lambda:UpdateFunctionCode on resource: arn:aws:lambda:us-east-1:{Account_Dst_Id}:function:{lambda_function_name}

I have given jenkins_ec2_role rights to update the Lambda in the other account, but it makes sense that I would need to reciprocate those rights somewhere in Account_Dst -- assuming there is a simple solution to this problem.

Now, possible resolutions. I could assume a role in Account_Dst that has the correct rights and update the Lambda, but that's more setup hassle than it is worth to me right now. I've seen some Google suggestions that I could use CodePipeline, but obviously I'm using Jenkins, so that doesn't seem like a good solution, either.

So, the question is, is there an easy solution here that I am missing?

Upvotes: 0

Views: 2101

Answers (2)

adrian-mezei
adrian-mezei

Reputation: 94

This is now possible. A Lambda resource based policy can be configured to allow a principal from another account to perform actions e.g. lambda:UpdateFunctionCode or lambda:Invoke.

In case of UpdateFunctionCode, the documentation states:

FunctionName

The name of the Lambda function.

Name formats

  • Function name – my-function.
  • Function ARN – arn:aws:lambda:us-west-2:123456789012:function:my-function.
  • Partial ARN – 123456789012:function:my-function.

...

Source: https://docs.aws.amazon.com/lambda/latest/dg/API_UpdateFunctionCode.html

The Lambda Function permission in account 222222222222 must be configured to allow the principal from account 111111111111 to update the function code:

aws lambda add-permission --function-name my-function --statement-id xaccount --action lambda:UpdateFunctionCode --principal 111111111111 --output out.txt

Source: https://docs.aws.amazon.com/lambda/latest/dg/access-control-resource-based.html#permissions-resource-xaccountinvoke

Then the function code in account 222222222222 can be updated from account 111111111111:

aws lambda update-function-code --function-name  arn:aws:lambda:us-west-2:222222222222:function:my-function --zip-file fileb://soure.zip

Upvotes: 2

John Rotenstein
John Rotenstein

Reputation: 269276

Granting permissions in Account_Bld to access Account_Dst is not sufficient to gain access to another account. This is good, because you wouldn't want people granting themselves access to other people's accounts.

The destination account needs to accept the incoming request. The method varies by service. For example, Amazon S3 can create a Bucket Policy to permit access from other accounts, as can Amazon SQS.

However, there is no such concept in Lambda to configure incoming requests from other accounts. There is simply nowhere that can be configured to allow update-function-code from another account.

Therefore, you will need to do as you suggested:

  • Create an IAM User or IAM Role in Account_Dst
  • Use the credentials from the Account_Dst IAM User (simplest) or use the existing Account_Bld credentials to assume the Role in Account_Dst (a few more lines of code)
  • Call update-function-code using those credentials

Upvotes: 0

Related Questions