2025-11-17 12:17:44 +07:00

145 lines
3.2 KiB
Go

package config
import (
"fmt"
"log"
"lost-and-found/internal/models"
"os"
"time"
"gorm.io/driver/mysql"
"gorm.io/gorm"
"gorm.io/gorm/logger"
)
var db *gorm.DB
// DatabaseConfig holds database connection configuration
type DatabaseConfig struct {
Host string
Port string
User string
Password string
DBName string
Charset string
ParseTime string
Loc string
}
// GetDatabaseConfig returns database configuration from environment
func GetDatabaseConfig() DatabaseConfig {
return DatabaseConfig{
Host: getEnv("DB_HOST", "localhost"),
Port: getEnv("DB_PORT", "3306"),
User: getEnv("DB_USER", "root"),
Password: getEnv("DB_PASSWORD", ""),
DBName: getEnv("DB_NAME", "lost_and_found"),
Charset: getEnv("DB_CHARSET", "utf8mb4"),
ParseTime: getEnv("DB_PARSE_TIME", "True"),
Loc: getEnv("DB_LOC", "Local"),
}
}
// InitDB initializes database connection
func InitDB() error {
config := GetDatabaseConfig()
// Build DSN (Data Source Name) for MySQL
dsn := fmt.Sprintf(
"%s:%s@tcp(%s:%s)/%s?charset=%s&parseTime=%s&loc=%s",
config.User,
config.Password,
config.Host,
config.Port,
config.DBName,
config.Charset,
config.ParseTime,
config.Loc,
)
// Configure GORM logger
gormLogger := logger.Default
if IsDevelopment() {
gormLogger = logger.Default.LogMode(logger.Info)
} else {
gormLogger = logger.Default.LogMode(logger.Error)
}
// Open database connection
var err error
db, err = gorm.Open(mysql.Open(dsn), &gorm.Config{
Logger: gormLogger,
NowFunc: func() time.Time {
return time.Now().Local()
},
})
if err != nil {
return fmt.Errorf("failed to connect to database: %w", err)
}
// Get underlying SQL database
sqlDB, err := db.DB()
if err != nil {
return fmt.Errorf("failed to get database instance: %w", err)
}
// Set connection pool settings
sqlDB.SetMaxIdleConns(10)
sqlDB.SetMaxOpenConns(100)
sqlDB.SetConnMaxLifetime(time.Hour)
// Test connection
if err := sqlDB.Ping(); err != nil {
return fmt.Errorf("failed to ping database: %w", err)
}
log.Println("✅ Database connected successfully")
return nil
}
// GetDB returns the database instance
func GetDB() *gorm.DB {
return db
}
// RunMigrations runs database migrations
func RunMigrations(db *gorm.DB) error {
log.Println("⚠️ Auto-migration is disabled. Please run schema.sql manually via HeidiSQL")
log.Println("📋 Steps:")
log.Println(" 1. Open HeidiSQL")
log.Println(" 2. Connect to your MySQL database")
log.Println(" 3. Create database 'lost_and_found' if not exists")
log.Println(" 4. Run database/schema.sql")
log.Println(" 5. Run database/seed.sql (optional)")
// Check if tables exist
if !db.Migrator().HasTable(&models.Role{}) {
return fmt.Errorf("❌ Tables not found. Please run database/schema.sql first")
}
log.Println("✅ Database tables detected")
return nil
}
// CloseDB closes database connection
func CloseDB() error {
if db != nil {
sqlDB, err := db.DB()
if err != nil {
return err
}
return sqlDB.Close()
}
return nil
}
// Helper function to get environment variable with default value
func getEnv(key, defaultValue string) string {
value := os.Getenv(key)
if value == "" {
return defaultValue
}
return value
}