package invite

import (
	"bytes"
	"encoding/json"
	"fmt"
	"io"
	"net/http"

	"codex-pool/internal/client"
)

// DefaultProxy 默认代理
const DefaultProxy = "http://127.0.0.1:7890"

// TeamInviter Team 邀请器
type TeamInviter struct {
	client      *client.TLSClient
	accessToken string
	accountID   string
}

// InviteRequest 邀请请求
type InviteRequest struct {
	EmailAddresses []string `json:"email_addresses"`
	Role           string   `json:"role"`
	ResendEmails   bool     `json:"resend_emails"`
}

// AccountCheckResponse 账号检查响应
type AccountCheckResponse struct {
	Accounts map[string]struct {
		Account struct {
			PlanType string `json:"plan_type"`
		} `json:"account"`
	} `json:"accounts"`
}

// New 创建邀请器 (使用默认代理)
func New(accessToken string) *TeamInviter {
	c, _ := client.New(DefaultProxy)
	return &TeamInviter{
		client:      c,
		accessToken: accessToken,
	}
}

// NewWithProxy 创建邀请器 (指定代理)
func NewWithProxy(accessToken, proxy string) *TeamInviter {
	c, _ := client.New(proxy)
	return &TeamInviter{
		client:      c,
		accessToken: accessToken,
	}
}

// GetAccountID 获取 Team 的 account_id (workspace_id)
func (t *TeamInviter) GetAccountID() (string, error) {
	req, _ := http.NewRequest("GET", "https://chatgpt.com/backend-api/accounts/check/v4-2023-04-27", nil)
	req.Header.Set("Authorization", "Bearer "+t.accessToken)
	req.Header.Set("Accept", "application/json")

	resp, err := t.client.Do(req)
	if err != nil {
		return "", fmt.Errorf("请求失败: %v", err)
	}
	defer resp.Body.Close()

	body, _ := io.ReadAll(resp.Body)

	if resp.StatusCode != 200 {
		return "", fmt.Errorf("HTTP %d: %s", resp.StatusCode, string(body)[:min(200, len(body))])
	}

	var result AccountCheckResponse
	if err := json.Unmarshal(body, &result); err != nil {
		return "", fmt.Errorf("解析失败: %v", err)
	}

	// 查找 team plan 的 account_id
	for accountID, info := range result.Accounts {
		if accountID != "default" && info.Account.PlanType == "team" {
			t.accountID = accountID
			return accountID, nil
		}
	}

	// 如果没找到 team，返回第一个非 default 的
	for accountID := range result.Accounts {
		if accountID != "default" {
			t.accountID = accountID
			return accountID, nil
		}
	}

	return "", fmt.Errorf("未找到 account_id")
}

// SendInvites 发送邀请
func (t *TeamInviter) SendInvites(emails []string) error {
	if t.accountID == "" {
		return fmt.Errorf("未设置 account_id，请先调用 GetAccountID()")
	}

	url := fmt.Sprintf("https://chatgpt.com/backend-api/accounts/%s/invites", t.accountID)

	payload := InviteRequest{
		EmailAddresses: emails,
		Role:           "standard-user",
		ResendEmails:   true,
	}
	body, _ := json.Marshal(payload)

	req, _ := http.NewRequest("POST", url, bytes.NewReader(body))
	req.Header.Set("Authorization", "Bearer "+t.accessToken)
	req.Header.Set("Content-Type", "application/json")
	req.Header.Set("Chatgpt-Account-Id", t.accountID)

	resp, err := t.client.Do(req)
	if err != nil {
		return fmt.Errorf("请求失败: %v", err)
	}
	defer resp.Body.Close()

	respBody, _ := io.ReadAll(resp.Body)

	if resp.StatusCode != 200 && resp.StatusCode != 201 {
		return fmt.Errorf("HTTP %d: %s", resp.StatusCode, string(respBody)[:min(200, len(respBody))])
	}

	return nil
}

// GetPendingInvites 获取待处理的邀请列表
func (t *TeamInviter) GetPendingInvites() ([]string, error) {
	if t.accountID == "" {
		return nil, fmt.Errorf("未设置 account_id")
	}

	url := fmt.Sprintf("https://chatgpt.com/backend-api/accounts/%s/invites?offset=0&limit=100&query=", t.accountID)

	req, _ := http.NewRequest("GET", url, nil)
	req.Header.Set("Authorization", "Bearer "+t.accessToken)

	resp, err := t.client.Do(req)
	if err != nil {
		return nil, err
	}
	defer resp.Body.Close()

	body, _ := io.ReadAll(resp.Body)

	var result struct {
		Invites []struct {
			Email string `json:"email"`
		} `json:"invites"`
	}

	if err := json.Unmarshal(body, &result); err != nil {
		return nil, err
	}

	var emails []string
	for _, inv := range result.Invites {
		emails = append(emails, inv.Email)
	}

	return emails, nil
}

// AcceptInvite 接受邀请 (使用被邀请账号的 token)
func AcceptInvite(inviteLink string, accessToken string) error {
	c, _ := client.New(DefaultProxy)

	req, _ := http.NewRequest("GET", inviteLink, nil)
	req.Header.Set("Authorization", "Bearer "+accessToken)

	resp, err := c.Do(req)
	if err != nil {
		return err
	}
	defer resp.Body.Close()

	if resp.StatusCode != 200 && resp.StatusCode != 302 {
		body, _ := io.ReadAll(resp.Body)
		return fmt.Errorf("HTTP %d: %s", resp.StatusCode, string(body)[:min(100, len(body))])
	}

	return nil
}
