package configs

import (
	"bytes"
	_ "embed"
	"io"

	"bindbox-game/internal/pkg/env"

	"github.com/spf13/viper"
)

var config = new(Config)

type Config struct {
	MySQL struct {
		Read struct {
			Addr string `mapstructure:"addr" toml:"addr"`
			User string `mapstructure:"user" toml:"user"`
			Pass string `mapstructure:"pass" toml:"pass"`
			Name string `mapstructure:"name" toml:"name"`
		} `mapstructure:"read" toml:"read"`
		Write struct {
			Addr string `mapstructure:"addr" toml:"addr"`
			User string `mapstructure:"user" toml:"user"`
			Pass string `mapstructure:"pass" toml:"pass"`
			Name string `mapstructure:"name" toml:"name"`
		} `mapstructure:"write" toml:"write"`
	} `mapstructure:"mysql" toml:"mysql"`

	JWT struct {
		AdminSecret   string `mapstructure:"admin_secret" toml:"admin_secret"`
		PatientSecret string `mapstructure:"patient_secret" toml:"patient_secret"`
		DoctorSecret  string `mapstructure:"doctor_secret" toml:"doctor_secret"`
	} `mapstructure:"jwt" toml:"jwt"`

	Language struct {
		Local string `mapstructure:"local" toml:"local"`
	} `mapstructure:"language" toml:"language"`

	Wechat struct {
		AppID     string `mapstructure:"app_id" toml:"app_id"`
		AppSecret string `mapstructure:"app_secret" toml:"app_secret"`
	} `mapstructure:"wechat" toml:"wechat"`

	COS struct {
		Bucket    string `mapstructure:"bucket" toml:"bucket"`
		Region    string `mapstructure:"region" toml:"region"`
		SecretID  string `mapstructure:"secret_id" toml:"secret_id"`
		SecretKey string `mapstructure:"secret_key" toml:"secret_key"`
		BaseURL   string `mapstructure:"base_url" toml:"base_url"`
	} `mapstructure:"cos" toml:"cos"`
}

var (
	//go:embed dev_configs.toml
	devConfigs []byte

	//go:embed fat_configs.toml
	fatConfigs []byte

	//go:embed uat_configs.toml
	uatConfigs []byte

	//go:embed pro_configs.toml
	proConfigs []byte
)

func init() {
	var r io.Reader

	switch env.Active().Value() {
	case "dev":
		r = bytes.NewReader(devConfigs)
	case "fat":
		r = bytes.NewReader(fatConfigs)
	case "uat":
		r = bytes.NewReader(uatConfigs)
	case "pro":
		r = bytes.NewReader(proConfigs)
	default:
		r = bytes.NewReader(fatConfigs)
	}

	viper.SetConfigType("toml")

	if err := viper.ReadConfig(r); err != nil {
		panic(err)
	}

	if err := viper.Unmarshal(config); err != nil {
		panic(err)
	}
}

func Get() Config {
	return *config
}
