github.com/mantzas/incata@v0.3.0/storage/storage.go (about) 1 package storage 2 3 import ( 4 "database/sql" 5 "fmt" 6 "strings" 7 ) 8 9 // DbType defines the type of the db 10 type DbType int 11 12 // Relational Db Types 13 const ( 14 MSSQL DbType = iota // MS SQL Server 15 PostgreSQL // Postgresql 16 ) 17 18 var dbTypeMap = map[string]DbType{ 19 "mssql": MSSQL, 20 "postgresql": PostgreSQL, 21 } 22 23 // ConvertToDbType convert's a string to a DbType 24 func ConvertToDbType(value string) (DbType, error) { 25 26 dbType, ok := dbTypeMap[strings.ToLower(value)] 27 28 if ok { 29 return dbType, nil 30 } 31 32 return 0, fmt.Errorf("Failed to convert %s to db type", value) 33 } 34 35 // Storage a db abstraction 36 type Storage struct { 37 innerDb *sql.DB 38 DbType DbType 39 AppendStatement string 40 SelectBySourceIDStatement string 41 } 42 43 // Exec executes sql statement 44 func (db *Storage) Exec(query string, args ...interface{}) (*sql.Result, error) { 45 result, err := db.innerDb.Exec(query, args...) 46 return &result, err 47 } 48 49 // Query executes a query statement 50 func (db *Storage) Query(query string, args ...interface{}) (*sql.Rows, error) { 51 rows, err := db.innerDb.Query(query, args...) 52 return rows, err 53 } 54 55 // Close close db 56 func (db *Storage) Close() (err error) { 57 err = db.innerDb.Close() 58 return 59 } 60 61 // NewStorage creates a new storage 62 func NewStorage(dbType DbType, connection string, tableName string) (*Storage, error) { 63 64 driver, appendStmt, selectStmt, err := getStatements(dbType, tableName) 65 if err != nil { 66 return nil, err 67 } 68 69 db, err := sql.Open(driver, connection) 70 if err != nil { 71 return nil, err 72 } 73 74 if err = db.Ping(); err != nil { 75 db.Close() 76 return nil, err 77 } 78 79 storage := &Storage{ 80 innerDb: db, 81 DbType: dbType, 82 AppendStatement: appendStmt, 83 SelectBySourceIDStatement: selectStmt, 84 } 85 return storage, nil 86 } 87 88 // NewStorageFinalized creates a new storage with a passed in db argument 89 func NewStorageFinalized(db *sql.DB, dbType DbType, tableName string) (*Storage, error) { 90 91 _, appendStmt, selectStmt, err := getStatements(dbType, tableName) 92 if err != nil { 93 return nil, err 94 } 95 96 storage := &Storage{ 97 innerDb: db, 98 DbType: dbType, 99 AppendStatement: appendStmt, 100 SelectBySourceIDStatement: selectStmt, 101 } 102 return storage, nil 103 } 104 105 func getStatements(dbType DbType, tableName string) (string, string, string, error) { 106 107 switch dbType { 108 109 case MSSQL: 110 return "mssql", fmt.Sprintf("INSERT INTO %s (SourceId, Created, EventType, Version, Payload) VALUES (?, ?, ?, ?, ?)", tableName), 111 fmt.Sprintf("SELECT Id, CAST(SourceId AS CHAR(36)), Created, EventType, Version, Payload FROM %s WHERE SourceId = ?", tableName), nil 112 113 case PostgreSQL: 114 return "postgres", fmt.Sprintf(`INSERT INTO %s ("SourceId", "Created", "EventType", "Version", "Payload") VALUES ($1, $2, $3, $4, $5)`, tableName), 115 fmt.Sprintf(`SELECT "Id", "SourceId", "Created", "EventType", "Version", "Payload" FROM %s WHERE "SourceId" = $1`, tableName), nil 116 117 default: 118 return "", "", "", fmt.Errorf("DB type %d is not supported", dbType) 119 } 120 }