diff options
author | Joe Chen <jc@unknwon.io> | 2022-06-12 14:15:01 +0800 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-06-12 14:15:01 +0800 |
commit | b772603d78cb10f0501f3d08b01553bb33914b6e (patch) | |
tree | 5f160df17f1bbd357370b3aeeb5289b0a5c3c08d /internal/db/migrations | |
parent | 2e19f5a3c8193776685a5e9fea9ca8663f14dd8d (diff) |
migrations: add tests and remove XORM (#7050)
Diffstat (limited to 'internal/db/migrations')
-rw-r--r-- | internal/db/migrations/main_test.go | 40 | ||||
-rw-r--r-- | internal/db/migrations/migrations.go | 63 | ||||
-rw-r--r-- | internal/db/migrations/v20_test.go | 70 |
3 files changed, 143 insertions, 30 deletions
diff --git a/internal/db/migrations/main_test.go b/internal/db/migrations/main_test.go new file mode 100644 index 00000000..ee13c3e3 --- /dev/null +++ b/internal/db/migrations/main_test.go @@ -0,0 +1,40 @@ +// Copyright 2022 The Gogs Authors. All rights reserved. +// Use of this source code is governed by a MIT-style +// license that can be found in the LICENSE file. + +package migrations + +import ( + "flag" + "fmt" + "os" + "testing" + + "gorm.io/gorm/logger" + _ "modernc.org/sqlite" + log "unknwon.dev/clog/v2" + + "gogs.io/gogs/internal/testutil" +) + +func TestMain(m *testing.M) { + flag.Parse() + + level := logger.Silent + if !testing.Verbose() { + // Remove the primary logger and register a noop logger. + log.Remove(log.DefaultConsoleName) + err := log.New("noop", testutil.InitNoopLogger) + if err != nil { + fmt.Println(err) + os.Exit(1) + } + } else { + level = logger.Info + } + + // NOTE: AutoMigrate does not respect logger passed in gorm.Config. + logger.Default = logger.Default.LogMode(level) + + os.Exit(m.Run()) +} diff --git a/internal/db/migrations/migrations.go b/internal/db/migrations/migrations.go index 1e89883f..4f93b9c5 100644 --- a/internal/db/migrations/migrations.go +++ b/internal/db/migrations/migrations.go @@ -5,11 +5,9 @@ package migrations import ( - "fmt" - + "github.com/pkg/errors" "gorm.io/gorm" log "unknwon.dev/clog/v2" - "xorm.io/xorm" ) const minDBVersion = 19 @@ -58,29 +56,32 @@ var migrations = []Migration{ NewMigration("migrate access tokens to store SHA56", migrateAccessTokenToSHA256), } -// Migrate database to current version -func Migrate(x *xorm.Engine, db *gorm.DB) error { - if err := x.Sync(new(Version)); err != nil { - return fmt.Errorf("sync: %v", err) +// Migrate migrates the database schema and/or data to the current version. +func Migrate(db *gorm.DB) error { + err := db.AutoMigrate(new(Version)) + if err != nil { + return errors.Wrap(err, `auto migrate "version" table`) } - currentVersion := &Version{ID: 1} - has, err := x.Get(currentVersion) - if err != nil { - return fmt.Errorf("get: %v", err) - } else if !has { - // If the version record does not exist we think - // it is a fresh installation and we can skip all migrations. - currentVersion.ID = 0 - currentVersion.Version = int64(minDBVersion + len(migrations)) - - if _, err = x.InsertOne(currentVersion); err != nil { - return fmt.Errorf("insert: %v", err) + var current Version + err = db.Where("id = ?", 1).First(¤t).Error + if err == gorm.ErrRecordNotFound { + err = db.Create( + &Version{ + ID: 1, + Version: int64(minDBVersion + len(migrations)), + }, + ).Error + if err != nil { + return errors.Wrap(err, "create the version record") } + return nil + + } else if err != nil { + return errors.Wrap(err, "get the version record") } - v := currentVersion.Version - if minDBVersion > v { + if minDBVersion > current.Version { log.Fatal(` Hi there, thank you for using Gogs for so long! However, Gogs has stopped supporting auto-migration from your previously installed version. @@ -108,20 +109,22 @@ In case you're stilling getting this notice, go through instructions again until return nil } - if int(v-minDBVersion) > len(migrations) { + if int(current.Version-minDBVersion) > len(migrations) { // User downgraded Gogs. - currentVersion.Version = int64(len(migrations) + minDBVersion) - _, err = x.Id(1).Update(currentVersion) - return err + current.Version = int64(len(migrations) + minDBVersion) + return db.Where("id = ?", current.ID).Updates(current).Error } - for i, m := range migrations[v-minDBVersion:] { + + for i, m := range migrations[current.Version-minDBVersion:] { log.Info("Migration: %s", m.Description()) if err = m.Migrate(db); err != nil { - return fmt.Errorf("do migrate: %v", err) + return errors.Wrap(err, "do migrate") } - currentVersion.Version = v + int64(i) + 1 - if _, err = x.Id(1).Update(currentVersion); err != nil { - return err + + current.Version += int64(i) + 1 + err = db.Where("id = ?", current.ID).Updates(current).Error + if err != nil { + return errors.Wrap(err, "update the version record") } } return nil diff --git a/internal/db/migrations/v20_test.go b/internal/db/migrations/v20_test.go new file mode 100644 index 00000000..b95360de --- /dev/null +++ b/internal/db/migrations/v20_test.go @@ -0,0 +1,70 @@ +// Copyright 2022 The Gogs Authors. All rights reserved. +// Use of this source code is governed by a MIT-style +// license that can be found in the LICENSE file. + +package migrations + +import ( + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + + "gogs.io/gogs/internal/dbtest" +) + +type accessTokenPreV20 struct { + ID int64 + UserID int64 `gorm:"COLUMN:uid;INDEX"` + Name string + Sha1 string `gorm:"TYPE:VARCHAR(40);UNIQUE"` + CreatedUnix int64 + UpdatedUnix int64 +} + +func (*accessTokenPreV20) TableName() string { + return "access_token" +} + +type accessTokenV20 struct { + ID int64 + UserID int64 `gorm:"column:uid;index"` + Name string + Sha1 string `gorm:"type:VARCHAR(40);unique"` + SHA256 string `gorm:"type:VARCHAR(64);unique;not null"` + CreatedUnix int64 + UpdatedUnix int64 +} + +func (*accessTokenV20) TableName() string { + return "access_token" +} + +func TestMigrateAccessTokenToSHA256(t *testing.T) { + if testing.Short() { + t.Skip() + } + t.Parallel() + + db := dbtest.NewDB(t, "migrateAccessTokenToSHA256", new(accessTokenPreV20)) + err := db.Create( + &accessTokenPreV20{ + ID: 1, + UserID: 1, + Name: "test", + Sha1: "73da7bb9d2a475bbc2ab79da7d4e94940cb9f9d5", + CreatedUnix: db.NowFunc().Unix(), + UpdatedUnix: db.NowFunc().Unix(), + }, + ).Error + require.NoError(t, err) + + err = migrateAccessTokenToSHA256(db) + require.NoError(t, err) + + var got accessTokenV20 + err = db.Where("id = ?", 1).First(&got).Error + require.NoError(t, err) + assert.Equal(t, "73da7bb9d2a475bbc2ab79da7d4e94940cb9f9d5", got.Sha1) + assert.Equal(t, "ab144c7bd170691bb9bb995f1541c608e33a78b40174f30fc8a1616c0bc3a477", got.SHA256) +} |