package media_test import ( "context" "crypto/rand" "encoding/base64" "os" "testing" "gorm.io/driver/postgres" "gorm.io/gorm" "git.ilapage.cn/ila/yovision/Sense/server/app/sense/admission" "git.ilapage.cn/ila/yovision/Sense/server/app/sense/credential" "git.ilapage.cn/ila/yovision/Sense/server/app/sense/media" ) type readyController struct{} func (readyController) Health(context.Context) error { return nil } func (readyController) Apply(context.Context, media.Source) error { return nil } func (readyController) Delete(context.Context, string) error { return nil } func (readyController) Status(context.Context, string) (media.PathStatus, error) { return media.PathStatus{Exists: true, Ready: true}, nil } func TestPostgresColdStartRestoresDesiredRoute(t *testing.T) { dsn := os.Getenv("SENSE_MEDIA_TEST_DATABASE_URL") if dsn == "" { t.Skip("set SENSE_MEDIA_TEST_DATABASE_URL to run PostgreSQL media recovery") } db, err := gorm.Open(postgres.Open(dsn), &gorm.Config{}) if err != nil { t.Fatal(err) } if err = db.AutoMigrate(&media.Route{}, &admission.Profile{}, &credential.DeviceCredential{}); err != nil { t.Fatal(err) } t.Cleanup(func() { db.Exec("DROP TABLE IF EXISTS sense_media_routes, sense_admission_profiles, sense_device_credentials") }) key := make([]byte, 32) if _, err = rand.Read(key); err != nil { t.Fatal(err) } t.Setenv(credential.EnvironmentKey, base64.StdEncoding.EncodeToString(key)) vault, _ := credential.NewVault(key) ciphertext, err := vault.Encrypt("device-pg", credential.PurposeRTSP, "synthetic-user", "synthetic-password") if err != nil { t.Fatal(err) } if err = db.Create(&credential.DeviceCredential{DeviceID: "device-pg", Purpose: credential.PurposeRTSP, Ciphertext: ciphertext, KeyVersion: credential.Version()}).Error; err != nil { t.Fatal(err) } if err = db.Create(&admission.Profile{DeviceID: "device-pg", Token: "main", Name: "Main", StreamURI: "rtsp://192.0.2.1/live", VerificationStatus: "ready", VerificationDetail: "synthetic"}).Error; err != nil { t.Fatal(err) } first := media.NewService(db, readyController{}, nil, media.RuntimeConfig{}) if err = first.EnsureDevice(context.Background(), "device-pg"); err != nil { t.Fatal(err) } second := media.NewService(db.Session(&gorm.Session{NewDB: true}), readyController{}, nil, media.RuntimeConfig{}) if err = second.ReconcileDue(context.Background()); err != nil { t.Fatal(err) } items, err := second.List(context.Background()) if err != nil || len(items) != 1 || items[0].Actual != "ready" { t.Fatalf("items=%#v err=%v", items, err) } }