package config

import (
	"bufio"
	"bytes"
	"fmt"
	"os"
	"strings"
	"xg_auto_deploy/internal/models"
)

//var ClusterConfig1 models.ClusterConfig

func GetClusterConfig(path string) (*models.ClusterConfig, error) {
	clusterConfig := models.ClusterConfig{}
	firstPart, secondPart, err := splitFileByNID(path)
	if err != nil {
		fmt.Println("GetClusterConfig Error:", err)
		return &clusterConfig, err
	}

	SetClusterConfig(firstPart, secondPart, &clusterConfig)
	return &clusterConfig, nil
}

// 切分cluster文件 NID上下部分
func splitFileByNID(filename string) (string, string, error) {
	file, err := os.Open(filename)
	if err != nil {
		return "", "", err
	}
	defer file.Close()

	scanner := bufio.NewScanner(file)

	var firstPart, secondPart string
	foundNID := false
	for scanner.Scan() {
		line := scanner.Text()
		if !foundNID {
			if strings.Contains(line, "NID") && (strings.Index(line, "NID") == 0 || line[strings.Index(line, "NID")-1] == ' ') {
				foundNID = true
			} else {
				firstPart += line + "\n"
			}
		}
		if foundNID {
			secondPart += line + "\n"
		}
	}

	if err := scanner.Err(); err != nil {
		return "", "", err
	}

	return firstPart, secondPart, nil
}

// 根据cluster文件 NID 上下部分分别设置ClusterConfig的各个字段
func SetClusterConfig(firstPart string, secondPart string, clusterConfig *models.ClusterConfig) {
	var clusterfirstPart models.ClusterfirstPart
	// 按空格分割字符串
	parts := strings.Split(firstPart, " ")

	// 遍历分割后的部分
	for _, part := range parts {
		// 寻找等号的下标
		eqIndex := strings.Index(part, "=")
		if eqIndex == -1 {
			continue
		}

		// 获取key和value
		key := part[:eqIndex]
		value := part[eqIndex+1:]
		setFieldValue(&clusterfirstPart, key, value)

	}

	clusterConfig.FirstPart = clusterfirstPart
	// 按行分割字符串
	lines := strings.Split(secondPart, "\n")
	// 遍历每一行
	for _, line := range lines {
		// 去除末尾的分号和空格
		line = strings.TrimSpace(strings.TrimSuffix(line, ";"))
		// 如果行为空,则停止读取
		if line == "" {
			break
		}

		// 按空格分割行
		parts := strings.Split(line, " ")

		node := models.ClustersecondPart{}

		// 遍历分割后的部分
		for _, part := range parts {
			// 寻找等号的下标
			eqIndex := strings.Index(part, "=")
			if eqIndex == -1 {
				continue
			}

			// 获取key和value
			key := part[:eqIndex]
			value := part[eqIndex+1:]
			setFieldValue(&node, key, value)

		}
		clusterConfig.SecondParts = append(clusterConfig.SecondParts, node)

	}

}

// 设置字段的值
func setFieldValue(target interface{}, key string, value string) {

	switch t := target.(type) {
	case *models.ClusterfirstPart:
		switch key {
		case "#MAX_NODES":
			t.MaxNodes = value
		case "MASTER_GRPS":
			t.MasterGrps = value
		case "PROTOCOL":
			t.Protocol = strings.Trim(value, "'")
		case "MSG_PORT_NUM":
			t.MsgPortNum = value
		case "MAX_SEND_WIN":
			t.MaxSendWin = value
		case "MSG_HAVE_CRC":
			t.MsgHaveCRC = value
		case "MERGE_SMALL_MSG":
			t.MergeSmallMsg = value
		case "MSG_SIZE":
			t.MsgSize = value
		case "TIMEOUT":
			t.Timeout = value
		case "RPC_WINDOW":
			t.RPCWindow = value
		case "EJE_WINDOW":
			t.EJEWindow = value
		case "MAX_SHAKE_TIME":
			t.MaxShakeTime = value
		case "MY_NID":
			t.MyNID = value
		case "CHECK_RACK":
			t.CheckRack = value
		}
	case *models.ClustersecondPart:
		// 根据key设置对应字段的值
		switch key {
		case "NID":
			t.NID = value
		case "RACK":
			t.RACK = value
		case "PORTS":
			t.PORTS = value
		case "ROLE":
			t.ROLE = value
		case "LPU":
			t.LPU = value
		case "STORE_WEIGHT":
			t.StoreWeight = value
		case "STATE":
			t.STATE = value
		}
	}

}

func SaveClusterConfigBuffer(clusterConfig *models.ClusterConfig, MyNID string) *bytes.Buffer {

	str := fmt.Sprintf(`#MAX_NODES=%s MASTER_GRPS=%s  PROTOCOL='%s'  MSG_PORT_NUM=%s  MAX_SEND_WIN=%s
MSG_HAVE_CRC=%s MERGE_SMALL_MSG=%s MSG_SIZE=%s  TIMEOUT=%s  RPC_WINDOW=%s
EJE_WINDOW=%s  MAX_SHAKE_TIME=%s MY_NID=%s  CHECK_RACK=%s 
`, clusterConfig.FirstPart.MaxNodes, clusterConfig.FirstPart.MasterGrps,
		clusterConfig.FirstPart.Protocol, clusterConfig.FirstPart.MsgPortNum, clusterConfig.FirstPart.MaxSendWin,
		clusterConfig.FirstPart.MsgHaveCRC, clusterConfig.FirstPart.MergeSmallMsg, clusterConfig.FirstPart.MsgSize,
		clusterConfig.FirstPart.Timeout, clusterConfig.FirstPart.RPCWindow, clusterConfig.FirstPart.EJEWindow,
		clusterConfig.FirstPart.MaxShakeTime, MyNID, clusterConfig.FirstPart.CheckRack)

	for _, v := range clusterConfig.SecondParts {
		str += fmt.Sprintf(`NID=%s  RACK=%s  PORTS=%s  ROLE=%s  LPU=%s  STORE_WEIGHT=%s  STATE=%s;
`, v.NID, v.RACK, v.PORTS, v.ROLE, v.LPU, v.StoreWeight, v.STATE)
	}
	buffer := bytes.NewBufferString(str)

	//fmt.Println("File created successfully.")
	return buffer
}

// func SaveClusterConfig(clusterConfig *models.ClusterConfig, MyNID string) string {

// 	str := fmt.Sprintf(`#MAX_NODES=%s MASTER_GRPS=%s  PROTOCOL='%s'  MSG_PORT_NUM=%s  MAX_SEND_WIN=%s
// MSG_HAVE_CRC=%s MERGE_SMALL_MSG=%s MSG_SIZE=%s  TIMEOUT=%s  RPC_WINDOW=%s
// EJE_WINDOW=%s  MAX_SHAKE_TIME=%s MY_NID=%s  CHECK_RACK=%s
// `, clusterConfig.MaxNodes, clusterConfig.MasterGrps,
// 		clusterConfig.Protocol, clusterConfig.MsgPortNum, clusterConfig.MaxSendWin,
// 		clusterConfig.MsgHaveCRC, clusterConfig.MergeSmallMsg, clusterConfig.MsgSize,
// 		clusterConfig.Timeout, clusterConfig.RPCWindow, clusterConfig.EJEWindow,
// 		clusterConfig.MaxShakeTime, MyNID, clusterConfig.CheckRack)

// 	for _, v := range clusterConfig.Nodes {
// 		str += fmt.Sprintf(`NID=%s  RACK=%s  PORTS='%s'  ROLE='%s'  LPU=%s  STORE_WEIGHT=%s  STATE=%s;
// `, v.NID, v.RACK, v.PORTS, v.ROLE, v.LPU, v.StoreWeight, v.STATE)
// 	}

// 	// 生成随机数种子
// 	rand.Seed(time.Now().UnixNano())

// 	// 生成随机值作为后缀
// 	randomValue := rand.Intn(10000)

// 	// 检查目录是否存在
// 	_, err := os.Stat("file")
// 	if err != nil {
// 		if os.IsNotExist(err) {
// 			// 创建目录
// 			err = os.MkdirAll("file", os.ModePerm)
// 			if err != nil {
// 				fmt.Println("Error creating folder:", err)
// 				os.Exit(0)
// 			}
// 			fmt.Printf("Folder '%s' created successfully.\n", "logs")
// 			os.Exit(0)
// 		} else {
// 			fmt.Println("Error checking folder:", err)
// 			os.Exit(0)
// 		}
// 	}
// 	foldername := ".clusterTemp"

// 	// 构建带有随机值的文件名
// 	foldername = fmt.Sprintf("./file/%s_%d", foldername, randomValue)
// 	err = os.Mkdir(foldername, 0755)
// 	if err != nil {
// 		log.Fatal("无法创建文件夹:", err)
// 		os.Exit(0)
// 	}

// 	filename := fmt.Sprintf("%s/cluster.ini", foldername)
// 	err = os.WriteFile(filename, []byte(str), 0644)
// 	if err != nil {
// 		log.Fatal(err)
// 	}

// 	//fmt.Println("File created successfully.")
// 	return filename
// }