Skip to content

Commit

Permalink
feat: add a new AWS plugin
Browse files Browse the repository at this point in the history
This plugin is used to assume an STS role and provide AWS credentials
for other tasks. It stores AWS credentials in the CI state so they can
be picked up later.

This is required for us to be able to assume different roles across
different accounts with Hako, we'll be deploying to separate test and
prod AWS accounts in future.

Later it makes sense to rework the `serverless` and
`upload-assets-to-s3` plugins to use this. I'd rather not actually do
this work until we've tested this with Hako.

Release-As: 0.1.0
Co-Authored-By: Alex Muller <[email protected]>
  • Loading branch information
rowanmanning and alexmuller committed Jan 31, 2025
1 parent f4765b5 commit 2b3b7cb
Show file tree
Hide file tree
Showing 8 changed files with 1,977 additions and 125 deletions.
1,964 changes: 1,839 additions & 125 deletions package-lock.json

Large diffs are not rendered by default.

4 changes: 4 additions & 0 deletions plugins/aws/.toolkitrc.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
tasks:
AwsAssumeRole: './lib/tasks/assume-role'

version: 2
38 changes: 38 additions & 0 deletions plugins/aws/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
{
"name": "@dotcom-tool-kit/aws",
"version": "0.1.0",
"main": "lib",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [],
"author": "FT.com Platforms Team <[email protected]>",
"license": "ISC",
"description": "",
"repository": {
"type": "git",
"url": "https://github.com/financial-times/dotcom-tool-kit.git",
"directory": "plugins/aws"
},
"bugs": "https://github.com/financial-times/dotcom-tool-kit/issues",
"homepage": "https://github.com/financial-times/dotcom-tool-kit/tree/main/plugins/aws",
"files": [
"/lib",
".toolkitrc.yml"
],
"engines": {
"node": "18.x || 20.x || 22.x"
},
"peerDependencies": {
"dotcom-tool-kit": "4.x"
},
"dependencies": {
"@aws-sdk/client-sts": "^3.738.0",
"@dotcom-tool-kit/base": "^1.1.7",
"@dotcom-tool-kit/error": "^4.1.0",
"@dotcom-tool-kit/state": "^4.2.0"
},
"devDependencies": {
"@dotcom-tool-kit/schemas": "^1.7.0"
}
}
31 changes: 31 additions & 0 deletions plugins/aws/readme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# dotcom-tool-kit/aws

## Installation & Usage

With Tool Kit [already set up](https://github.com/financial-times/dotcom-tool-kit#installing-and-using-tool-kit), install this plugin as a dev dependency:

```sh
npm install --save-dev @dotcom-tool-kit/aws
```

And add it to your repo's `.toolkitrc.yml`:

```yml
plugins:
- '@dotcom-tool-kit/aws'
```
<!-- begin autogenerated docs -->
## Tasks
### `AwsAssumeRole`

Assume an AWS IAM role for use in future tasks
#### Task options

| Property | Description | Type |
| :----------------- | :------------------------------- | :----------------------------------------------- |
| **`roleArn`** (\*) | the ARN of an IAM role to assume | `string` (_regex: `/^arn:aws:iam::\d+:role\//`_) |

_(\*) Required._
<!-- end autogenerated docs -->
39 changes: 39 additions & 0 deletions plugins/aws/src/tasks/assume-role.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
import { AssumeRoleWithWebIdentityCommand, STSClient } from '@aws-sdk/client-sts'
import { type AwsAssumeRoleSchema } from '@dotcom-tool-kit/schemas/lib/tasks/aws-assume-role'
import { randomUUID } from 'node:crypto'
import { Task } from '@dotcom-tool-kit/base'
import { ToolKitError } from '@dotcom-tool-kit/error'
import { writeState } from '@dotcom-tool-kit/state'

export default class AwsAssumeRole extends Task<{ task: typeof AwsAssumeRoleSchema }> {
async run() {
try {
this.logger.info(`Assuming AWS role "${this.options.roleArn}"`)

const RoleArn = this.options.roleArn
const RoleSessionName = `toolkit-${randomUUID()}`
const WebIdentityToken = process.env.CIRCLE_OIDC_TOKEN_V2

const client = new STSClient({ region: 'eu-west-1' })
const { Credentials } = await client.send(
new AssumeRoleWithWebIdentityCommand({ RoleArn, RoleSessionName, WebIdentityToken })
)

const awsCredentials = {
accessKeyId: Credentials?.AccessKeyId,
secretAccessKey: Credentials?.SecretAccessKey,
sessionToken: Credentials?.SessionToken
}
writeState('ci', { awsCredentials })
this.logger.info(`Saved AWS credentials to "ci" state with session name "${RoleSessionName}"`)
} catch (err) {
if (err instanceof Error) {
const error = new ToolKitError('failed to assume AWS role')
error.details = err.message
throw error
} else {
throw err
}
}
}
}
22 changes: 22 additions & 0 deletions plugins/aws/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
{
"extends": "../../tsconfig.settings.json",
"compilerOptions": {
"outDir": "lib",
"rootDir": "src"
},
"references": [
{
"path": "../../lib/error"
},
{
"path": "../../lib/base"
},
{
"path": "../../lib/schemas"
},
{
"path": "../../lib/state"
}
],
"include": ["src/**/*"]
}
1 change: 1 addition & 0 deletions release-please-config.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
"package-name": "orb",
"release-type": "simple"
},
"plugins/aws": {},
"plugins/babel": {},
"plugins/backend-heroku-app": {},
"plugins/backend-serverless-app": {},
Expand Down
3 changes: 3 additions & 0 deletions tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,9 @@
},
{
"path": "plugins/docker"
},
{
"path": "plugins/aws"
}
]
}

0 comments on commit 2b3b7cb

Please sign in to comment.