package client

import (
	"fmt"
	"log"
	"net/http"
	"testing"
	"time"

	"github.com/openp2p-cn/inp2p/internal/server"
	"github.com/openp2p-cn/inp2p/pkg/config"
	"github.com/openp2p-cn/inp2p/pkg/nat"
)

func TestClientLogin(t *testing.T) {
	// Server
	sCfg := config.DefaultServerConfig()
	sCfg.WSPort = 29400
	sCfg.STUNUDP1 = 29482
	sCfg.STUNUDP2 = 29484
	sCfg.STUNTCP1 = 29480
	sCfg.STUNTCP2 = 29481
	sCfg.Token = 777

	stunQuit := make(chan struct{})
	defer close(stunQuit)
	go nat.ServeUDPSTUN(sCfg.STUNUDP1, stunQuit)
	go nat.ServeUDPSTUN(sCfg.STUNUDP2, stunQuit)
	go nat.ServeTCPSTUN(sCfg.STUNTCP1, stunQuit)
	go nat.ServeTCPSTUN(sCfg.STUNTCP2, stunQuit)

	srv := server.New(sCfg)
	srv.StartCleanup()
	mux := http.NewServeMux()
	mux.HandleFunc("/ws", srv.HandleWS)
	go http.ListenAndServe(fmt.Sprintf(":%d", sCfg.WSPort), mux)
	time.Sleep(300 * time.Millisecond)

	// Client
	cCfg := config.DefaultClientConfig()
	cCfg.ServerHost = "127.0.0.1"
	cCfg.ServerPort = 29400
	cCfg.Node = "testClient"
	cCfg.Token = 777
	cCfg.Insecure = true
	cCfg.RelayEnabled = true
	cCfg.STUNUDP1 = 29482
	cCfg.STUNUDP2 = 29484
	cCfg.STUNTCP1 = 29480
	cCfg.STUNTCP2 = 29481

	c := New(cCfg)

	// Run in background, should connect within 8 seconds
	connected := make(chan struct{})
	go func() {
		// We'll just let it run for a bit
		c.Run()
	}()

	// Wait for login
	time.Sleep(8 * time.Second)

	nodes := srv.GetOnlineNodes()
	log.Printf("Online nodes: %d", len(nodes))
	for _, n := range nodes {
		log.Printf("  - %s (NAT=%s, relay=%v)", n.Name, n.NATType, n.RelayEnabled)
	}

	if len(nodes) == 1 && nodes[0].Name == "testClient" {
		close(connected)
		log.Println("✅ Client connected successfully!")
	} else {
		t.Fatalf("Expected testClient online, got %d nodes", len(nodes))
	}

	c.Stop()
	srv.Stop()
}
