# AWS Database Migration Guide

This guide explains how to migrate the authentication service from a local Docker PostgreSQL database to an AWS PostgreSQL database using AWS SSM Parameter Store for secure credential management.

## Overview

**Security Model**: Database credentials are fetched from AWS SSM Parameter Store at runtime. NO database credentials are stored in `.env` files or code.

## Prerequisites

1. AWS Account with access to Systems Manager Parameter Store
2. IAM user/role with permissions to read SSM parameters:
   - `ssm:GetParameter` for `/test/livingai/db/app`
   - `ssm:GetParameter` for `/test/livingai/db/app/readonly`
3. AWS PostgreSQL database instance (RDS or managed PostgreSQL)
4. Database users created:
   - `read_write_user` (for authentication service)
   - `read_only_user` (optional, for read-only operations)

## AWS Configuration

### 1. Set Up AWS SSM Parameters

Store database credentials in AWS SSM Parameter Store as **SecureString** parameters:

#### Read-Write User (Authentication Service)
**Parameter Path**: `/test/livingai/db/app`

**Parameter Value** (JSON format):
```json
{
  "user": "read_write_user",
  "password": "your_secure_password_here",
  "host": "db.livingai.app",
  "port": "5432",
  "database": "livingai_test_db"
}
```

#### Read-Only User (Optional)
**Parameter Path**: `/test/livingai/db/app/readonly`

**Parameter Value** (JSON format):
```json
{
  "user": "read_only_user",
  "password": "your_secure_password_here",
  "host": "db.livingai.app",
  "port": "5432",
  "database": "livingai_test_db"
}
```

### 2. Create IAM Policy

Create an IAM policy that allows reading SSM parameters:

```json
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "ssm:GetParameter",
        "ssm:GetParameters"
      ],
      "Resource": [
        "arn:aws:ssm:ap-south-1:*:parameter/test/livingai/db/app",
        "arn:aws:ssm:ap-south-1:*:parameter/test/livingai/db/app/readonly"
      ]
    }
  ]
}
```

Attach this policy to your IAM user or role.

## Environment Variables

### Required Variables

Create or update your `.env` file with **ONLY** these AWS credentials:

```env
# AWS Configuration (for SSM Parameter Store access)
AWS_REGION=ap-south-1
AWS_ACCESS_KEY_ID=your_aws_access_key_here
AWS_SECRET_ACCESS_KEY=your_aws_secret_key_here

# Enable AWS SSM for database credentials
USE_AWS_SSM=true

# JWT Configuration (REQUIRED)
JWT_ACCESS_SECRET=your_jwt_access_secret_here
JWT_REFRESH_SECRET=your_jwt_refresh_secret_here
```

### Optional Variables

```env
# Control which database user to use
# false = read_write_user (default for auth service)
# true = read_only_user
DB_USE_READONLY=false

# Database connection settings (auto-detected if not set)
DB_HOST=db.livingai.app
DB_PORT=5432
DB_NAME=livingai_test_db
```

### ⚠️ DO NOT Include

**NEVER** include these in your `.env` file:
- `DB_USER`
- `DB_PASSWORD`
- `DATABASE_URL` (with credentials)
- Any database credentials

Database credentials are fetched from AWS SSM at runtime.

## Database Configuration

### AWS PostgreSQL Settings

- **Host**: `db.livingai.app`
- **Port**: `5432`
- **Database**: `livingai_test_db`
- **SSL**: Required (self-signed certificates supported)

### SSL Configuration

The connection automatically handles SSL with self-signed certificates:
- `rejectUnauthorized: false` is set for self-signed certificate support
- Connection string includes `?sslmode=require`

## Migration Steps

### Step 1: Update Environment Variables

1. Remove any existing database credentials from `.env`:
   ```bash
   # Remove these if present:
   # DB_HOST=...
   # DB_USER=...
   # DB_PASSWORD=...
   # DATABASE_URL=...
   ```

2. Add AWS credentials to `.env`:
   ```env
   AWS_REGION=ap-south-1
   AWS_ACCESS_KEY_ID=your_aws_access_key
   AWS_SECRET_ACCESS_KEY=your_aws_secret_key
   USE_AWS_SSM=true
   ```

### Step 2: Verify SSM Parameters

Ensure your SSM parameters are set correctly:

```bash
# Using AWS CLI (if configured)
aws ssm get-parameter --name "/test/livingai/db/app" --with-decryption --region ap-south-1
```

### Step 3: Test Database Connection

Start your application:

```bash
npm start
```

You should see:
```
✅ Successfully fetched DB credentials from SSM: /test/livingai/db/app (read-write user)
✅ Using database credentials from AWS SSM Parameter Store
   Host: db.livingai.app, Database: livingai_test_db, User: read_write_user
✅ Database connection established successfully
```

### Step 4: Run Database Migrations

If you have schema changes, run migrations:

```bash
node run-migration.js
```

## Connection Pool Configuration

The connection pool is configured with:
- **Max connections**: 20
- **Idle timeout**: 30 seconds
- **Connection timeout**: 2 seconds

These can be adjusted in `src/db.js` if needed.

## Troubleshooting

### Error: "Cannot access AWS SSM Parameter Store"

**Causes**:
- Missing AWS credentials in `.env`
- IAM user doesn't have SSM permissions
- Wrong AWS region

**Solutions**:
1. Verify `AWS_ACCESS_KEY_ID` and `AWS_SECRET_ACCESS_KEY` are set
2. Check IAM permissions for SSM access
3. Verify `AWS_REGION` matches your SSM parameter region

### Error: "Database connection failed: SSL required"

**Cause**: Database requires SSL but connection isn't using it.

**Solution**: SSL is automatically configured. Verify your database security group allows SSL connections.

### Error: "Parameter not found"

**Cause**: SSM parameter path doesn't exist or has wrong name.

**Solution**:
1. Verify parameter path: `/test/livingai/db/app`
2. Check parameter is in correct region
3. Ensure parameter type is "SecureString"

### Error: "Invalid credentials format"

**Cause**: SSM parameter value is not valid JSON.

**Solution**: Ensure parameter value is JSON format:
```json
{
  "user": "username",
  "password": "password",
  "host": "host",
  "port": "5432",
  "database": "dbname"
}
```

## Local Development

For local development without AWS SSM, you can use `DATABASE_URL`:

```env
# Disable AWS SSM for local development
USE_AWS_SSM=false

# Use local database
DATABASE_URL=postgresql://postgres:password@localhost:5432/farmmarket
```

**Note**: This should only be used for local development. Production must use AWS SSM.

## Security Best Practices

1. **Never commit `.env` files** - Add `.env` to `.gitignore`
2. **Rotate credentials regularly** - Update SSM parameters periodically
3. **Use least privilege** - IAM user should only have SSM read permissions
4. **Monitor SSM access** - Enable CloudTrail to audit SSM parameter access
5. **Use different credentials per environment** - Separate SSM parameters for test/prod

## Code Changes Summary

### Files Modified

1. **`src/utils/awsSsm.js`**
   - Updated to use correct SSM parameter paths
   - Added support for read-only/read-write user selection
   - Improved error handling and validation

2. **`src/db.js`**
   - Added SSL configuration for self-signed certificates
   - Updated to use `buildDatabaseConfig` instead of connection string
   - Improved error handling and logging

3. **`src/config.js`**
   - Removed `DATABASE_URL` from required env vars when using SSM
   - Added AWS credentials validation

### No Changes Required

- All business logic remains unchanged
- All API endpoints work as before
- All database queries work as before
- Only connection configuration changed

## Verification Checklist

- [ ] AWS SSM parameters created with correct paths
- [ ] IAM user/role has SSM read permissions
- [ ] `.env` file has AWS credentials (no DB credentials)
- [ ] `USE_AWS_SSM=true` in `.env`
- [ ] Application starts without errors
- [ ] Database connection established successfully
- [ ] API endpoints respond correctly
- [ ] Database queries execute successfully

## Support

For issues or questions:
1. Check application logs for detailed error messages
2. Verify SSM parameters using AWS Console or CLI
3. Test AWS credentials with AWS CLI
4. Review IAM permissions for SSM access

