Files
dancefinder/domain/dancehall_test.go
T
argoyle 68dfcdfb03 feat(tests): add comprehensive band and dancehall tests
Introduce multiple unit tests for band event handling and creation, ensuring 
data integrity by validating commands and event generation. Confirm name 
preservation across various scenarios and verify aggregate identity and 
timestamps within events. Enhance application stability through improved 
test coverage.
2025-11-04 21:38:26 +01:00

269 lines
6.7 KiB
Go

package domain
import (
"context"
"testing"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"gitlab.com/unboundsoftware/dancefinder/dancefinder/testutil"
)
// TestDanceHall_ApplyDanceHallCreated tests that DanceHallCreated event builds state
func TestDanceHall_ApplyDanceHallCreated(t *testing.T) {
// Given
hall := &DanceHall{}
data := testutil.NewDanceHallData().
WithID("hall-123").
WithName("Folkets Hus").
WithLocation("Stockholm", "Stockholm", "Stockholms län")
event := &DanceHallCreated{
BaseEvent: data.BaseEvent(),
Name: data.Name,
City: data.City,
Municipality: data.Municipality,
State: data.State,
}
// When
err := hall.Apply(event)
// Then
require.NoError(t, err)
assert.Equal(t, "Folkets Hus", hall.Name)
assert.Equal(t, "Stockholm", hall.City)
assert.Equal(t, "Stockholm", hall.Municipality)
assert.Equal(t, "Stockholms län", hall.State)
assert.Equal(t, "hall-123", string(*hall.Identity()))
assert.Nil(t, hall.Latitude)
assert.Nil(t, hall.Longitude)
}
// TestDanceHall_ApplyDanceHallGeocoded tests geocoding event
func TestDanceHall_ApplyDanceHallGeocoded(t *testing.T) {
// Given
hall := &DanceHall{}
data := testutil.NewDanceHallData().WithID("hall-456")
createdEvent := &DanceHallCreated{
BaseEvent: data.BaseEvent(),
Name: data.Name,
City: data.City,
Municipality: data.Municipality,
State: data.State,
}
hall.Apply(createdEvent)
lat, lng := 59.3293, 18.0686
geocodedEvent := &DanceHallGeocoded{
BaseEvent: data.BaseEvent(),
Latitude: lat,
Longitude: lng,
}
// When
err := hall.Apply(geocodedEvent)
// Then
require.NoError(t, err)
require.NotNil(t, hall.Latitude)
require.NotNil(t, hall.Longitude)
assert.Equal(t, lat, *hall.Latitude)
assert.Equal(t, lng, *hall.Longitude)
}
// TestDanceHall_ApplyEventsInSequence tests event replay with multiple events
func TestDanceHall_ApplyEventsInSequence(t *testing.T) {
// Given
hall := &DanceHall{}
data := testutil.NewDanceHallData().
WithID("hall-789").
WithName("Test Hall").
WithCoordinates(59.0, 18.0)
createdEvent := &DanceHallCreated{
BaseEvent: data.BaseEvent(),
Name: data.Name,
City: data.City,
Municipality: data.Municipality,
State: data.State,
}
geocodedEvent := &DanceHallGeocoded{
BaseEvent: data.BaseEvent(),
Latitude: *data.Latitude,
Longitude: *data.Longitude,
}
// When - apply created, then geocoded
err1 := hall.Apply(createdEvent)
err2 := hall.Apply(geocodedEvent)
// Then
require.NoError(t, err1)
require.NoError(t, err2)
assert.Equal(t, "Test Hall", hall.Name)
assert.NotNil(t, hall.Latitude)
assert.NotNil(t, hall.Longitude)
assert.Equal(t, 59.0, *hall.Latitude)
assert.Equal(t, 18.0, *hall.Longitude)
}
// TestCreateDanceHall_Validate_ValidCommand tests successful validation
func TestCreateDanceHall_Validate_ValidCommand(t *testing.T) {
// Given
cmd := &CreateDanceHall{
Name: "Test Hall",
City: "Stockholm",
Municipality: "Stockholm",
State: "Stockholms län",
}
// When
err := cmd.Validate(context.Background(), &DanceHall{})
// Then
assert.NoError(t, err)
}
// TestCreateDanceHall_Validate_EmptyName tests validation failure
func TestCreateDanceHall_Validate_EmptyName(t *testing.T) {
// Given
cmd := &CreateDanceHall{
Name: "",
City: "Stockholm",
Municipality: "Stockholm",
State: "Stockholms län",
}
// When
err := cmd.Validate(context.Background(), &DanceHall{})
// Then
require.Error(t, err)
assert.ErrorIs(t, err, ErrDanceHallNameRequired)
}
// TestCreateDanceHall_Event tests event generation
func TestCreateDanceHall_Event(t *testing.T) {
// Given
cmd := &CreateDanceHall{
Name: "Test Hall",
City: "Göteborg",
Municipality: "Göteborg",
State: "Västra Götalands län",
}
// When
event := cmd.Event(context.Background())
// Then
require.NotNil(t, event)
hallCreated, ok := event.(*DanceHallCreated)
require.True(t, ok)
assert.Equal(t, "Test Hall", hallCreated.Name)
assert.Equal(t, "Göteborg", hallCreated.City)
assert.Equal(t, "Göteborg", hallCreated.Municipality)
assert.Equal(t, "Västra Götalands län", hallCreated.State)
}
// TestGeocodeDanceHall_Validate tests geocode command validation
func TestGeocodeDanceHall_Validate(t *testing.T) {
// Given
cmd := &GeocodeDanceHall{
Latitude: 59.3293,
Longitude: 18.0686,
}
// When
err := cmd.Validate(context.Background(), &DanceHall{})
// Then
assert.NoError(t, err)
}
// TestGeocodeDanceHall_Event tests geocode event generation
func TestGeocodeDanceHall_Event(t *testing.T) {
// Given
cmd := &GeocodeDanceHall{
Latitude: 59.3293,
Longitude: 18.0686,
}
// When
event := cmd.Event(context.Background())
// Then
require.NotNil(t, event)
geocoded, ok := event.(*DanceHallGeocoded)
require.True(t, ok)
assert.Equal(t, 59.3293, geocoded.Latitude)
assert.Equal(t, 18.0686, geocoded.Longitude)
}
// TestGeocodeDanceHall_Event_PreservesCoordinates tests coordinate precision
func TestGeocodeDanceHall_Event_PreservesCoordinates(t *testing.T) {
testCases := []struct {
name string
lat float64
lng float64
}{
{"Stockholm", 59.3293, 18.0686},
{"Göteborg", 57.7089, 11.9746},
{"Malmö", 55.6050, 13.0038},
{"High precision", 59.329323456789, 18.068612345678},
{"Zero", 0.0, 0.0},
{"Negative", -33.8688, 151.2093},
}
for _, tc := range testCases {
t.Run(tc.name, func(t *testing.T) {
// Given
cmd := &GeocodeDanceHall{
Latitude: tc.lat,
Longitude: tc.lng,
}
// When
event := cmd.Event(context.Background()).(*DanceHallGeocoded)
// Then
assert.Equal(t, tc.lat, event.Latitude)
assert.Equal(t, tc.lng, event.Longitude)
})
}
}
// TestDanceHall_ApplyDanceHallGeocoded_UpdatesCoordinates tests coordinate updates
func TestDanceHall_ApplyDanceHallGeocoded_UpdatesCoordinates(t *testing.T) {
// Given - hall with initial coordinates
hall := &DanceHall{}
data := testutil.NewDanceHallData().WithCoordinates(59.0, 18.0)
createdEvent := &DanceHallCreated{
BaseEvent: data.BaseEvent(),
Name: data.Name,
City: data.City,
Municipality: data.Municipality,
State: data.State,
}
geocodedEvent1 := &DanceHallGeocoded{
BaseEvent: data.BaseEvent(),
Latitude: 59.0,
Longitude: 18.0,
}
hall.Apply(createdEvent)
hall.Apply(geocodedEvent1)
// When - apply new geocoding (coordinates updated)
newLat, newLng := 60.0, 19.0
geocodedEvent2 := &DanceHallGeocoded{
BaseEvent: testutil.CreateTestBaseEvent("test-hall-456"),
Latitude: newLat,
Longitude: newLng,
}
err := hall.Apply(geocodedEvent2)
// Then
require.NoError(t, err)
assert.Equal(t, newLat, *hall.Latitude)
assert.Equal(t, newLng, *hall.Longitude)
}