package event

import (
	"reflect"
	"testing"

	"github.com/google/uuid"
)

func getTestEntityUUID() uuid.UUID {
	id, _ := uuid.Parse("688a264e-5f85-40f8-bd13-afc42fcd5c7a")

	return id
}

func TestNewAddEvent(t *testing.T) {
	type args struct {
		entityID uuid.UUID
	}
	tests := []struct {
		name string
		args args
		want Event
	}{
		{
			name: "should create a new add event",
			args: args{
				entityID: getTestEntityUUID(),
			},
			want: Event{
				ID:       uuid.New(),
				EntityID: getTestEntityUUID(),
				Type:     TypeAdd,
			},
		},
	}
	for _, tt := range tests {
		t.Run(tt.name, func(t *testing.T) {
			got := NewAddEvent(tt.args.entityID)

			if !reflect.DeepEqual(got.EntityID, tt.want.EntityID) {
				t.Errorf("NewAddEvent().EntityID = %v, want %v", got, tt.want)
			}

			if !reflect.DeepEqual(got.Type, tt.want.Type) {
				t.Errorf("NewAddEvent().Type = %v, want %v", got, tt.want)
			}
		})
	}
}

func TestNewDeleteEvent(t *testing.T) {
	type args struct {
		entityID uuid.UUID
	}
	tests := []struct {
		name string
		args args
		want Event
	}{
		{
			name: "should create a new delete event",
			args: args{
				entityID: getTestEntityUUID(),
			},
			want: Event{
				ID:       uuid.New(),
				EntityID: getTestEntityUUID(),
				Type:     TypeDelete,
			},
		},
	}
	for _, tt := range tests {
		t.Run(tt.name, func(t *testing.T) {
			got := NewDeleteEvent(tt.args.entityID)

			if !reflect.DeepEqual(got.EntityID, tt.want.EntityID) {
				t.Errorf("NewDeleteEvent().EntityID = %v, want %v", got, tt.want)
			}

			if !reflect.DeepEqual(got.Type, tt.want.Type) {
				t.Errorf("NewDeleteEvent().Type = %v, want %v", got, tt.want)
			}
		})
	}
}

func TestNewUpdateEvent(t *testing.T) {
	type args struct {
		entityID uuid.UUID
	}
	tests := []struct {
		name string
		args args
		want Event
	}{
		{
			name: "should create a new update event",
			args: args{
				entityID: getTestEntityUUID(),
			},
			want: Event{
				ID:       uuid.New(),
				EntityID: getTestEntityUUID(),
				Type:     TypeUpdate,
			},
		},
	}
	for _, tt := range tests {
		t.Run(tt.name, func(t *testing.T) {
			got := NewUpdateEvent(tt.args.entityID)

			if !reflect.DeepEqual(got.EntityID, tt.want.EntityID) {
				t.Errorf("NewUpdateEvent().EntityID = %v, want %v", got, tt.want)
			}

			if !reflect.DeepEqual(got.Type, tt.want.Type) {
				t.Errorf("NewUpdateEvent().Type = %v, want %v", got, tt.want)
			}
		})
	}
}

func TestNewMneUpdateEvent(t *testing.T) {
	type args struct {
		entityID          uuid.UUID
		pathsAndValuesMap map[string]string
	}
	tests := []struct {
		name string
		args args
		want Event
	}{
		{
			name: "should create a new update event",
			args: args{
				entityID:          getTestEntityUUID(),
				pathsAndValuesMap: map[string]string{"some/random/path": "val"},
			},
			want: Event{
				ID:                uuid.New(),
				EntityID:          getTestEntityUUID(),
				Type:              TypeUpdate,
				PathsAndValuesMap: map[string]string{"some/random/path": "val"},
			},
		},
	}
	for _, tt := range tests {
		t.Run(tt.name, func(t *testing.T) {
			got := NewMneUpdateEvent(tt.args.entityID, tt.args.pathsAndValuesMap)

			if !reflect.DeepEqual(got.EntityID, tt.want.EntityID) {
				t.Errorf("NewMneUpdateEvent().EntityID = %v, want %v", got, tt.want)
			}

			if !reflect.DeepEqual(got.Type, tt.want.Type) {
				t.Errorf("NewMneUpdateEvent().Type = %v, want %v", got, tt.want)
			}

			if !reflect.DeepEqual(got.PathsAndValuesMap, tt.want.PathsAndValuesMap) {
				t.Errorf("NewMneUpdateEvent().PathsAndValuesMap = %v, want %v", got, tt.want)
			}
		})
	}
}
