- Fork elmeg-demo codebase for multi-band support - Add data importer infrastructure with base class - Create band-specific importers: - phish.py: Phish.net API v5 - grateful_dead.py: Grateful Stats API - setlistfm.py: Dead & Company, Billy Strings (Setlist.fm) - Add spec-kit configuration for Gemini - Update README with supported bands and architecture
141 lines
3.2 KiB
Markdown
141 lines
3.2 KiB
Markdown
# AWS SES Email Setup
|
|
|
|
## Environment Configuration
|
|
|
|
### Production (`elmeg.xyz`)
|
|
|
|
```bash
|
|
AWS_ACCESS_KEY_ID=AKIA... # IAM user with SES send-only perms
|
|
AWS_SECRET_ACCESS_KEY=...
|
|
AWS_SES_REGION=us-east-1 # Must match region where domain is verified
|
|
EMAIL_FROM=noreply@elmeg.xyz # Must be on SES-verified domain
|
|
FRONTEND_URL=https://elmeg.xyz
|
|
NODE_ENV=production
|
|
APP_ENV=production
|
|
```
|
|
|
|
### Development (`elmeg.runfoo.run`)
|
|
|
|
```bash
|
|
FRONTEND_URL=https://elmeg.runfoo.run
|
|
APP_ENV=development
|
|
# AWS keys optional in dev - emails log to console instead
|
|
```
|
|
|
|
---
|
|
|
|
## SES Setup Checklist
|
|
|
|
### 1. Verify Domain in SES
|
|
|
|
1. AWS Console → SES → Verified Identities → Create identity
|
|
2. Select "Domain" → enter `elmeg.xyz`
|
|
3. Add DNS records AWS provides:
|
|
- **TXT record** for domain verification
|
|
- **3 CNAME records** for DKIM signing
|
|
|
|
> [!IMPORTANT]
|
|
> Add DKIM records or mail will get flagged as spam
|
|
|
|
### 2. Move Out of Sandbox
|
|
|
|
By default SES is sandboxed (can only send to verified emails).
|
|
|
|
1. SES → Account dashboard → Request production access
|
|
2. Fill out:
|
|
- Mail type: **Transactional**
|
|
- Website URL: `https://elmeg.xyz`
|
|
- Use case: "User registration verification, password reset for live music rating platform"
|
|
3. Wait for approval (~24hrs)
|
|
|
|
### 3. Create IAM User
|
|
|
|
1. IAM → Users → Create user: `elmeg-ses-sender`
|
|
2. Attach inline policy (SES send only):
|
|
|
|
```json
|
|
{
|
|
"Version": "2012-10-17",
|
|
"Statement": [
|
|
{
|
|
"Effect": "Allow",
|
|
"Action": [
|
|
"ses:SendEmail",
|
|
"ses:SendRawEmail"
|
|
],
|
|
"Resource": "*"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
3. Security credentials → Create access key
|
|
4. Save credentials securely
|
|
|
|
> [!CAUTION]
|
|
> **Never commit AWS keys.** Use environment variables only. Never use root AWS credentials - always create a scoped IAM user.
|
|
|
|
---
|
|
|
|
## DNS Records Required
|
|
|
|
Add these to `elmeg.xyz` DNS (exact values from SES console):
|
|
|
|
| Type | Name | Value |
|
|
|------|------|-------|
|
|
| TXT | `_amazonses.elmeg.xyz` | (provided by SES) |
|
|
| CNAME | `xxxx._domainkey.elmeg.xyz` | (DKIM 1) |
|
|
| CNAME | `xxxx._domainkey.elmeg.xyz` | (DKIM 2) |
|
|
| CNAME | `xxxx._domainkey.elmeg.xyz` | (DKIM 3) |
|
|
|
|
---
|
|
|
|
## Deployment
|
|
|
|
### Add to production server
|
|
|
|
```bash
|
|
ssh root@tangible-aacorn
|
|
cd /srv/containers/elmeg-demo
|
|
```
|
|
|
|
Edit `docker-compose.yml` backend environment:
|
|
|
|
```yaml
|
|
backend:
|
|
environment:
|
|
- DATABASE_URL=postgresql://elmeg:elmeg@db:5432/elmeg
|
|
- AWS_ACCESS_KEY_ID=AKIA...
|
|
- AWS_SECRET_ACCESS_KEY=...
|
|
- AWS_SES_REGION=us-east-1
|
|
- EMAIL_FROM=noreply@elmeg.xyz
|
|
- FRONTEND_URL=https://elmeg.xyz
|
|
- APP_ENV=production
|
|
```
|
|
|
|
Rebuild and restart:
|
|
|
|
```bash
|
|
docker compose build backend
|
|
docker compose restart backend
|
|
```
|
|
|
|
---
|
|
|
|
## Cost
|
|
|
|
- **$0.10 per 1,000 emails**
|
|
- No monthly minimum
|
|
- First 62,000 emails/month free if sending from EC2
|
|
|
|
---
|
|
|
|
## Troubleshooting
|
|
|
|
| Issue | Solution |
|
|
|-------|----------|
|
|
| "Email address is not verified" | Domain not verified, or still in sandbox |
|
|
| "Access Denied" | Check IAM policy has `ses:SendEmail` |
|
|
| Emails not sending | Check `docker compose logs backend` |
|
|
| Emails in spam | Verify DKIM records are set correctly |
|
|
| Wrong links in emails | Check `FRONTEND_URL` matches prod domain |
|