tercul-backend/internal/platform/config/config.go
google-labs-jules[bot] 1bb3e23c47 refactor(api): Consolidate server setup
This commit refactors the API server startup logic in `cmd/api/main.go` to simplify the application's architecture.

Key changes:
- Consolidates the three separate HTTP servers (GraphQL API, GraphQL Playground, and Prometheus metrics) into a single `http.Server` instance.
- Uses a single `http.ServeMux` to route requests to the appropriate handlers on distinct paths (`/query`, `/playground`, `/metrics`).
- Removes the now-redundant `PlaygroundPort` from the application's configuration.

This change simplifies the server startup and shutdown logic, reduces resource usage, and makes the application's entry point cleaner and easier to maintain.
2025-10-05 12:18:57 +00:00

160 lines
4.4 KiB
Go

package config
import (
"fmt"
"log"
"os"
"strconv"
"time"
)
// Config holds all configuration for the application
type Config struct {
// Database configuration
DBHost string
DBPort string
DBUser string
DBPassword string
DBName string
DBSSLMode string
DBTimeZone string
// Weaviate configuration
WeaviateScheme string
WeaviateHost string
// Redis configuration
RedisAddr string
RedisPassword string
RedisDB int
// Application configuration
Port string
ServerPort string
Environment string
LogLevel string
// Performance configuration
BatchSize int
PageSize int
RetryInterval time.Duration
MaxRetries int
// Security configuration
RateLimit int // Requests per second
RateLimitBurst int // Maximum burst size
JWTSecret string
JWTExpiration time.Duration
// NLP providers configuration
NLPUseLingua bool
NLPUseVADER bool
NLPUseTFIDF bool
// NLP cache configuration
NLPMemoryCacheCap int
NLPRedisCacheTTLSeconds int
}
// Cfg is the global configuration instance
var Cfg Config
// LoadConfig loads configuration from environment variables
func LoadConfig() {
Cfg = Config{
// Database configuration
DBHost: getEnv("DB_HOST", "localhost"),
DBPort: getEnv("DB_PORT", "5432"),
DBUser: getEnv("DB_USER", "postgres"),
DBPassword: getEnv("DB_PASSWORD", "postgres"),
DBName: getEnv("DB_NAME", "tercul"),
DBSSLMode: getEnv("DB_SSLMODE", "disable"),
DBTimeZone: getEnv("DB_TIMEZONE", "UTC"),
// Weaviate configuration
WeaviateScheme: getEnv("WEAVIATE_SCHEME", "http"),
WeaviateHost: getEnv("WEAVIATE_HOST", "localhost:8080"),
// Redis configuration
RedisAddr: getEnv("REDIS_ADDR", "127.0.0.1:6379"),
RedisPassword: getEnv("REDIS_PASSWORD", ""),
RedisDB: getEnvAsInt("REDIS_DB", 0),
// Application configuration
Port: getEnv("PORT", "8080"),
ServerPort: getEnv("SERVER_PORT", "8080"),
Environment: getEnv("ENVIRONMENT", "development"),
LogLevel: getEnv("LOG_LEVEL", "info"),
// Performance configuration
BatchSize: getEnvAsInt("BATCH_SIZE", 100),
PageSize: getEnvAsInt("PAGE_SIZE", 20),
RetryInterval: time.Duration(getEnvAsInt("RETRY_INTERVAL_SECONDS", 2)) * time.Second,
MaxRetries: getEnvAsInt("MAX_RETRIES", 3),
// Security configuration
RateLimit: getEnvAsInt("RATE_LIMIT", 10), // 10 requests per second by default
RateLimitBurst: getEnvAsInt("RATE_LIMIT_BURST", 50), // 50 burst requests by default
JWTSecret: getEnv("JWT_SECRET", ""),
JWTExpiration: time.Duration(getEnvAsInt("JWT_EXPIRATION_HOURS", 24)) * time.Hour,
// NLP providers configuration (enabled by default)
NLPUseLingua: getEnvAsBool("NLP_USE_LINGUA", true),
NLPUseVADER: getEnvAsBool("NLP_USE_VADER", true),
NLPUseTFIDF: getEnvAsBool("NLP_USE_TFIDF", true),
// NLP cache configuration
NLPMemoryCacheCap: getEnvAsInt("NLP_MEMORY_CACHE_CAP", 1024),
NLPRedisCacheTTLSeconds: getEnvAsInt("NLP_REDIS_CACHE_TTL_SECONDS", 86400),
}
log.Printf("Configuration loaded: Environment=%s, LogLevel=%s", Cfg.Environment, Cfg.LogLevel)
}
// GetDSN returns the database connection string
func (c *Config) GetDSN() string {
return fmt.Sprintf("host=%s port=%s user=%s password=%s dbname=%s sslmode=%s TimeZone=%s",
c.DBHost, c.DBPort, c.DBUser, c.DBPassword, c.DBName, c.DBSSLMode, c.DBTimeZone)
}
// Helper functions for environment variables
// getEnv gets an environment variable or returns a default value
func getEnv(key, defaultValue string) string {
value, exists := os.LookupEnv(key)
if !exists {
return defaultValue
}
return value
}
// getEnvAsInt gets an environment variable as an integer or returns a default value
func getEnvAsInt(key string, defaultValue int) int {
valueStr := getEnv(key, "")
if valueStr == "" {
return defaultValue
}
value, err := strconv.Atoi(valueStr)
if err != nil {
log.Printf("Warning: Invalid value for %s, using default: %v", key, err)
return defaultValue
}
return value
}
// getEnvAsBool gets an environment variable as a boolean or returns a default value
func getEnvAsBool(key string, defaultValue bool) bool {
valueStr := getEnv(key, "")
if valueStr == "" {
return defaultValue
}
switch valueStr {
case "1", "true", "TRUE", "True", "yes", "YES", "Yes", "on", "ON", "On":
return true
case "0", "false", "FALSE", "False", "no", "NO", "No", "off", "OFF", "Off":
return false
default:
return defaultValue
}
}