Backend Architecture¶
Overview¶
The backend is a FastAPI application providing email services and API endpoints.
Technology Stack¶
- Framework: FastAPI
- Language: Python 3.11
- ASGI Server: Uvicorn
- Validation: Pydantic
- Email: SMTP (Gmail)
Project Structure¶
API Endpoints¶
Health Check¶
Contact Form¶
POST /api/contact
Request: {
"name": "string",
"email": "string",
"message": "string",
"company": "string" (optional)
}
Response: {
"success": true,
"message": "Thank you for your message!"
}
Email Service¶
Features¶
- Dual Emails: Notification + Confirmation
- HTML Templates: Professional branded emails
- Error Handling: Graceful fallbacks
- Logging: Comprehensive error logging
Email Flow¶
sequenceDiagram
participant User
participant Frontend
participant Backend
participant Gmail
participant Recipient
User->>Frontend: Submit contact form
Frontend->>Backend: POST /api/contact
Backend->>Gmail: Send notification email
Gmail->>Recipient: Deliver to sven.relijveld@onedna.nl
Backend->>Gmail: Send confirmation email
Gmail->>User: Deliver confirmation
Backend->>Frontend: Success response
Frontend->>User: Show success message
SMTP Configuration¶
SMTP_SERVER = "smtp.gmail.com"
SMTP_PORT = 587
EMAIL_ADDRESS = os.getenv("EMAIL_ADDRESS")
EMAIL_PASSWORD = os.getenv("EMAIL_PASSWORD") # App Password
Security¶
Secrets Management¶
- Azure Key Vault: Production secrets
- Environment Variables: Development
- No Hardcoding: All secrets externalized
CORS Configuration¶
app.add_middleware(
CORSMiddleware,
allow_origins=["*"], # Configured per environment
allow_credentials=False,
allow_methods=["GET", "POST", "PUT", "DELETE", "OPTIONS"],
allow_headers=["*"],
)
Docker Build¶
FROM python:3.11-slim
WORKDIR /app
COPY api/requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY api/ .
CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]
Performance¶
- Async/Await: Non-blocking I/O
- Connection Pooling: Efficient SMTP connections
- Caching: Response caching where applicable
- Monitoring: Application Insights integration
Error Handling¶
try:
# Email sending logic
return {"success": True}
except SMTPAuthenticationError:
logger.error("Authentication failed")
return {"success": False}
except Exception as e:
logger.error(f"Unexpected error: {e}")
raise HTTPException(status_code=500)