Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Managed identity support for Azure Database for PostgreSQL #215

Merged
merged 14 commits into from
Sep 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
"VARIANT": "jammy"
}
},
"postStartCommand": "./.devcontainer/scripts/onCreateCommand.sh",
"remoteUser": "vscode",
"containerEnv": {
"M2": "/home/vscode" // required because the java feature is not setting this correctly
Expand Down
3 changes: 3 additions & 0 deletions .devcontainer/scripts/onCreateCommand.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
set -x

az extension add --name serviceconnector-passwordless --upgrade
9 changes: 9 additions & 0 deletions infra/scripts/setup-service-connector.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#!/usr/bin/env bash

source_id=$1
target_id=$2

random_string=$RANDOM
connection_name=postgresql_${RANDOM}

az webapp connection create postgres-flexible --connection ${connection_name} --source-id ${source_id} --target-id ${target_id} --client-type springBoot --system-identity
4 changes: 0 additions & 4 deletions infra/shared/terraform/modules/app-service/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -99,10 +99,6 @@ resource "azurerm_linux_web_app" "application" {
APPLICATIONINSIGHTS_CONNECTION_STRING = var.app_insights_connection_string
ApplicationInsightsAgent_EXTENSION_VERSION = "~3"

SPRING_DATASOURCE_URL = var.contoso_webapp_options.postgresql_database_url
SPRING_DATASOURCE_USERNAME = var.contoso_webapp_options.postgresql_database_user
SPRING_DATASOURCE_PASSWORD = var.contoso_webapp_options.postgresql_database_password

SPRING_CLOUD_AZURE_ACTIVE_DIRECTORY_CREDENTIAL_CLIENT_ID = var.contoso_webapp_options.contoso_active_directory_client_id
SPRING_CLOUD_AZURE_ACTIVE_DIRECTORY_CREDENTIAL_CLIENT_SECRET = var.contoso_webapp_options.contoso_active_directory_client_secret
SPRING_CLOUD_AZURE_ACTIVE_DIRECTORY_PROFILE_TENANT_ID = var.contoso_webapp_options.contoso_active_directory_tenant_id
Expand Down
4 changes: 0 additions & 4 deletions infra/shared/terraform/modules/app-service/variables.tf
Original file line number Diff line number Diff line change
Expand Up @@ -65,10 +65,6 @@ variable "contoso_webapp_options" {
contoso_active_directory_client_id = string
contoso_active_directory_client_secret = string

postgresql_database_url = string
postgresql_database_user = string
postgresql_database_password = string

redis_host_name = string
redis_port = number
redis_password = string
Expand Down
14 changes: 0 additions & 14 deletions infra/shared/terraform/modules/cache/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -75,28 +75,14 @@ resource "azurerm_monitor_diagnostic_setting" "redis_diagnostic" {

enabled_log {
category_group = "audit"

retention_policy {
days = 0
enabled = false
}
}

enabled_log {
category_group = "allLogs"

retention_policy {
days = 0
enabled = false
}
}

metric {
category = "AllMetrics"
enabled = true
retention_policy {
enabled = false
days = 0
}
}
}
14 changes: 0 additions & 14 deletions infra/shared/terraform/modules/key-vault/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -87,28 +87,14 @@ resource "azurerm_monitor_diagnostic_setting" "key_vault_diagnostic" {

enabled_log {
category_group = "audit"

retention_policy {
days = 0
enabled = false
}
}

enabled_log {
category_group = "allLogs"

retention_policy {
days = 0
enabled = false
}
}

metric {
category = "AllMetrics"
enabled = true
retention_policy {
enabled = false
days = 0
}
}
}
41 changes: 1 addition & 40 deletions infra/shared/terraform/modules/postresql/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -7,29 +7,6 @@ terraform {
}
}

# Quickstart: Use Terraform to create an Azure Database for MySQL - Flexible Server
# https://docs.microsoft.com/azure/mysql/flexible-server/quickstart-create-terraform?tabs=azure-cli


# Azure Private DNS provides a reliable, secure DNS service to manage and
# resolve domain names in a virtual network without the need to add a custom DNS solution
# https://docs.microsoft.com/azure/dns/private-dns-privatednszone
resource "azurerm_private_dns_zone" "postgresql_database" {
count = var.environment == "prod" ? 1 : 0
name = "privatelink.${var.location}.postgres.database.azure.com"
resource_group_name = var.resource_group
}

# After you create a private DNS zone in Azure, you'll need to link a virtual network to it.
# https://docs.microsoft.com/azure/dns/private-dns-virtual-network-links
resource "azurerm_private_dns_zone_virtual_network_link" "postgresql_database" {
count = var.environment == "prod" ? 1 : 0
name = azurerm_private_dns_zone.postgresql_database[0].name
private_dns_zone_name = azurerm_private_dns_zone.postgresql_database[0].name
virtual_network_id = var.virtual_network_id
resource_group_name = var.resource_group
}

resource "azurecaf_name" "postgresql_server" {
count = var.environment == "prod" ? 1 : 0
name = var.application_name
Expand All @@ -54,7 +31,7 @@ resource "azurerm_postgresql_flexible_server" "postgresql_database" {

public_network_access_enabled = false
delegated_subnet_id = var.subnet_network_id
private_dns_zone_id = azurerm_private_dns_zone.postgresql_database[0].id
private_dns_zone_id = var.private_dns_zone_id #azurerm_private_dns_zone.postgresql_database[0].id

geo_redundant_backup_enabled = false

Expand Down Expand Up @@ -85,8 +62,6 @@ resource "azurerm_postgresql_flexible_server" "postgresql_database" {
"environment" = var.environment
"application-name" = var.application_name
}

depends_on = [azurerm_private_dns_zone_virtual_network_link.postgresql_database]
}

# Configure Diagnostic Settings for PostgreSQL
Expand All @@ -98,29 +73,15 @@ resource "azurerm_monitor_diagnostic_setting" "postgresql_diagnostic" {

enabled_log {
category_group = "audit"

retention_policy {
days = 0
enabled = false
}
}

enabled_log {
category_group = "allLogs"

retention_policy {
days = 0
enabled = false
}
}

metric {
category = "AllMetrics"
enabled = true
retention_policy {
enabled = false
days = 0
}
}
}

Expand Down
5 changes: 5 additions & 0 deletions infra/shared/terraform/modules/postresql/outputs.tf
Original file line number Diff line number Diff line change
Expand Up @@ -27,3 +27,8 @@ output "dev_database_fqdn" {
value = length(azurerm_postgresql_flexible_server.dev_postresql_database) > 0 ? azurerm_postgresql_flexible_server.dev_postresql_database[0].fqdn : ""
description = "The FQDN of the database"
}

output "dev_database_name" {
value = length(azurerm_postgresql_flexible_server.dev_postresql_database) > 0 ? azurerm_postgresql_flexible_server.dev_postresql_database[0].name : ""
description = "The name of the database server"
}
5 changes: 5 additions & 0 deletions infra/shared/terraform/modules/postresql/variables.tf
Original file line number Diff line number Diff line change
Expand Up @@ -65,4 +65,9 @@ variable "log_analytics_workspace_id" {
variable "sku_name" {
type = string
default = "B_Standard_B1ms"
}

variable "private_dns_zone_id" {
type = string
description = "The id of the private dns zone"
}
27 changes: 18 additions & 9 deletions infra/terraform/application.tf
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,6 @@ module "application" {
contoso_active_directory_tenant_id = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_application_tenant_id[0].id})"
contoso_active_directory_client_id = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_application_client_id[0].id})"
contoso_active_directory_client_secret = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_application_client_secret[0].id})"
postgresql_database_url = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_database_url[0].id})"
postgresql_database_user = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_database_admin[0].id})"
postgresql_database_password = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_database_admin_password[0].id})"
redis_host_name = module.cache[0].cache_hostname
redis_port = module.cache[0].cache_ssl_port
redis_password = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_cache_secret[0].id})"
Expand Down Expand Up @@ -59,9 +56,6 @@ module "secondary_application" {
contoso_active_directory_tenant_id = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_application_tenant_id[0].id})"
contoso_active_directory_client_id = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_application_client_id[0].id})"
contoso_active_directory_client_secret = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_application_client_secret[0].id})"
postgresql_database_url = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.secondary_contoso_database_url[0].id})"
postgresql_database_user = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_database_admin[0].id})"
postgresql_database_password = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_database_admin_password[0].id})"
redis_host_name = module.secondary_cache[0].cache_hostname
redis_port = module.secondary_cache[0].cache_ssl_port
redis_password = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.contoso_cache_secret[0].id})"
Expand Down Expand Up @@ -96,11 +90,26 @@ module "dev_application" {
contoso_active_directory_tenant_id = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_application_tenant_id[0].id})"
contoso_active_directory_client_id = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_application_client_id[0].id})"
contoso_active_directory_client_secret = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_application_client_secret[0].id})"
postgresql_database_url = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_database_url[0].id})"
postgresql_database_user = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_database_admin[0].id})"
postgresql_database_password = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_database_admin_password[0].id})"
redis_host_name = module.dev-cache[0].cache_hostname
redis_port = module.dev-cache[0].cache_ssl_port
redis_password = "@Microsoft.KeyVault(SecretUri=${azurerm_key_vault_secret.dev_contoso_cache_secret[0].id})"
}
}

resource "null_resource" "dev_service_connector" {
count = var.environment == "dev" ? 1 : 0

triggers = {
always_run = "${timestamp()}"
}

provisioner "local-exec" {
command = "bash ../scripts/setup-service-connector.sh ${module.dev_application[0].web_app_id} ${azurerm_postgresql_flexible_server_database.dev_postresql_database_db[0].id}"
}

depends_on = [
module.dev_application,
azurerm_postgresql_flexible_server_database.dev_postresql_database_db,
azurerm_postgresql_flexible_server_active_directory_administrator.dev-contoso-ad-admin
]
}
27 changes: 24 additions & 3 deletions infra/terraform/database.tf
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ module "postresql_database" {
administrator_password = local.database_administrator_password
log_analytics_workspace_id = module.hub_app_insights[0].log_analytics_workspace_id
sku_name = local.postgresql_sku_name
private_dns_zone_id = azurerm_private_dns_zone.postgres_dns_zone[0].id
}

resource "azurerm_postgresql_flexible_server_database" "postresql_database" {
Expand All @@ -34,15 +35,14 @@ resource "azurerm_postgresql_flexible_server_database" "postresql_database" {
server_id = module.postresql_database[0].database_server_id
}


# Demo purposes only: assign current user as admin to the created DB
# Demo purposes only: assign current user as admin for the primary DB
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should you make it so that there is an 'azd env set' before they can use 'azd up' to reflect their awareness? As the user will probably NOT read the terraform?

resource "azurerm_postgresql_flexible_server_active_directory_administrator" "contoso-ad-admin" {
count = var.environment == "prod" ? 1 : 0
server_name = module.postresql_database[0].database_name
resource_group_name = azurerm_resource_group.spoke[0].name
tenant_id = data.azuread_client_config.current.tenant_id
object_id = data.azuread_client_config.current.object_id
principal_name = data.azuread_client_config.current.object_id
principal_name = data.azuread_user.current.user_principal_name
principal_type = "User"
}

Expand All @@ -64,6 +64,7 @@ module "secondary_postresql_database" {
administrator_password = local.database_administrator_password
log_analytics_workspace_id = module.hub_app_insights[0].log_analytics_workspace_id
sku_name = local.postgresql_sku_name
private_dns_zone_id = azurerm_private_dns_zone.postgres_dns_zone[0].id

depends_on = [
module.spoke_vnet[0],
Expand Down Expand Up @@ -91,6 +92,26 @@ module "dev_postresql_database" {
administrator_password = local.database_administrator_password
log_analytics_workspace_id = module.dev_app_insights[0].log_analytics_workspace_id
sku_name = local.postgresql_sku_name
private_dns_zone_id = null
}

resource "azurerm_postgresql_flexible_server_firewall_rule" "dev_postresql_database_allow_access_rule_local_ip" {
count = var.environment == "dev" ? 1 : 0
name = "allow-access-from-local-ip"
server_id = module.dev_postresql_database[0].dev_database_server_id
start_ip_address = local.myip
end_ip_address = local.myip
}

# Demo purposes only: assign current user as admin for the dev DB
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similar as before

resource "azurerm_postgresql_flexible_server_active_directory_administrator" "dev-contoso-ad-admin" {
count = var.environment == "dev" ? 1 : 0
server_name = module.dev_postresql_database[0].dev_database_name
resource_group_name = azurerm_resource_group.dev[0].name
tenant_id = data.azuread_client_config.current.tenant_id
object_id = data.azuread_client_config.current.object_id
principal_name = data.azuread_client_config.current.object_id
principal_type = "User"
}

resource "azurerm_postgresql_flexible_server_database" "dev_postresql_database_db" {
Expand Down
Loading