2021-07-06 22:44:11 +02:00
|
|
|
package sqlstore
|
|
|
|
|
|
|
|
import (
|
|
|
|
"database/sql"
|
2022-04-25 17:43:06 +02:00
|
|
|
"encoding/json"
|
2021-12-17 18:30:47 +01:00
|
|
|
"fmt"
|
2022-03-24 22:45:10 +01:00
|
|
|
"io/ioutil"
|
2021-12-17 18:30:47 +01:00
|
|
|
"os"
|
|
|
|
"strings"
|
2021-07-06 22:44:11 +02:00
|
|
|
|
2022-03-22 15:24:34 +01:00
|
|
|
"github.com/mattermost/focalboard/server/model"
|
2021-12-17 18:30:47 +01:00
|
|
|
"github.com/mattermost/focalboard/server/utils"
|
2021-12-10 16:46:37 +01:00
|
|
|
|
2021-08-25 22:08:01 +02:00
|
|
|
"github.com/mattermost/mattermost-server/v6/shared/mlog"
|
2021-07-06 22:44:11 +02:00
|
|
|
)
|
|
|
|
|
|
|
|
func (s *SQLStore) CloseRows(rows *sql.Rows) {
|
|
|
|
if err := rows.Close(); err != nil {
|
|
|
|
s.logger.Error("error closing MattermostAuthLayer row set", mlog.Err(err))
|
|
|
|
}
|
|
|
|
}
|
2021-12-10 16:46:37 +01:00
|
|
|
|
|
|
|
func (s *SQLStore) IsErrNotFound(err error) bool {
|
2022-04-20 17:02:12 +02:00
|
|
|
return model.IsErrNotFound(err)
|
2021-12-10 16:46:37 +01:00
|
|
|
}
|
2021-12-17 18:30:47 +01:00
|
|
|
|
2022-06-15 12:17:44 +02:00
|
|
|
func (s *SQLStore) IsErrNotAllFound(err error) bool {
|
|
|
|
return model.IsErrNotAllFound(err)
|
|
|
|
}
|
|
|
|
|
2022-04-25 17:43:06 +02:00
|
|
|
func (s *SQLStore) MarshalJSONB(data interface{}) ([]byte, error) {
|
|
|
|
b, err := json.Marshal(data)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
if s.isBinaryParam {
|
|
|
|
b = append([]byte{0x01}, b...)
|
|
|
|
}
|
|
|
|
|
|
|
|
return b, nil
|
|
|
|
}
|
|
|
|
|
2021-12-17 18:30:47 +01:00
|
|
|
func PrepareNewTestDatabase() (dbType string, connectionString string, err error) {
|
2022-05-05 21:49:34 +02:00
|
|
|
dbType = strings.TrimSpace(os.Getenv("FOCALBOARD_STORE_TEST_DB_TYPE"))
|
2021-12-17 18:30:47 +01:00
|
|
|
if dbType == "" {
|
2022-03-22 15:24:34 +01:00
|
|
|
dbType = model.SqliteDBType
|
2021-12-17 18:30:47 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
var dbName string
|
|
|
|
var rootUser string
|
|
|
|
|
2022-03-22 15:24:34 +01:00
|
|
|
if dbType == model.SqliteDBType {
|
2022-03-24 22:45:10 +01:00
|
|
|
file, err := ioutil.TempFile("", "fbtest_*.db")
|
|
|
|
if err != nil {
|
|
|
|
return "", "", err
|
|
|
|
}
|
|
|
|
connectionString = file.Name() + "?_busy_timeout=5000"
|
|
|
|
_ = file.Close()
|
2022-05-05 21:49:34 +02:00
|
|
|
} else if port := strings.TrimSpace(os.Getenv("FOCALBOARD_STORE_TEST_DOCKER_PORT")); port != "" {
|
2021-12-17 18:30:47 +01:00
|
|
|
// docker unit tests take priority over any DSN env vars
|
|
|
|
var template string
|
|
|
|
switch dbType {
|
2022-03-22 15:24:34 +01:00
|
|
|
case model.MysqlDBType:
|
2021-12-17 18:30:47 +01:00
|
|
|
template = "%s:mostest@tcp(localhost:%s)/%s?charset=utf8mb4,utf8&writeTimeout=30s"
|
|
|
|
rootUser = "root"
|
2022-03-22 15:24:34 +01:00
|
|
|
case model.PostgresDBType:
|
2021-12-17 18:30:47 +01:00
|
|
|
template = "postgres://%s:mostest@localhost:%s/%s?sslmode=disable\u0026connect_timeout=10"
|
|
|
|
rootUser = "mmuser"
|
|
|
|
default:
|
|
|
|
return "", "", newErrInvalidDBType(dbType)
|
|
|
|
}
|
|
|
|
|
|
|
|
connectionString = fmt.Sprintf(template, rootUser, port, "")
|
|
|
|
|
|
|
|
// create a new database each run
|
|
|
|
sqlDB, err := sql.Open(dbType, connectionString)
|
|
|
|
if err != nil {
|
|
|
|
return "", "", fmt.Errorf("cannot connect to %s database: %w", dbType, err)
|
|
|
|
}
|
|
|
|
defer sqlDB.Close()
|
|
|
|
|
|
|
|
err = sqlDB.Ping()
|
|
|
|
if err != nil {
|
|
|
|
return "", "", fmt.Errorf("cannot ping %s database: %w", dbType, err)
|
|
|
|
}
|
|
|
|
|
|
|
|
dbName = "testdb_" + utils.NewID(utils.IDTypeNone)[:8]
|
|
|
|
_, err = sqlDB.Exec(fmt.Sprintf("CREATE DATABASE %s;", dbName))
|
|
|
|
if err != nil {
|
|
|
|
return "", "", fmt.Errorf("cannot create %s database %s: %w", dbType, dbName, err)
|
|
|
|
}
|
|
|
|
|
2022-03-22 15:24:34 +01:00
|
|
|
if dbType != model.PostgresDBType {
|
2021-12-17 18:30:47 +01:00
|
|
|
_, err = sqlDB.Exec(fmt.Sprintf("GRANT ALL PRIVILEGES ON %s.* TO mmuser;", dbName))
|
|
|
|
if err != nil {
|
|
|
|
return "", "", fmt.Errorf("cannot grant permissions on %s database %s: %w", dbType, dbName, err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
connectionString = fmt.Sprintf(template, "mmuser", port, dbName)
|
|
|
|
} else {
|
|
|
|
// mysql or postgres need a DSN (connection string)
|
2022-05-05 21:49:34 +02:00
|
|
|
connectionString = strings.TrimSpace(os.Getenv("FOCALBOARD_STORE_TEST_CONN_STRING"))
|
2021-12-17 18:30:47 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
return dbType, connectionString, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
type ErrInvalidDBType struct {
|
|
|
|
dbType string
|
|
|
|
}
|
|
|
|
|
|
|
|
func newErrInvalidDBType(dbType string) error {
|
|
|
|
return ErrInvalidDBType{
|
|
|
|
dbType: dbType,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func (e ErrInvalidDBType) Error() string {
|
|
|
|
return "unsupported database type: " + e.dbType
|
|
|
|
}
|