package main

import (
	"auth-service/internal/handler"
	"auth-service/internal/model"
	"auth-service/internal/repository"
	"auth-service/internal/service"
	"auth-service/pkg/middleware"
	"auth-service/pkg/utils"
	"fmt"
	"log"
	"os"

	_ "auth-service/docs" // docs is generated by Swag CLI

	"github.com/gin-gonic/gin"
	swaggerFiles "github.com/swaggo/files"
	ginSwagger "github.com/swaggo/gin-swagger"
	"gorm.io/driver/postgres"
	"gorm.io/gorm"
)

// @title           Auth Service API
// @version         1.0
// @description     LLM Filter System Authentication Service API
// @host            localhost:8080
// @BasePath        /api/v1
// @securityDefinitions.apikey BearerAuth
// @in header
// @name Authorization

func main() {
	// 获取环境变量配置
	dbHost := os.Getenv("DB_HOST")
	dbUser := os.Getenv("DB_USER")
	dbPassword := os.Getenv("DB_PASSWORD")
	dbName := os.Getenv("DB_NAME")
	dbPort := os.Getenv("DB_PORT")

	// 必需的环境变量检查
	if dbHost == "" || dbUser == "" || dbPassword == "" || dbName == "" || dbPort == "" {
		log.Fatal("Missing required database environment variables: DB_HOST, DB_USER, DB_PASSWORD, DB_NAME, DB_PORT")
	}

	dsn := fmt.Sprintf("host=%s user=%s password=%s dbname=%s port=%s sslmode=disable TimeZone=Asia/Shanghai",
		dbHost, dbUser, dbPassword, dbName, dbPort)

	db, err := gorm.Open(postgres.Open(dsn), &gorm.Config{})
	if err != nil {
		log.Fatalf("Failed to connect to database: %v", err)
	}

	// 自动迁移数据库结构
	if err := db.AutoMigrate(&model.User{}, &model.Binding{}); err != nil {
		log.Fatalf("Failed to migrate database: %v", err)
	}

	// 初始化依赖注入
	userRepo := repository.NewUserRepository(db)

	// 初始化管理员账号
	initAdminUser(userRepo)

	bindingRepo := repository.NewBindingRepository(db)
	bindingSvc := service.NewBindingService(bindingRepo)
	bindingHandler := handler.NewBindingHandler(bindingSvc)

	authSvc := service.NewAuthService(userRepo, bindingRepo)
	authHandler := handler.NewAuthHandler(authSvc)

	r := gin.Default()

	// Swagger 文档路由
	r.GET("/swagger/*any", ginSwagger.WrapHandler(swaggerFiles.Handler))

	// 路由分组
	v1 := r.Group("/api/v1")
	{
		authGroup := v1.Group("/auth")
		{
			authGroup.POST("/login", authHandler.Login)
			authGroup.POST("/register", authHandler.Register)
		}

		// 绑定相关路由，需要认证
		bindingsGroup := v1.Group("/bindings")
		bindingsGroup.Use(middleware.AuthMiddleware())
		{
			bindingsGroup.POST("", bindingHandler.Bind)
			bindingsGroup.DELETE("/:person_id", bindingHandler.Unbind)
			bindingsGroup.GET("/me", bindingHandler.Me)
		}
	}

	log.Println("Auth Service starting on :8081...")
	if err := r.Run(":8081"); err != nil {
		log.Fatal("Server failed to start:", err)
	}
}

func initAdminUser(repo *repository.UserRepository) {
	adminUsername := os.Getenv("ADMIN_USERNAME")
	if adminUsername == "" {
		adminUsername = "admin"
	}

	exists, err := repo.ExistsByUsername(adminUsername)
	if err != nil {
		log.Printf("Failed to check admin user existence: %v", err)
		return
	}

	if !exists {
		log.Println("Admin user not found. Creating default admin user...")

		adminPassword := os.Getenv("ADMIN_PASSWORD")
		if adminPassword == "" {
			log.Fatal("ADMIN_PASSWORD environment variable is required for initial admin user creation")
		}

		hashedPwd, err := utils.HashPassword(adminPassword)
		if err != nil {
			log.Printf("Failed to hash admin password: %v", err)
			return
		}

		adminEmail := os.Getenv("ADMIN_EMAIL")
		if adminEmail == "" {
			adminEmail = "admin@example.com"
		}

		adminUser := &model.User{
			Username:  adminUsername,
			Email:     adminEmail,
			Password:  hashedPwd,
			Role:      "administrator",
			RoleLevel: 5,
			Edition:   "edu",
		}

		if err := repo.Create(adminUser); err != nil {
			log.Printf("Failed to create admin user: %v", err)
		} else {
			log.Printf("Admin user created successfully. Username: %s", adminUsername)
		}
	} else {
		log.Println("Admin user already exists.")
	}
}
