crossplane-contrib / crossplane-contrib/provider-sql
feat: Add AWS IAM database authentication support for MySQL and PostgreSQL
- Dominant language
- Go
- Stars
- 154
- Forks
- 119
- Avg merge
- 6d 17h
- Merged PRs (30d)
- 8
Description
### What problem are you facing?
When running provider-sql on EKS to manage Aurora MySQL or Aurora PostgreSQL databases, the only authentication option is static username/password credentials stored in a Kubernetes Secret. AWS Aurora supports [IAM database authentication](https://docs.aws.amazon.com/AmazonRDS/latest/AuroraUserGuide/UsingWithRDS.IAMDBAuth.html), which allows generating short-lived authentication tokens (15 min TTL) using AWS IAM credentials instead of static passwords.
Combined with [EKS Pod Identity](https://docs.aws.amazon.com/eks/latest/userguide/pod-identities.html) or [IRSA](https://docs.aws.amazon.com/eks/latest/userguide/iam-roles-for-service-accounts.html), this eliminates the need for static database passwords entirely, the provider pod assumes an IAM role and generates tokens at connection time.
This is similar to the Azure AD/Entra ID authentication work in #165 / #166 (MSSQL) and #196 (PostgreSQL), but for AWS.
### How could Crossplane help solve your problem?
Add a new `AWSIAMAuth` credential source to the MySQL and PostgreSQL ProviderConfig, alongside the existing `MySQLConnectionSecret` / `PostgreSQLConnectionSecret` sources.
**Proposed approach:**
1. A new `AWSIAMAuth` value for the `credentials.source` enum in ProviderConfig
2. The connection secret still provides `endpoint`, `port`, and `username` but no `password` (the token replaces it at connection time)
3. An optional `region` field on the credentials spec, with fallback to the secret's `region` key, then to the AWS SDK default credential chain
4. TLS/SSL automatically enforced (required by IAM auth)
5. Uses `aws-sdk-go-v2/feature/rds/auth.BuildAuthToken()` for token generation
6. AWS credentials are discovered automatically from the environment (Pod Identity, IRSA, instance metadata)
**Example ProviderConfig:**
```yaml
apiVersion: postgresql.sql.crossplane.io/v1alpha1
kind: ProviderConfig
metadata:
name: aurora-iam
spec:
credentials:
source: AWSIAMAuth
connectionSecretRef:
namespace: crossplane-system
name: aurora-conn # contains endpoint, port, username (no password)
region: us-east-1 # optional, defaults to AWS SDK chain
sslMode: require
```
**Scope:** This proposal covers **provider authentication only**; how provider-sql connects to the database. Creating IAM-authenticated database users (e.g., `GRANT rds_iam TO myuser` for PostgreSQL, `IDENTIFIED WITH AWSAuthenticationPlugin` for MySQL) would be a separate follow-up, as suggested in the discussion on #196.
**Why this fits well architecturally:**
- The provider already creates a fresh connection on every reconcile cycle (stateless), so token expiration (15 min) is a non-issue, a new token is generated each time
- TLS support already exists for both MySQL and PostgreSQL
- The `ProviderCredentials.Source` enum is the natural extension point
- The actual change to each reconciler's `Connect()` is minimal: generate token → inject as password → proceed as normal
I'm happy to implement this and submit a PR. Would appreciate feedback on the approach before I start.
Contributor guide
No contributing guide indexed for this repository
Research direction
Start at the ProviderConfig credentials source and ProviderCredentials.Source enum, then trace the MySQL and PostgreSQL reconciler Connect() entry points and existing TLS handling. Review aws-sdk-go-v2/feature/rds/auth.BuildAuthToken() and the related Azure authentication issues; done means AWSIAMAuth works for both databases with region and credential-chain handling, token-based passwords, and enforced TLS.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- aws, go, mysql, postgresql
- Domain
- cloud, databases
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 48/100