Add simplified PostgreSQL infrastructure role for database services

- Provides PostgreSQL server as shared database infrastructure
- Follows KISS principle with only essential configuration (11 variables vs 45 originally)
- Implements maximum security with Unix socket-only superuser access
- Uses scram-sha-256 authentication for application users
- Includes SystemD security hardening
- Applications manage their own databases/users via this infrastructure
- Production-ready with data checksums and localhost-only access
This commit is contained in:
2025-11-18 21:33:50 +01:00
parent 7c3b02e5ad
commit 762d00eebf
9 changed files with 532 additions and 0 deletions

252
roles/postgresql/README.md Normal file
View File

@@ -0,0 +1,252 @@
# PostgreSQL Infrastructure Role
This role provides PostgreSQL as shared database infrastructure for rick-infra applications. It follows the self-contained service architecture where this role provides the database server, and applications manage their own databases and users.
## Architecture
PostgreSQL serves as database infrastructure (similar to how Caddy provides web infrastructure):
- **PostgreSQL Role**: Installs and configures PostgreSQL server
- **Application Roles**: Create their own databases/users via dependency
## Features
- ✅ Native Arch Linux installation via pacman
- ✅ Secure configuration with scram-sha-256 authentication
- ✅ SystemD security hardening
- ✅ Data integrity with checksums enabled by default
- ✅ Performance-tuned defaults
- ✅ Comprehensive logging configuration
- ✅ UTF-8 encoding with C.UTF-8 locale
## Usage
### In Application Roles
Add PostgreSQL as a dependency in your application's `meta/main.yml`:
```yaml
dependencies:
- role: postgresql
tags: ['postgresql', 'infrastructure']
```
Then create your application's database and user in your tasks:
```yaml
- name: Create application database user
postgresql_user:
name: "{{ myapp_db_user }}"
password: "{{ myapp_db_password }}"
encrypted: yes
become: yes
become_user: postgres
- name: Create application database
postgresql_db:
name: "{{ myapp_db_name }}"
owner: "{{ myapp_db_user }}"
encoding: UTF8
template: template0
become: yes
become_user: postgres
```
### In site.yml
```yaml
- name: Deploy Infrastructure
hosts: arch-vps
become: yes
roles:
- role: postgresql
tags: ['postgresql', 'infrastructure', 'database']
- role: myapp # Will use PostgreSQL infrastructure
tags: ['myapp']
```
## Configuration Variables
### Basic Configuration
| Variable | Default | Description |
|----------|---------|-------------|
| `postgresql_service_enabled` | `true` | Enable PostgreSQL service |
| `postgresql_service_state` | `"started"` | Service state |
| `postgresql_port` | `5432` | PostgreSQL port |
| `postgresql_listen_addresses` | `"localhost"` | Listen addresses |
### Security Configuration
| Variable | Default | Description |
|----------|---------|-------------|
| `postgresql_auth_method` | `"scram-sha-256"` | Authentication method |
| `postgresql_systemd_security` | `true` | Enable systemd security hardening |
| `postgresql_data_checksums` | `true` | Enable data checksums |
| `postgresql_ssl` | `false` | Enable SSL/TLS |
### Performance Configuration
| Variable | Default | Description |
|----------|---------|-------------|
| `postgresql_max_connections` | `100` | Maximum connections |
| `postgresql_shared_buffers` | `"128MB"` | Shared buffer size |
| `postgresql_effective_cache_size` | `"1GB"` | Effective cache size |
See `defaults/main.yml` for all available configuration options.
## Security Features
### SystemD Hardening
The role implements comprehensive systemd security restrictions:
- `NoNewPrivileges=true`
- `PrivateTmp=true`
- `ProtectHome=true`
- `ProtectSystem=strict`
- Memory execution protection
- System call filtering
### Authentication
- Secure `scram-sha-256` password authentication
- `peer` authentication for postgres superuser
- Local connections only by default
- Encrypted password storage
### File System Security
- Proper ownership and permissions
- Protected configuration files (mode 0600)
- Separate log directory with appropriate access
## Directory Structure
```
/var/lib/postgres/data/ # PostgreSQL data directory
/var/lib/postgres/ # PostgreSQL home directory
/var/log/postgresql/ # PostgreSQL logs
/etc/systemd/system/postgresql.service.d/ # SystemD overrides
```
## Database Administration
### Connect as postgres superuser:
```bash
sudo -u postgres psql
```
### Create application database and user:
```sql
CREATE ROLE myapp WITH LOGIN PASSWORD 'secure_password';
CREATE DATABASE myapp WITH OWNER myapp TEMPLATE template0 ENCODING 'UTF8';
```
### List databases:
```sql
\l
```
### List users:
```sql
\du
```
## Performance Tuning
The role provides conservative performance defaults suitable for most applications. For production workloads, consider adjusting:
- `postgresql_shared_buffers`: 25% of system RAM
- `postgresql_effective_cache_size`: 75% of system RAM
- `postgresql_max_connections`: Based on application needs
- `postgresql_maintenance_work_mem`: For large datasets
## Monitoring
### Service Status
```bash
systemctl status postgresql
```
### Logs
```bash
journalctl -u postgresql
# or
sudo -u postgres tail -f /var/log/postgresql/postgresql-*.log
```
### Connection Test
```bash
sudo -u postgres psql -c "SELECT version();"
```
## Troubleshooting
### Common Issues
1. **Permission Denied**: Ensure postgres user owns data directory
2. **Connection Refused**: Check service status and listen_addresses
3. **Authentication Failed**: Verify pg_hba.conf configuration
### Debug Mode
Enable detailed logging:
```yaml
postgresql_log_statement: "all"
postgresql_log_connections: true
postgresql_log_disconnections: true
```
## Examples
### Development Setup
```yaml
postgresql_log_statement: "all" # Log all statements
postgresql_max_connections: 50 # Lower for development
```
### Production Setup
```yaml
postgresql_shared_buffers: "256MB"
postgresql_effective_cache_size: "2GB"
postgresql_log_min_duration_statement: 1000 # Log slow queries
postgresql_log_connections: true # Audit trail
```
### High Security Setup
```yaml
postgresql_ssl: true
postgresql_log_connections: true
postgresql_log_disconnections: true
postgresql_log_statement: "ddl" # Log schema changes
```
## Dependencies
- Arch Linux PostgreSQL package
- python-psycopg2 (for Ansible modules)
## Compatibility
- **OS**: Arch Linux
- **PostgreSQL**: Latest stable version from Arch repositories
- **Ansible**: >= 2.9
## Contributing
When modifying this role:
1. Update this README for any new features
2. Test with example applications
3. Ensure security configurations remain intact
4. Follow rick-infra coding standards
## Integration Examples
See roles that use this infrastructure:
- `gitea`: Git repository management
- `nextcloud` (planned): File sharing and collaboration
---
**Rick-Infra PostgreSQL Infrastructure Role**
Provides secure, performant PostgreSQL database infrastructure for rick-infra applications.