mirror of
https://github.com/Team254/cheesy-arena-lite.git
synced 2026-03-09 21:56:50 -04:00
Refactor database models into separate package.
This commit is contained in:
135
model/database.go
Normal file
135
model/database.go
Normal file
@@ -0,0 +1,135 @@
|
||||
// Copyright 2014 Team 254. All Rights Reserved.
|
||||
// Author: pat@patfairbank.com (Patrick Fairbank)
|
||||
//
|
||||
// Functions for manipulating the per-event SQLite datastore.
|
||||
|
||||
package model
|
||||
|
||||
import (
|
||||
"bitbucket.org/liamstask/goose/lib/goose"
|
||||
"database/sql"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"github.com/jmoiron/modl"
|
||||
_ "github.com/mattn/go-sqlite3"
|
||||
"io"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
const backupsDir = "db/backups"
|
||||
const migrationsDir = "db/migrations"
|
||||
|
||||
type Database struct {
|
||||
baseDir string
|
||||
filename string
|
||||
db *sql.DB
|
||||
eventSettingsMap *modl.DbMap
|
||||
matchMap *modl.DbMap
|
||||
matchResultMap *modl.DbMap
|
||||
rankingMap *modl.DbMap
|
||||
teamMap *modl.DbMap
|
||||
allianceTeamMap *modl.DbMap
|
||||
lowerThirdMap *modl.DbMap
|
||||
sponsorSlideMap *modl.DbMap
|
||||
}
|
||||
|
||||
// Opens the SQLite database at the given path, creating it if it doesn't exist, and runs any pending
|
||||
// migrations.
|
||||
func OpenDatabase(baseDir, filename string) (*Database, error) {
|
||||
// Find and run the migrations using goose. This also auto-creates the DB.
|
||||
database := Database{baseDir: baseDir, filename: filename}
|
||||
migrationsPath := filepath.Join(baseDir, migrationsDir)
|
||||
dbDriver := goose.DBDriver{"sqlite3", database.GetPath(), "github.com/mattn/go-sqlite3", &goose.Sqlite3Dialect{}}
|
||||
dbConf := goose.DBConf{MigrationsDir: migrationsPath, Env: "prod", Driver: dbDriver}
|
||||
target, err := goose.GetMostRecentDBVersion(migrationsPath)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
err = goose.RunMigrations(&dbConf, migrationsPath, target)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
db, err := sql.Open("sqlite3", database.GetPath())
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
database.db = db
|
||||
database.mapTables()
|
||||
|
||||
return &database, nil
|
||||
}
|
||||
|
||||
func (database *Database) Close() {
|
||||
database.db.Close()
|
||||
}
|
||||
|
||||
// Creates a copy of the current database and saves it to the backups directory.
|
||||
func (database *Database) Backup(eventName, reason string) error {
|
||||
backupsPath := filepath.Join(database.baseDir, backupsDir)
|
||||
err := os.MkdirAll(backupsPath, 0755)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
filename := fmt.Sprintf("%s/%s_%s_%s.db", backupsPath, strings.Replace(eventName, " ", "_", -1),
|
||||
time.Now().Format("20060102150405"), reason)
|
||||
src, err := os.Open(database.GetPath())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer src.Close()
|
||||
dest, err := os.Create(filename)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer dest.Close()
|
||||
if _, err := io.Copy(dest, src); err != nil {
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (database *Database) GetPath() string {
|
||||
return filepath.Join(database.baseDir, database.filename)
|
||||
}
|
||||
|
||||
// Sets up table-object associations.
|
||||
func (database *Database) mapTables() {
|
||||
dialect := new(modl.SqliteDialect)
|
||||
|
||||
database.eventSettingsMap = modl.NewDbMap(database.db, dialect)
|
||||
database.eventSettingsMap.AddTableWithName(EventSettings{}, "event_settings").SetKeys(false, "Id")
|
||||
|
||||
database.matchMap = modl.NewDbMap(database.db, dialect)
|
||||
database.matchMap.AddTableWithName(Match{}, "matches").SetKeys(true, "Id")
|
||||
|
||||
database.matchResultMap = modl.NewDbMap(database.db, dialect)
|
||||
database.matchResultMap.AddTableWithName(MatchResultDb{}, "match_results").SetKeys(true, "Id")
|
||||
|
||||
database.rankingMap = modl.NewDbMap(database.db, dialect)
|
||||
database.rankingMap.AddTableWithName(RankingDb{}, "rankings").SetKeys(false, "TeamId")
|
||||
|
||||
database.teamMap = modl.NewDbMap(database.db, dialect)
|
||||
database.teamMap.AddTableWithName(Team{}, "teams").SetKeys(false, "Id")
|
||||
|
||||
database.allianceTeamMap = modl.NewDbMap(database.db, dialect)
|
||||
database.allianceTeamMap.AddTableWithName(AllianceTeam{}, "alliance_teams").SetKeys(true, "Id")
|
||||
|
||||
database.lowerThirdMap = modl.NewDbMap(database.db, dialect)
|
||||
database.lowerThirdMap.AddTableWithName(LowerThird{}, "lower_thirds").SetKeys(true, "Id")
|
||||
|
||||
database.sponsorSlideMap = modl.NewDbMap(database.db, dialect)
|
||||
database.sponsorSlideMap.AddTableWithName(SponsorSlide{}, "sponsor_slides").SetKeys(true, "Id")
|
||||
}
|
||||
|
||||
func serializeHelper(target *string, source interface{}) error {
|
||||
bytes, err := json.Marshal(source)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
*target = string(bytes)
|
||||
return nil
|
||||
}
|
||||
Reference in New Issue
Block a user