aboutsummaryrefslogtreecommitdiff
path: root/common/db.go
diff options
context:
space:
mode:
authorAnhgelus Morhtuuzh <william@herges.fr>2026-03-08 13:38:10 +0100
committerAnhgelus Morhtuuzh <william@herges.fr>2026-03-08 13:38:10 +0100
commitddd6306752186c149f8ad3bf2f59b5428cf01296 (patch)
tree0e40562ef636a9a76cc298e8695cc04abbdcfda5 /common/db.go
parent88e1b886e5471552c055374f71d848d3a3dcb4b6 (diff)
feat(db): run migrations
Diffstat (limited to 'common/db.go')
-rw-r--r--common/db.go57
1 files changed, 57 insertions, 0 deletions
diff --git a/common/db.go b/common/db.go
new file mode 100644
index 0000000..76e39a2
--- /dev/null
+++ b/common/db.go
@@ -0,0 +1,57 @@
+package common
+
+import (
+ "context"
+ "database/sql"
+ "embed"
+ "fmt"
+ "log/slog"
+ "path"
+ "regexp"
+ "strconv"
+ "strings"
+
+ "github.com/nyttikord/avl"
+)
+
+var regexpMigration = regexp.MustCompile(`(\d{3})-(.*)\.sql`)
+
+type migrationData struct {
+ id uint64
+ name string
+ content string
+}
+
+func Migrate(ctx context.Context, log *slog.Logger, db *sql.DB, migrations embed.FS, dir string) error {
+ entries, err := migrations.ReadDir(dir)
+ if err != nil {
+ return err
+ }
+ tree := avl.NewKeySimple[uint64, migrationData]()
+ for _, entry := range entries {
+ if strings.HasSuffix(entry.Name(), ".sql") {
+ log.Debug("reading migration...", "path", dir+"/"+entry.Name())
+ subs := regexpMigration.FindStringSubmatch(entry.Name())
+ if len(subs) < 3 {
+ return fmt.Errorf("invalid migration name %s", entry.Name())
+ }
+ id, _ := strconv.ParseUint(subs[1], 10, 16)
+ b, err := migrations.ReadFile(path.Join(dir, entry.Name()))
+ if err != nil {
+ return err
+ }
+ tree.Insert(id, migrationData{id, subs[2], string(b)})
+ } else {
+ log.Warn("invalid migration entry, skipping", "path", dir+"/"+entry.Name())
+ }
+ }
+ for _, mig := range tree.Sort() {
+ log.Debug("migrating...", "id", mig.id, "name", mig.name)
+ _, err := db.ExecContext(ctx, mig.content)
+ if err != nil {
+ log.Error("migrating", "id", mig.id, "name", mig.name)
+ return err
+ }
+ }
+ return nil
+}