package crypto

import (
	"fmt"
	"testing"
)

// TestPasswordHash 测试密码加密功能
func TestPasswordHash(t *testing.T) {
	testCases := []struct {
		name     string
		password string
		cost     int
		wantErr  bool
	}{
		{
			name:     "默认cost加密",
			password: "123456",
			cost:     0, // 使用默认cost
			wantErr:  false,
		},
		{
			name:     "自定义cost加密",
			password: "admin123",
			cost:     12,
			wantErr:  false,
		},
		{
			name:     "空密码",
			password: "",
			cost:     10,
			wantErr:  false,
		},
		{
			name:     "复杂密码",
			password: "MyP@ssw0rd!2024",
			cost:     11,
			wantErr:  false,
		},
	}

	for _, tc := range testCases {
		t.Run(tc.name, func(t *testing.T) {
			var hash string
			var err error

			if tc.cost > 0 {
				hash, err = PasswordHash(tc.password, tc.cost)
			} else {
				hash, err = PasswordHash(tc.password)
			}

			if tc.wantErr {
				if err == nil {
					t.Errorf("PasswordHash() 期望出错，但没有错误")
				}
				return
			}

			if err != nil {
				t.Errorf("PasswordHash() 出现错误 = %v", err)
				return
			}

			if hash == "" {
				t.Errorf("PasswordHash() 返回空字符串")
				return
			}

			// 验证生成的hash长度合理（bcrypt hash通常是60字符）
			if len(hash) < 50 {
				t.Errorf("PasswordHash() 返回的hash太短 = %d", len(hash))
			}

			// 验证密码验证功能
			if !PasswordVerify(tc.password, hash) {
				t.Errorf("PasswordVerify() 验证失败，密码不匹配")
			}

			// 验证错误密码
			if PasswordVerify("wrongpassword", hash) {
				t.Errorf("PasswordVerify() 应该验证失败，但验证成功了")
			}
		})
	}
}

// TestPasswordVerify 测试密码验证功能
func TestPasswordVerify(t *testing.T) {
	// 先生成一个已知的hash用于测试
	testPassword := "123456"
	testHash, err := PasswordHash(testPassword, 10)
	if err != nil {
		t.Fatalf("生成测试hash失败: %v", err)
	}

	testCases := []struct {
		name     string
		password string
		hash     string
		want     bool
	}{
		{
			name:     "正确密码",
			password: testPassword,
			hash:     testHash,
			want:     true,
		},
		{
			name:     "错误密码",
			password: "wrongpassword",
			hash:     testHash,
			want:     false,
		},
	}

	for _, tc := range testCases {
		t.Run(tc.name, func(t *testing.T) {
			got := PasswordVerify(tc.password, tc.hash)
			if got != tc.want {
				t.Errorf("PasswordVerify() = %v, want %v", got, tc.want)
			}
		})
	}
}

// TestGeneratePasswords 生成常用密码的hash值（用于实际使用）
func TestGeneratePasswords(t *testing.T) {
	// 常用密码列表
	passwords := []string{
		"123456",
		"admin123",
		"password",
		"root",
		"test123",
		"MyP@ssw0rd!2024",
		"admin123.",
		"123456789",
		"qwerty",
		"abc123",
	}

	fmt.Println("\n=== 生成密码Hash值 ===")
	for i, password := range passwords {
		hash, err := PasswordHash(password)
		if err != nil {
			t.Errorf("生成密码 %s 的hash失败: %v", password, err)
			continue
		}

		fmt.Printf("%d. 密码: %-20s Hash: %s\n", i+1, password, hash)

		// 验证生成的hash是否正确
		if !PasswordVerify(password, hash) {
			t.Errorf("验证密码 %s 失败", password)
		}
	}
	fmt.Println("=== 密码生成完成 ===")
}

// BenchmarkPasswordHash 性能测试
func BenchmarkPasswordHash(b *testing.B) {
	password := "testpassword123"

	b.Run("Cost10", func(b *testing.B) {
		for i := 0; i < b.N; i++ {
			_, err := PasswordHash(password, 10)
			if err != nil {
				b.Fatal(err)
			}
		}
	})

	b.Run("Cost12", func(b *testing.B) {
		for i := 0; i < b.N; i++ {
			_, err := PasswordHash(password, 12)
			if err != nil {
				b.Fatal(err)
			}
		}
	})
}

// BenchmarkPasswordVerify 验证性能测试
func BenchmarkPasswordVerify(b *testing.B) {
	password := "testpassword123"
	hash, _ := PasswordHash(password, 10)

	b.ResetTimer()
	for i := 0; i < b.N; i++ {
		PasswordVerify(password, hash)
	}
}
