package main import ( "errors" "os" "path/filepath" "slices" "testing" ) func TestNewMigrationReturnsMigrationWithProperties(t *testing.T) { migration := NewMigration("path", "name", "requires") if migration.Path != "path" || migration.Name != "name" || migration.Requires != "requires" || migration.Run != false { t.Errorf("Expected Migration with passed values and default, got %#v", migration) } } func TestMigrationBytesReturnsBytesFromMigrationFile(t *testing.T) { mockMigrationData := []byte("SELECT * FROM myTable;") migrationRoot := t.TempDir() migrationPath := filepath.Join(migrationRoot, "0001.sql") os.WriteFile(migrationPath, mockMigrationData, 0750) migration := NewMigration(migrationPath, "TestMigration", "") migrationBytes, _ := migration.Bytes() if !slices.Equal(migrationBytes, mockMigrationData) { t.Errorf("Expected bytes to be %#v, got %#v.", mockMigrationData, migrationBytes) } } func TestMigrationBytesErrorsIfFileCannotBeRead(t *testing.T) { migration := NewMigration("not-a-file", "TestMigration", "") _, err := migration.Bytes() if err == nil { t.Errorf("Expected error, got nil.") } } func TestMigrationTextReturnsFileContentAsString(t *testing.T) { mockMigrationData := []byte("SELECT * FROM myTable;") migrationRoot := t.TempDir() migrationPath := filepath.Join(migrationRoot, "0001.sql") os.WriteFile(migrationPath, mockMigrationData, 0750) migration := NewMigration(migrationPath, "TestMigration", "") migrationStr, _ := migration.Text() if migrationStr != string(mockMigrationData) { t.Errorf("Expected text to be %#v, got %#v.", string(mockMigrationData), migrationStr) } } func TestMigrationTextErrorsIfFileCannotBeRead(t *testing.T) { migration := NewMigration("not-a-file", "TestMigration", "") _, err := migration.Text() if err == nil { t.Errorf("Expected error, got nil.") } } func TestMigrationSqlReturnsSqlAsStringWithoutComments(t *testing.T) { mockMigrationData := []byte("SELECT * FROM myTable;") mockMigrationComment := []byte("--comment\n") mockMigrationDataWithComment := append(mockMigrationComment, mockMigrationData...) migrationRoot := t.TempDir() migrationPath := filepath.Join(migrationRoot, "0001.sql") os.WriteFile(migrationPath, mockMigrationDataWithComment, 0750) migration := NewMigration(migrationPath, "TestMigration", "") migrationStr, _ := migration.Sql() if migrationStr != string(mockMigrationData) { t.Errorf("Expected text to be %#v, got %#v.", string(mockMigrationData), migrationStr) } } func TestMigrationSqlErrorsIfFileCannotBeRead(t *testing.T) { migration := NewMigration("not-a-file", "TestMigration", "") _, err := migration.Sql() if err == nil { t.Errorf("Expected error, got nil.") } } func TestMigrationApplyRunsTheSqlOnTheGivenDatabase(t *testing.T) { mockMigrationData := []byte("SELECT * FROM myTable;") migrationRoot := t.TempDir() migrationPath := filepath.Join(migrationRoot, "0001.sql") os.WriteFile(migrationPath, mockMigrationData, 0750) migration := NewMigration(migrationPath, "TestMigration", "") mockDB := &MockSqlDB{} err := migration.Apply(mockDB) if err != nil { t.Errorf("Did not expect error, got %#v", err) } expectedQueries := []string{string(mockMigrationData)} if !slices.Equal(mockDB.queries, expectedQueries) { t.Errorf("Expected queries %#v, got %#v", expectedQueries, mockDB.queries) } } func TestMigrationApplyErrorsIfFileCannotBeRead(t *testing.T) { migration := NewMigration("not-a-file", "TestMigration", "") mockDB := &MockSqlDB{} err := migration.Apply(mockDB) if err == nil { t.Errorf("Expected error, got nil.") } } func TestMigrationApplyErrorsIfRunningSqlFails(t *testing.T) { mockMigrationData := []byte("SELECT * FROM myTable;") migrationRoot := t.TempDir() migrationPath := filepath.Join(migrationRoot, "0001.sql") os.WriteFile(migrationPath, mockMigrationData, 0750) migration := NewMigration(migrationPath, "TestMigration", "") mockDB := &MockSqlDB{ mockedError: errors.New("test error"), } err := migration.Apply(mockDB) if err == nil { t.Errorf("Expected error, got nil") } }