stash/pkg/database/database.go

100 lines
2.1 KiB
Go
Raw Normal View History

2019-02-09 12:30:49 +00:00
package database
import (
"database/sql"
"errors"
2019-02-09 12:30:49 +00:00
"fmt"
2019-11-14 18:28:17 +00:00
"os"
"regexp"
2019-11-14 18:28:17 +00:00
2019-02-09 12:30:49 +00:00
"github.com/gobuffalo/packr/v2"
"github.com/golang-migrate/migrate/v4"
"github.com/golang-migrate/migrate/v4/source"
"github.com/jmoiron/sqlx"
sqlite3 "github.com/mattn/go-sqlite3"
2019-02-14 23:42:52 +00:00
"github.com/stashapp/stash/pkg/logger"
"github.com/stashapp/stash/pkg/utils"
2019-02-09 12:30:49 +00:00
)
var DB *sqlx.DB
var appSchemaVersion uint = 4
2019-02-09 12:30:49 +00:00
const sqlite3Driver = "sqlite3_regexp"
2019-11-14 18:28:17 +00:00
func init() {
// register custom driver with regexp function
registerRegexpFunc()
2019-11-14 18:28:17 +00:00
}
func Initialize(databasePath string) {
runMigrations(databasePath)
2019-02-09 12:30:49 +00:00
// https://github.com/mattn/go-sqlite3
conn, err := sqlx.Open(sqlite3Driver, "file:"+databasePath+"?_fk=true")
conn.SetMaxOpenConns(25)
conn.SetMaxIdleConns(4)
2019-02-09 12:30:49 +00:00
if err != nil {
logger.Fatalf("db.Open(): %q\n", err)
}
DB = conn
}
func Reset(databasePath string) error {
err := DB.Close()
if err != nil {
return errors.New("Error closing database: " + err.Error())
}
err = os.Remove(databasePath)
if err != nil {
return errors.New("Error removing database: " + err.Error())
}
Initialize(databasePath)
return nil
2019-02-09 12:30:49 +00:00
}
// Migrate the database
func runMigrations(databasePath string) {
migrationsBox := packr.New("Migrations Box", "./migrations")
packrSource := &Packr2Source{
Box: migrationsBox,
Migrations: source.NewMigrations(),
}
2019-02-10 18:13:23 +00:00
databasePath = utils.FixWindowsPath(databasePath)
2019-02-09 12:30:49 +00:00
s, _ := WithInstance(packrSource)
m, err := migrate.NewWithSourceInstance(
"packr2",
s,
fmt.Sprintf("sqlite3://%s", "file:"+databasePath),
2019-02-09 12:30:49 +00:00
)
if err != nil {
panic(err.Error())
}
databaseSchemaVersion, _, _ := m.Version()
stepNumber := appSchemaVersion - databaseSchemaVersion
if stepNumber != 0 {
err = m.Steps(int(stepNumber))
if err != nil {
panic(err.Error())
}
2019-02-09 12:30:49 +00:00
}
m.Close()
}
func registerRegexpFunc() {
regexFn := func(re, s string) (bool, error) {
return regexp.MatchString(re, s)
}
sql.Register(sqlite3Driver,
&sqlite3.SQLiteDriver{
ConnectHook: func(conn *sqlite3.SQLiteConn) error {
return conn.RegisterFunc("regexp", regexFn, true)
},
})
}