Files
SharedClassManager/backend-go/internal/config/config.go
canglan 4193a1a153 refactor: 清理旧版兼容性,升级为 bcrypt 密码算法
- 密码哈希从 MD5+SHA1 升级为 bcrypt
- 删除 super_admins/users 表中的 salt 字段
- 删除旧版升级文件(upgrade.php, check_upgrade, execute_upgrade, sql/upgrades/)
- 删除 PASSWORD_SALT 配置项
- 清理所有'兼容 Python 版'注释
- 新项目独立,无历史包袱
2026-06-22 10:45:13 +08:00

156 lines
4.1 KiB
Go

// ===========================================
// 多班级版班级管理系统 - Go 后端
//
// 开发者: Canglan
// 联系方式: admin@sea-studio.top
// 版权归属: Sea Network Technology Studio
// 许可证: Apache License 2.0
//
// 版权所有 © Sea Network Technology Studio
// ===========================================
package config
import (
"fmt"
"os"
"strconv"
"strings"
"github.com/joho/godotenv"
)
// Config 应用全局配置结构体
type Config struct {
// 应用基础配置
AppName string
AppEnv string
Debug bool
AppPort string
// MySQL 数据库配置
DBHost string
DBPort int
DBUser string
DBPassword string
DBName string
DBMaxOpenConns int
DBMaxIdleConns int
DBConnMaxLife int // 秒
// Redis 配置
RedisHost string
RedisPort int
RedisPassword string
RedisDB int
RedisMaxConns int
// JWT 配置
JWTSecretKey string
JWTAlgorithm string
JWTExpireMinutes int
JWTIdleTimeoutMinutes int
// 系统管理员配置
SuperAdminLoginPath string
SuperAdminDefaultUser string
SuperAdminDefaultPass string
// 日志
LogLevel string
LogFile string
}
// AppConfig 全局配置实例
var AppConfig *Config
// Load 加载配置:先尝试加载 .env 文件,然后读取环境变量
func Load() (*Config, error) {
// 尝试加载 .env 文件(不存在不报错)
_ = godotenv.Load()
cfg := &Config{
AppName: getEnv("APP_NAME", "多班级版班级管理系统"),
AppEnv: getEnv("APP_ENV", "production"),
Debug: getEnvBool("DEBUG", false),
AppPort: getEnv("APP_PORT", "56789"),
DBHost: getEnv("DB_HOST", "localhost"),
DBPort: getEnvInt("DB_PORT", 3306),
DBUser: getEnv("DB_USER", "class_admin"),
DBPassword: getEnv("DB_PASSWORD", ""),
DBName: getEnv("DB_NAME", "classmanagerdb"),
DBMaxOpenConns: getEnvInt("DB_MAX_OPEN_CONNS", 25),
DBMaxIdleConns: getEnvInt("DB_MAX_IDLE_CONNS", 10),
DBConnMaxLife: getEnvInt("DB_CONN_MAX_LIFETIME", 300),
RedisHost: getEnv("REDIS_HOST", "localhost"),
RedisPort: getEnvInt("REDIS_PORT", 6379),
RedisPassword: getEnv("REDIS_PASSWORD", ""),
RedisDB: getEnvInt("REDIS_DB", 0),
RedisMaxConns: getEnvInt("REDIS_MAX_CONNECTIONS", 500),
JWTSecretKey: getEnv("JWT_SECRET_KEY", ""),
JWTAlgorithm: getEnv("JWT_ALGORITHM", "HS256"),
JWTExpireMinutes: getEnvInt("JWT_EXPIRE_MINUTES", 60),
JWTIdleTimeoutMinutes: getEnvInt("JWT_IDLE_TIMEOUT_MINUTES", 10),
SuperAdminLoginPath: getEnv("SUPER_ADMIN_LOGIN_PATH", "/super-admin"),
SuperAdminDefaultUser: getEnv("SUPER_ADMIN_DEFAULT_USERNAME", "admin"),
// 安全警告:默认密码仅用于首次部署初始化,上线前必须在 .env 中修改 SUPER_ADMIN_DEFAULT_PASSWORD。
// EnsureDefaultAdmin 通过 need_change_password=1 强制首次登录改密作为缓解措施。
SuperAdminDefaultPass: getEnv("SUPER_ADMIN_DEFAULT_PASSWORD", "Admin123"),
LogLevel: getEnv("LOG_LEVEL", "info"),
LogFile: getEnv("LOG_FILE", "logs/app.log"),
}
// 校验必填项
// 校验必填项
if cfg.JWTSecretKey == "" {
return nil, fmt.Errorf("配置 JWT_SECRET_KEY 不能为空")
}
AppConfig = cfg
return cfg, nil
}
// DSN 返回 MySQL 连接字符串
func (c *Config) DSN() string {
return fmt.Sprintf("%s:%s@tcp(%s:%d)/%s?charset=utf8mb4&parseTime=True&loc=Local",
c.DBUser, c.DBPassword, c.DBHost, c.DBPort, c.DBName)
}
// RedisAddr 返回 Redis 地址
func (c *Config) RedisAddr() string {
return fmt.Sprintf("%s:%d", c.RedisHost, c.RedisPort)
}
// IsProduction 判断是否为生产环境
func (c *Config) IsProduction() bool {
return c.AppEnv == "production"
}
// --- 辅助函数 ---
func getEnv(key, fallback string) string {
if val, ok := os.LookupEnv(key); ok {
return val
}
return fallback
}
func getEnvInt(key string, fallback int) int {
if val, ok := os.LookupEnv(key); ok {
if i, err := strconv.Atoi(val); err == nil {
return i
}
}
return fallback
}
func getEnvBool(key string, fallback bool) bool {
if val, ok := os.LookupEnv(key); ok {
return strings.ToLower(val) == "true"
}
return fallback
}