Add comprehensive human-readable comments to all Go files

- Comments explain what each function does and why
- Fixed unused strconv import in queue.go
- Better documentation for SMTP email service
- Explained journalctl log parsing in logs.go
- Clarified queue operations in queue.go
This commit is contained in:
Christoph Haas 2026-03-22 22:43:41 +01:00
parent 3e3620a24f
commit 68285d861a
9 changed files with 728 additions and 203 deletions

View file

@ -1,68 +1,125 @@
// Package config handles loading configuration from environment variables.
// Configuration is loaded from .env files (for development) and environment variables (for production).
package config
import (
"os"
"os" // Standard library for reading environment variables
"github.com/joho/godotenv"
"github.com/joho/godotenv" // Third-party library for loading .env files
)
// Config holds all configuration options for the application.
// Each field corresponds to either an environment variable or a default value.
type Config struct {
DBHost string
DBPort string
DBUser string
DBPassword string
DBName string
Bind string
Port string
JWTSecret string
AdminUser string
AdminPassword string
MailDataDir string
PostqueuePath string
PostsuperPath string
DovecotQuotaCmd string
JournalctlPath string
RspamdAPI string
SMTPHost string
SMTPPort string
SMTPUser string
SMTPPassword string
SMTPFrom string
BaseURL string
// Database connection settings
DBHost string // Database server hostname or IP address
DBPort string // Database server port (usually 3306 for MySQL/MariaDB)
DBUser string // Database username
DBPassword string // Database password (keep this secret!)
DBName string // Database name (e.g., "mailserver")
// Network settings for the web server
Bind string // IP address to bind to (0.0.0.0 = all interfaces, 127.0.0.1 = localhost only)
Port string // TCP port to listen on
// Security settings
JWTSecret string // Secret key for signing JWT tokens (keep this secret!)
// Admin user configuration (used when --reset-admin-password is not used)
AdminUser string // Username for the admin account
AdminPassword string // Password for the admin account (only used during startup)
// Mail server paths and settings
MailDataDir string // Directory where mail is stored (e.g., /var/vmail)
PostqueuePath string // Path to postqueue command (for mail queue operations)
PostsuperPath string // Path to postsuper command (for mail queue operations)
DovecotQuotaCmd string // Path to doveadm command (for quota operations)
// System integration
JournalctlPath string // Path to journalctl command (for reading system logs)
// Rspamd settings (spam filter)
RspamdAPI string // URL of the Rspamd web interface
// SMTP settings (for sending password reset emails)
SMTPHost string // SMTP server hostname
SMTPPort string // SMTP server port (587 for submission, 465 for SMTPS)
SMTPUser string // SMTP username
SMTPPassword string // SMTP password
SMTPFrom string // From address in outgoing emails
// Application settings
BaseURL string // Base URL of this application (used for generating links in emails)
}
// Load reads configuration from environment variables and .env files.
// It returns a Config struct with all settings.
//
// Environment variables take precedence over .env file values.
// .env file values take precedence over code defaults.
//
// The function looks for a .env file in the current directory.
func Load() *Config {
// Load .env file if it exists.
// This is for local development convenience.
// In production, use environment variables directly.
godotenv.Load("backend/.env")
// Return a new Config struct with all values.
// getEnv(key, default) returns the environment variable value,
// or the default if the environment variable is not set.
return &Config{
DBHost: getEnv("DB_HOST", "localhost"),
DBPort: getEnv("DB_PORT", "3306"),
DBUser: getEnv("DB_USER", "mailadmin"),
DBPassword: getEnv("DB_PASSWORD", ""),
DBName: getEnv("DB_NAME", "mailserver"),
Bind: getEnv("BIND", "0.0.0.0"),
Port: getEnv("PORT", "8080"),
JWTSecret: getEnv("JWT_SECRET", "change-this-secret-in-production"),
AdminUser: getEnv("ADMIN_USER", ""),
AdminPassword: getEnv("ADMIN_PASSWORD", ""),
// Database settings
// Default: localhost:3306 with mailadmin user
DBHost: getEnv("DB_HOST", "localhost"),
DBPort: getEnv("DB_PORT", "3306"),
DBUser: getEnv("DB_USER", "mailadmin"),
DBPassword: getEnv("DB_PASSWORD", ""), // No default - must be set!
DBName: getEnv("DB_NAME", "mailserver"),
// Server settings
// Default: bind to all interfaces on port 8080
Bind: getEnv("BIND", "0.0.0.0"),
Port: getEnv("PORT", "8080"),
// Security
// Default JWT secret is insecure - must be changed in production!
JWTSecret: getEnv("JWT_SECRET", "change-this-secret-in-production"),
// Admin user (optional - used during startup if set)
AdminUser: getEnv("ADMIN_USER", ""),
AdminPassword: getEnv("ADMIN_PASSWORD", ""),
// Mail server paths
MailDataDir: getEnv("MAIL_DATA_DIR", "/var/vmail"),
PostqueuePath: getEnv("POSTQUEUE_PATH", "/usr/sbin/postqueue"),
PostsuperPath: getEnv("POSTSUPER_PATH", "/usr/sbin/postsuper"),
DovecotQuotaCmd: getEnv("DOVECOT_QUOTA_CMD", "/usr/bin/doveadm"),
JournalctlPath: getEnv("JOURNALCTL_PATH", "/usr/bin/journalctl"),
RspamdAPI: getEnv("RSPAMD_API", "http://127.0.0.1:11334"),
SMTPHost: getEnv("SMTP_HOST", "localhost"),
SMTPPort: getEnv("SMTP_PORT", "587"),
SMTPUser: getEnv("SMTP_USER", ""),
SMTPPassword: getEnv("SMTP_PASSWORD", ""),
SMTPFrom: getEnv("SMTP_FROM", "noreply@localhost"),
BaseURL: getEnv("BASE_URL", "http://localhost:8080"),
// External services
RspamdAPI: getEnv("RSPAMD_API", "http://127.0.0.1:11334"),
// SMTP settings (for password reset emails)
SMTPHost: getEnv("SMTP_HOST", "localhost"),
SMTPPort: getEnv("SMTP_PORT", "587"),
SMTPUser: getEnv("SMTP_USER", ""),
SMTPPassword: getEnv("SMTP_PASSWORD", ""),
SMTPFrom: getEnv("SMTP_FROM", "noreply@localhost"),
// Application URL (for generating links in emails)
BaseURL: getEnv("BASE_URL", "http://localhost:8080"),
}
}
// getEnv reads an environment variable or returns a default value.
// key: the name of the environment variable.
// defaultValue: the value to return if the environment variable is not set.
func getEnv(key, defaultValue string) string {
// Check if the environment variable is set and not empty.
if value := os.Getenv(key); value != "" {
return value
}
// Return the default value.
return defaultValue
}