package auth

import (
	"bytes"
	"fmt"
	"math/rand"
	"reflect"
	"testing"
)

func makeRandomString(n int) string {
	var buf bytes.Buffer
	for i := 0; i < n; i++ {
		c := byte(rand.Intn(254) + 1)
		buf.Write([]byte{c})
	}
	return buf.String()
}

func makeRandomMap() map[string]string {
	m := make(map[string]string)
	for i := 0; i < 7; i++ {
		var value string
		n := rand.Intn(10)
		switch {
		case n < 3:
			value = "asdf \""
		case n < 5:
			value = makeRandomString(64)
		default:
			value = fmt.Sprintf("value%d", i+1)
		}
		m[fmt.Sprintf("key%d", i+1)] = value
	}
	return m
}

func TestCodec_UTF8(t *testing.T) {
	c := &kvCodec{}
	m := map[string]string{
		"hello": "Hello, 世界",
	}
	b := c.Encode(m)
	m2 := make(map[string]string)
	err := c.Decode(b, m2)
	if err != nil {
		t.Fatal("Decode():", err)
	}
	if !reflect.DeepEqual(m, m2) {
		t.Fatalf("results differ: %+v vs %+v", m, m2)
	}
}

func TestCodec_Random(t *testing.T) {
	c := &kvCodec{}

	for i := 0; i < 1000; i++ {
		m := makeRandomMap()
		b := c.Encode(m)
		//t.Logf("encoded: '%s'", string(b))

		m2 := make(map[string]string)
		err := c.Decode(b, m2)
		if err != nil {
			t.Fatalf("Decode(%s): %v", string(b), err)
		}
		if !reflect.DeepEqual(m, m2) {
			t.Fatalf("decode results differ: %+v vs %+v", m, m2)
		}
	}
}