Skip to content

Commit

Permalink
Check in role manager archive (#695)
Browse files Browse the repository at this point in the history
- Remove role manager dependencies from source control
- Add role manager archive to source control
- Add make command for building role manager archive
- Add documentation on how to update role manager

## Context

The “check in role manager dependencies” change in [PR
493](#493) does not
function as desired. The role manager lambda still shows a diff on the
source_code_hash on a clean checkout of the repo. This change removes
the archive_file data source altogether, and checks in the zip archive
directly into the codebase. Benefits include:
- We no longer need to check in the python dependencies into source
control, which is a ton of files including binary files
- There’s nothing nondeterministic for project teams, the archive file
is exactly the zip package that gets deployed to lambda

The downside is that updating the role manager is more manual. So this
change also adds a `make infra-module-database-role-manager-archive` to
rebuild the role manager package and adds instructions for doing that.
  • Loading branch information
lorenyu authored Jul 18, 2024
1 parent 2514d1c commit dd4f11f
Show file tree
Hide file tree
Showing 112 changed files with 31 additions and 37,506 deletions.
5 changes: 5 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ __check_defined = \
infra-lint-scripts \
infra-lint-terraform \
infra-lint-workflows \
infra-module-database-role-manager \
infra-set-up-account \
infra-test-service \
infra-update-app-build-repository \
Expand Down Expand Up @@ -108,6 +109,10 @@ infra-update-app-database: ## Create or update $APP_NAME's database module for $
terraform -chdir="infra/$(APP_NAME)/database" init -input=false -reconfigure -backend-config="$(ENVIRONMENT).s3.tfbackend"
terraform -chdir="infra/$(APP_NAME)/database" apply -var="environment_name=$(ENVIRONMENT)"

infra-module-database-role-manager-archive: ## Build/rebuild role manager code package for Lambda deploys
pip3 install -r infra/modules/database/role_manager/requirements.txt -t infra/modules/database/role_manager/vendor --upgrade
zip -r infra/modules/database/role_manager.zip infra/modules/database/role_manager

infra-update-app-database-roles: ## Create or update database roles and schemas for $APP_NAME's database in $ENVIRONMENT
@:$(call check_defined, APP_NAME, the name of subdirectory of /infra that holds the application's infrastructure code)
@:$(call check_defined, ENVIRONMENT, the name of the application environment e.g. "prod" or "staging")
Expand Down
14 changes: 14 additions & 0 deletions docs/infra/database-access-control.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,17 @@ The database authenticates connections with [IAM database authentication](https:

* The system leverages IAM to centrally manage access to the database
* There are no long-lived user database credentials that need to be stored as database authentication tokens are generated by IAM and have a lifetime of 15 minutes

## Update the role manager

If you need to update the role manager code or dependencies, first build the role manager Lambda zip file by running:

```bash
make infra-module-database-role-manager-archive
```

Then deploy the changes to the role manager by running

```bash
make infra-update-app-database APP_NAME=<APP_NAME> ENVIRONMENT=<ENVIRONMENT>
```
10 changes: 7 additions & 3 deletions docs/infra/set-up-database.md
Original file line number Diff line number Diff line change
Expand Up @@ -91,12 +91,16 @@ The Lambda function's response should describe the resulting PostgreSQL roles an
}
```

### Important note on Postgres table permissions
### Updating the role manager

Before creating migrations that create tables, first create a migration that includes the following SQL command (or equivalent if your migrations are written in a general-purpose programming language):
To make changes to the role manager such as updating dependencies or adding functionality, see [database access control](./database-access-control.md#update-the-role-manager)

### Note on Postgres table permissions

The role manager executes the following statement as part of database setup:

```sql
ALTER DEFAULT PRIVILEGES GRANT ALL ON TABLES TO app
ALTER DEFAULT PRIVILEGES IN SCHEMA app GRANT ALL ON TABLES TO app
```

This will cause all future tables created by the `migrator` user to automatically be accessible by the `app` user. See the [Postgres docs on ALTER DEFAULT PRIVILEGES](https://www.postgresql.org/docs/current/sql-alterdefaultprivileges.html) for more info. As an example see the example app's migrations file [migrations.sql](https://github.com/navapbc/template-infra/blob/main/app/migrations.sql).
Expand Down
3 changes: 0 additions & 3 deletions infra/.gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,3 @@ override.tf.json
# example: *tfplan*
*.plan
*.tfstate

# Ignore archives used for deploying lambdas
*.zip
1 change: 1 addition & 0 deletions infra/modules/database/.gitignore
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
__pycache__
vendor/
1 change: 0 additions & 1 deletion infra/modules/database/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ locals {
master_username = "postgres"
primary_instance_name = "${var.name}-primary"
role_manager_name = "${var.name}-role-manager"
role_manager_package = "${path.root}/role_manager.zip"
# The ARN that represents the users accessing the database are of the format: "arn:aws:rds-db:<region>:<account-id>:dbuser:<resource-id>/<database-user-name>""
# See https://aws.amazon.com/blogs/database/using-iam-authentication-to-connect-with-pgadmin-amazon-aurora-postgresql-or-amazon-rds-for-postgresql/
db_user_arn_prefix = "arn:aws:rds-db:${data.aws_region.current.name}:${data.aws_caller_identity.current.account_id}:dbuser:${aws_rds_cluster.db.cluster_resource_id}"
Expand Down
13 changes: 4 additions & 9 deletions infra/modules/database/role-manager.tf
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,15 @@
# as well as viewing existing roles

locals {
db_password_param_name = "/aws/reference/secretsmanager/${data.aws_secretsmanager_secret.db_password.name}"
db_password_param_name = "/aws/reference/secretsmanager/${data.aws_secretsmanager_secret.db_password.name}"
role_manager_archive_path = "${path.module}/role_manager.zip"
}

resource "aws_lambda_function" "role_manager" {
function_name = local.role_manager_name

filename = local.role_manager_package
source_code_hash = data.archive_file.role_manager.output_base64sha256
filename = local.role_manager_archive_path
source_code_hash = filebase64sha256(local.role_manager_archive_path)
runtime = "python3.9"
handler = "role_manager.lambda_handler"
role = aws_iam_role.role_manager.arn
Expand Down Expand Up @@ -53,12 +54,6 @@ resource "aws_lambda_function" "role_manager" {
# checkov:skip=CKV_AWS_116:Dead letter queue (DLQ) configuration is only relevant for asynchronous invocations
}

data "archive_file" "role_manager" {
type = "zip"
source_dir = "${path.module}/role_manager"
output_path = local.role_manager_package
}

data "aws_kms_key" "default_ssm_key" {
key_id = "alias/aws/ssm"
}
Expand Down
Binary file added infra/modules/database/role_manager.zip
Binary file not shown.

This file was deleted.

This file was deleted.

Loading

0 comments on commit dd4f11f

Please sign in to comment.