forked from tangled.org/core
Monorepo for Tangled

spindle: recreate repos table

This new db migration won't migrate existing records in repos table.
Instead, it will simply rename the legacy table to `repos_old` and
create a new one with same name.

repo backfill will be done with tap

Signed-off-by: Seongmin Lee <git@boltless.me>

boltless.me 2f1dddb0 f056c271

verified
Changed files
+46 -5
spindle
+45 -4
spindle/db/db.go
··· 1 package db 2 3 import ( 4 "database/sql" 5 "strings" 6 7 _ "github.com/mattn/go-sqlite3" 8 ) 9 10 type DB struct { 11 *sql.DB 12 } 13 14 - func Make(dbPath string) (*DB, error) { 15 // https://github.com/mattn/go-sqlite3#connection-string 16 opts := []string{ 17 "_foreign_keys=1", ··· 19 "_synchronous=NORMAL", 20 "_auto_vacuum=incremental", 21 } 22 23 db, err := sql.Open("sqlite3", dbPath+"?"+strings.Join(opts, "&")) 24 if err != nil { 25 return nil, err 26 } 27 28 - // NOTE: If any other migration is added here, you MUST 29 - // copy the pattern in appview: use a single sql.Conn 30 - // for every migration. 31 32 _, err = db.Exec(` 33 create table if not exists _jetstream ( ··· 75 if err != nil { 76 return nil, err 77 } 78 79 return &DB{db}, nil 80 }
··· 1 package db 2 3 import ( 4 + "context" 5 "database/sql" 6 "strings" 7 8 _ "github.com/mattn/go-sqlite3" 9 + "tangled.org/core/log" 10 + "tangled.org/core/orm" 11 ) 12 13 type DB struct { 14 *sql.DB 15 } 16 17 + func Make(ctx context.Context, dbPath string) (*DB, error) { 18 // https://github.com/mattn/go-sqlite3#connection-string 19 opts := []string{ 20 "_foreign_keys=1", ··· 22 "_synchronous=NORMAL", 23 "_auto_vacuum=incremental", 24 } 25 + 26 + logger := log.FromContext(ctx) 27 + logger = log.SubLogger(logger, "db") 28 29 db, err := sql.Open("sqlite3", dbPath+"?"+strings.Join(opts, "&")) 30 if err != nil { 31 return nil, err 32 } 33 34 + conn, err := db.Conn(ctx) 35 + if err != nil { 36 + return nil, err 37 + } 38 + defer conn.Close() 39 40 _, err = db.Exec(` 41 create table if not exists _jetstream ( ··· 83 if err != nil { 84 return nil, err 85 } 86 + 87 + // run migrations 88 + 89 + // NOTE: this won't migrate existing records 90 + // they will be fetched again with tap instead 91 + orm.RunMigration(conn, logger, "add-rkey-to-repos", func(tx *sql.Tx) error { 92 + // archive legacy repos (just in case) 93 + _, err = tx.Exec(`alter table repos rename to repos_old`) 94 + if err != nil { 95 + return err 96 + } 97 + 98 + _, err := tx.Exec(` 99 + create table repos_new ( 100 + -- identifiers 101 + id integer primary key autoincrement, 102 + did text not null, 103 + rkey text not null, 104 + at_uri text generated always as ('at://' || did || '/' || 'sh.tangled.repo' || '/' || rkey) stored, 105 + 106 + name text not null, 107 + knot text not null, 108 + 109 + addedAt text not null default (strftime('%Y-%m-%dT%H:%M:%SZ', 'now')), 110 + unique(did, rkey) 111 + ); 112 + `) 113 + if err != nil { 114 + return err 115 + } 116 + 117 + return nil 118 + }) 119 120 return &DB{db}, nil 121 }
+1 -1
spindle/server.go
··· 50 func New(ctx context.Context, cfg *config.Config, engines map[string]models.Engine) (*Spindle, error) { 51 logger := log.FromContext(ctx) 52 53 - d, err := db.Make(cfg.Server.DBPath) 54 if err != nil { 55 return nil, fmt.Errorf("failed to setup db: %w", err) 56 }
··· 50 func New(ctx context.Context, cfg *config.Config, engines map[string]models.Engine) (*Spindle, error) { 51 logger := log.FromContext(ctx) 52 53 + d, err := db.Make(ctx, cfg.Server.DBPath) 54 if err != nil { 55 return nil, fmt.Errorf("failed to setup db: %w", err) 56 }