Files
fn_registry/functions/infra/migration_parse_test.go
T
egutierrez ec36278c7b feat: tipos Migration/MigrationStatus y funciones puras migration_parse + migration_validate
Fase 1 del issue 0015. Tipos Go en functions/infra/migration.go con metadata en
types/infra/. Funciones puras: MigrationParse (parsea filename NNN_name.sql +
bloques -- +up/-- +down) y MigrationValidate (verifica secuencia, huecos,
duplicados, bloques vacios). 16 tests, todos pasan.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-13 02:01:34 +02:00

96 lines
2.9 KiB
Go

package infra
import (
"strings"
"testing"
)
func TestMigrationParse(t *testing.T) {
t.Run("archivo valido con up y down retorna Migration correcta", func(t *testing.T) {
content := "\n-- +up\nCREATE TABLE users (id TEXT PRIMARY KEY);\n\n-- +down\nDROP TABLE IF EXISTS users;\n"
m, err := MigrationParse("001_create_users.sql", content)
if err != nil {
t.Fatalf("unexpected error: %v", err)
}
if m.Version != 1 {
t.Errorf("Version: got %d, want 1", m.Version)
}
if m.Name != "create_users" {
t.Errorf("Name: got %q, want %q", m.Name, "create_users")
}
if !strings.Contains(m.UpSQL, "CREATE TABLE users") {
t.Errorf("UpSQL missing CREATE TABLE: %q", m.UpSQL)
}
if !strings.Contains(m.DownSQL, "DROP TABLE") {
t.Errorf("DownSQL missing DROP TABLE: %q", m.DownSQL)
}
})
t.Run("archivo sin bloque down retorna DownSQL vacio sin error", func(t *testing.T) {
content := "-- +up\nCREATE TABLE logs (id INTEGER PRIMARY KEY);\n"
m, err := MigrationParse("002_create_logs.sql", content)
if err != nil {
t.Fatalf("unexpected error: %v", err)
}
if m.Version != 2 {
t.Errorf("Version: got %d, want 2", m.Version)
}
if m.Name != "create_logs" {
t.Errorf("Name: got %q, want %q", m.Name, "create_logs")
}
if m.DownSQL != "" {
t.Errorf("DownSQL: got %q, want empty", m.DownSQL)
}
})
t.Run("filename sin separador underscore retorna error", func(t *testing.T) {
_, err := MigrationParse("001.sql", "-- +up\nCREATE TABLE x (id TEXT);\n")
if err == nil {
t.Fatal("expected error, got nil")
}
})
t.Run("version no numerica retorna error", func(t *testing.T) {
_, err := MigrationParse("abc_create_users.sql", "-- +up\nCREATE TABLE x (id TEXT);\n")
if err == nil {
t.Fatal("expected error, got nil")
}
})
t.Run("bloque up vacio retorna error", func(t *testing.T) {
content := "-- +up\n\n-- +down\nDROP TABLE users;\n"
_, err := MigrationParse("001_create_users.sql", content)
if err == nil {
t.Fatal("expected error for empty up block, got nil")
}
})
t.Run("version cero retorna error", func(t *testing.T) {
_, err := MigrationParse("000_something.sql", "-- +up\nCREATE TABLE x (id TEXT);\n")
if err == nil {
t.Fatal("expected error for version 0, got nil")
}
})
t.Run("nombre descriptivo vacio retorna error", func(t *testing.T) {
_, err := MigrationParse("001_.sql", "-- +up\nCREATE TABLE x (id TEXT);\n")
if err == nil {
t.Fatal("expected error for empty descriptive name, got nil")
}
})
t.Run("filename con path completo extrae nombre base", func(t *testing.T) {
content := "-- +up\nCREATE TABLE x (id TEXT PRIMARY KEY);\n-- +down\nDROP TABLE x;\n"
m, err := MigrationParse("apps/my_app/migrations/003_add_index.sql", content)
if err != nil {
t.Fatalf("unexpected error: %v", err)
}
if m.Version != 3 {
t.Errorf("Version: got %d, want 3", m.Version)
}
if m.Name != "add_index" {
t.Errorf("Name: got %q, want %q", m.Name, "add_index")
}
})
}