mirror of https://github.com/statping/statping
gorm DB - issue fixes - DB seeds - benchmark tests
parent
e4ccdba34d
commit
1eb55a0c71
|
@ -12,6 +12,14 @@
|
||||||
pruneopts = "UT"
|
pruneopts = "UT"
|
||||||
revision = "c02ca9a983da5807ddf7d796784928f5be4afd09"
|
revision = "c02ca9a983da5807ddf7d796784928f5be4afd09"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
digest = "1:e92f5581902c345eb4ceffdcd4a854fb8f73cf436d47d837d1ec98ef1fe0a214"
|
||||||
|
name = "github.com/StackExchange/wmi"
|
||||||
|
packages = ["."]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "5d049714c4a64225c3c79a7cf7d02f7fb5b96338"
|
||||||
|
version = "1.0.0"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
branch = "master"
|
branch = "master"
|
||||||
digest = "1:4b79025e1eaa5726b92e409a46571f1998b56f0a2d881d6271ca616095eae46e"
|
digest = "1:4b79025e1eaa5726b92e409a46571f1998b56f0a2d881d6271ca616095eae46e"
|
||||||
|
@ -44,6 +52,17 @@
|
||||||
pruneopts = "UT"
|
pruneopts = "UT"
|
||||||
revision = "ebf56d35bba727c68ac77f56f2fcf90b181851aa"
|
revision = "ebf56d35bba727c68ac77f56f2fcf90b181851aa"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
digest = "1:64a5a67c69b70c2420e607a8545d674a23778ed9c3e80607bfd17b77c6c87f6a"
|
||||||
|
name = "github.com/go-ole/go-ole"
|
||||||
|
packages = [
|
||||||
|
".",
|
||||||
|
"oleutil",
|
||||||
|
]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "a41e3c4b706f6ae8dfbff342b06e40fa4d2d0506"
|
||||||
|
version = "v1.2.1"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
branch = "master"
|
branch = "master"
|
||||||
digest = "1:70a20b8adf085489a342d033b68b7fc27f4017c51e015b857387249493ee0561"
|
digest = "1:70a20b8adf085489a342d033b68b7fc27f4017c51e015b857387249493ee0561"
|
||||||
|
@ -68,6 +87,14 @@
|
||||||
revision = "08b5f424b9271eedf6f9f0ce86cb9396ed337a42"
|
revision = "08b5f424b9271eedf6f9f0ce86cb9396ed337a42"
|
||||||
version = "v1.1.1"
|
version = "v1.1.1"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
digest = "1:664d37ea261f0fc73dd17f4a1f5f46d01fbb0b0d75f6375af064824424109b7d"
|
||||||
|
name = "github.com/gorilla/handlers"
|
||||||
|
packages = ["."]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "7e0847f9db758cdebd26c149d0ae9d5d0b9c98ce"
|
||||||
|
version = "v1.4.0"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
digest = "1:195b71563f8432dac9d9692aca2a9ae098bc35763999573eb1c7d52a02a47ce7"
|
digest = "1:195b71563f8432dac9d9692aca2a9ae098bc35763999573eb1c7d52a02a47ce7"
|
||||||
name = "github.com/gorilla/mux"
|
name = "github.com/gorilla/mux"
|
||||||
|
@ -91,6 +118,14 @@
|
||||||
revision = "03b6f63cc43ef9c7240a635a5e22b13180e822b8"
|
revision = "03b6f63cc43ef9c7240a635a5e22b13180e822b8"
|
||||||
version = "v1.1.1"
|
version = "v1.1.1"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
digest = "1:7b5c6e2eeaa9ae5907c391a91c132abfd5c9e8a784a341b5625e750c67e6825d"
|
||||||
|
name = "github.com/gorilla/websocket"
|
||||||
|
packages = ["."]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "66b9c49e59c6c48f0ffce28c2d8b8a5678502c6d"
|
||||||
|
version = "v1.4.0"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
branch = "master"
|
branch = "master"
|
||||||
digest = "1:d166a4b3543a71d87e34767ace94e8b516e79ba45111730306f07c8d6f797f1f"
|
digest = "1:d166a4b3543a71d87e34767ace94e8b516e79ba45111730306f07c8d6f797f1f"
|
||||||
|
@ -126,6 +161,17 @@
|
||||||
pruneopts = "UT"
|
pruneopts = "UT"
|
||||||
revision = "b3511bfdd742af558b54eb6160aca9446d762a19"
|
revision = "b3511bfdd742af558b54eb6160aca9446d762a19"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
branch = "master"
|
||||||
|
digest = "1:4f4fd75cbdd5ad0696f4d762328f094b9c86061323c9a9f8d0de157f06197e89"
|
||||||
|
name = "github.com/mkevac/debugcharts"
|
||||||
|
packages = [
|
||||||
|
".",
|
||||||
|
"bindata",
|
||||||
|
]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "d3203a8fa92649b82dc35c214979861de918874a"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
branch = "master"
|
branch = "master"
|
||||||
digest = "1:3891cc78541df6e4596b3e73978eb062d32967084069270ec881b959be5155ae"
|
digest = "1:3891cc78541df6e4596b3e73978eb062d32967084069270ec881b959be5155ae"
|
||||||
|
@ -150,6 +196,29 @@
|
||||||
pruneopts = "UT"
|
pruneopts = "UT"
|
||||||
revision = "6283090d169f51a2410b4e260341a01c9a4c0ca7"
|
revision = "6283090d169f51a2410b4e260341a01c9a4c0ca7"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
digest = "1:7395b855a6078ad2e6c40311402a057a91125fb9f32cf228e1b32cdc57c33538"
|
||||||
|
name = "github.com/shirou/gopsutil"
|
||||||
|
packages = [
|
||||||
|
"cpu",
|
||||||
|
"host",
|
||||||
|
"internal/common",
|
||||||
|
"mem",
|
||||||
|
"net",
|
||||||
|
"process",
|
||||||
|
]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "8048a2e9c5773235122027dd585cf821b2af1249"
|
||||||
|
version = "v2.18.07"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
branch = "master"
|
||||||
|
digest = "1:99c6a6dab47067c9b898e8c8b13d130c6ab4ffbcc4b7cc6236c2cd0b1e344f5b"
|
||||||
|
name = "github.com/shirou/w32"
|
||||||
|
packages = ["."]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "bb4de0191aa41b5507caa14b0650cdbddcd9280b"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
digest = "1:18752d0b95816a1b777505a97f71c7467a8445b8ffb55631a7bf779f6ba4fa83"
|
digest = "1:18752d0b95816a1b777505a97f71c7467a8445b8ffb55631a7bf779f6ba4fa83"
|
||||||
name = "github.com/stretchr/testify"
|
name = "github.com/stretchr/testify"
|
||||||
|
@ -168,6 +237,17 @@
|
||||||
pruneopts = "UT"
|
pruneopts = "UT"
|
||||||
revision = "c126467f60eb25f8f27e5a981f32a87e3965053f"
|
revision = "c126467f60eb25f8f27e5a981f32a87e3965053f"
|
||||||
|
|
||||||
|
[[projects]]
|
||||||
|
branch = "master"
|
||||||
|
digest = "1:629034aef6b53eb8ea737e6d82cb5402907e2757fbab5ddf5e74c08b4c6473af"
|
||||||
|
name = "golang.org/x/sys"
|
||||||
|
packages = [
|
||||||
|
"unix",
|
||||||
|
"windows",
|
||||||
|
]
|
||||||
|
pruneopts = "UT"
|
||||||
|
revision = "fa5fdf94c78965f1aa8423f0cc50b8b8d728b05a"
|
||||||
|
|
||||||
[[projects]]
|
[[projects]]
|
||||||
digest = "1:c25289f43ac4a68d88b02245742347c94f1e108c534dda442188015ff80669b3"
|
digest = "1:c25289f43ac4a68d88b02245742347c94f1e108c534dda442188015ff80669b3"
|
||||||
name = "google.golang.org/appengine"
|
name = "google.golang.org/appengine"
|
||||||
|
@ -230,9 +310,11 @@
|
||||||
"github.com/ararog/timeago",
|
"github.com/ararog/timeago",
|
||||||
"github.com/fatih/structs",
|
"github.com/fatih/structs",
|
||||||
"github.com/go-yaml/yaml",
|
"github.com/go-yaml/yaml",
|
||||||
|
"github.com/gorilla/handlers",
|
||||||
"github.com/gorilla/mux",
|
"github.com/gorilla/mux",
|
||||||
"github.com/gorilla/sessions",
|
"github.com/gorilla/sessions",
|
||||||
"github.com/joho/godotenv",
|
"github.com/joho/godotenv",
|
||||||
|
"github.com/mkevac/debugcharts",
|
||||||
"github.com/pkg/errors",
|
"github.com/pkg/errors",
|
||||||
"github.com/rendon/testcli",
|
"github.com/rendon/testcli",
|
||||||
"github.com/stretchr/testify/assert",
|
"github.com/stretchr/testify/assert",
|
||||||
|
|
6
Makefile
6
Makefile
|
@ -1,4 +1,4 @@
|
||||||
VERSION=0.52
|
VERSION=0.53
|
||||||
BINARY_NAME=statup
|
BINARY_NAME=statup
|
||||||
GOPATH:=$(GOPATH)
|
GOPATH:=$(GOPATH)
|
||||||
GOCMD=go
|
GOCMD=go
|
||||||
|
@ -26,6 +26,10 @@ docker-build-all: docker-build-base docker-dev docker
|
||||||
|
|
||||||
docker-publish-all: docker-push-base docker-push-dev docker-push-latest
|
docker-publish-all: docker-push-base docker-push-dev docker-push-latest
|
||||||
|
|
||||||
|
seed:
|
||||||
|
rm -f statup.db
|
||||||
|
cat dev/seed.sql | sqlite3 statup.db
|
||||||
|
|
||||||
build: compile
|
build: compile
|
||||||
$(GOBUILD) $(BUILDVERSION) -o $(BINARY_NAME) -v ./cmd
|
$(GOBUILD) $(BUILDVERSION) -o $(BINARY_NAME) -v ./cmd
|
||||||
|
|
||||||
|
|
21
cmd/cli.go
21
cmd/cli.go
|
@ -24,13 +24,13 @@ import (
|
||||||
"github.com/hunterlong/statup/source"
|
"github.com/hunterlong/statup/source"
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
|
"github.com/jinzhu/gorm"
|
||||||
"github.com/joho/godotenv"
|
"github.com/joho/godotenv"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"math/rand"
|
"math/rand"
|
||||||
"net/http"
|
"net/http"
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
"upper.io/db.v3/sqlite"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
@ -45,6 +45,8 @@ func CatchCLI(args []string) error {
|
||||||
LoadDotEnvs()
|
LoadDotEnvs()
|
||||||
|
|
||||||
switch args[0] {
|
switch args[0] {
|
||||||
|
case "seed":
|
||||||
|
handlers.DesktopInit(ipAddress, port)
|
||||||
case "app":
|
case "app":
|
||||||
handlers.DesktopInit(ipAddress, port)
|
handlers.DesktopInit(ipAddress, port)
|
||||||
case "version":
|
case "version":
|
||||||
|
@ -94,7 +96,7 @@ func CatchCLI(args []string) error {
|
||||||
case "export":
|
case "export":
|
||||||
var err error
|
var err error
|
||||||
fmt.Printf("Statup v%v Exporting Static 'index.html' page...\n", VERSION)
|
fmt.Printf("Statup v%v Exporting Static 'index.html' page...\n", VERSION)
|
||||||
core.Configs, err = core.LoadConfig()
|
core.Configs, err = core.LoadConfig(dir)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, "config.yml file not found")
|
utils.Log(4, "config.yml file not found")
|
||||||
return err
|
return err
|
||||||
|
@ -132,11 +134,11 @@ func CatchCLI(args []string) error {
|
||||||
|
|
||||||
func RunOnce() {
|
func RunOnce() {
|
||||||
var err error
|
var err error
|
||||||
core.Configs, err = core.LoadConfig()
|
core.Configs, err = core.LoadConfig(utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, "config.yml file not found")
|
utils.Log(4, "config.yml file not found")
|
||||||
}
|
}
|
||||||
err = core.DbConnection(core.Configs.Connection, false, utils.Directory)
|
err = core.Configs.Connect(false, utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, err)
|
utils.Log(4, err)
|
||||||
}
|
}
|
||||||
|
@ -234,19 +236,16 @@ func FakeSeed(plug types.PluginActions) {
|
||||||
fmt.Printf("\n" + BRAKER)
|
fmt.Printf("\n" + BRAKER)
|
||||||
|
|
||||||
fmt.Println("\nCreating a SQLite database for testing, will be deleted automatically...")
|
fmt.Println("\nCreating a SQLite database for testing, will be deleted automatically...")
|
||||||
sqlFake := sqlite.ConnectionURL{
|
core.DbSession, err = gorm.Open("sqlite", "./.plugin_test.db")
|
||||||
Database: "./.plugin_test.db",
|
|
||||||
}
|
|
||||||
core.DbSession, err = sqlite.Open(sqlFake)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
}
|
}
|
||||||
up, _ := source.SqlBox.String("sqlite_up.sql")
|
up, _ := source.SqlBox.String("sqlite_up.sql")
|
||||||
requests := strings.Split(up, ";")
|
requests := strings.Split(up, ";")
|
||||||
for _, request := range requests {
|
for _, request := range requests {
|
||||||
_, err := core.DbSession.Exec(request)
|
db := core.DbSession.Exec(request)
|
||||||
if err != nil {
|
if db.Error != nil {
|
||||||
utils.Log(2, err)
|
utils.Log(2, db.Error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
20
cmd/main.go
20
cmd/main.go
|
@ -55,6 +55,8 @@ func parseFlags() {
|
||||||
func main() {
|
func main() {
|
||||||
var err error
|
var err error
|
||||||
parseFlags()
|
parseFlags()
|
||||||
|
LoadDotEnvs()
|
||||||
|
source.Assets()
|
||||||
utils.InitLogs()
|
utils.InitLogs()
|
||||||
args := flag.Args()
|
args := flag.Args()
|
||||||
|
|
||||||
|
@ -68,13 +70,8 @@ func main() {
|
||||||
os.Exit(1)
|
os.Exit(1)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
source.Assets()
|
|
||||||
LoadDotEnvs()
|
|
||||||
|
|
||||||
utils.Log(1, fmt.Sprintf("Starting Statup v%v", VERSION))
|
utils.Log(1, fmt.Sprintf("Starting Statup v%v", VERSION))
|
||||||
|
core.Configs, err = core.LoadConfig(utils.Directory)
|
||||||
core.Configs, err = core.LoadConfig()
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
core.SetupMode = true
|
core.SetupMode = true
|
||||||
|
@ -94,15 +91,18 @@ func LoadDotEnvs() error {
|
||||||
}
|
}
|
||||||
|
|
||||||
func mainProcess() {
|
func mainProcess() {
|
||||||
|
dir := utils.Directory
|
||||||
var err error
|
var err error
|
||||||
err = core.DbConnection(core.Configs.Connection, false, utils.Directory)
|
core.Configs, err = core.LoadConfig(dir)
|
||||||
|
if err != nil {
|
||||||
|
utils.Log(4, fmt.Sprintf("could not load config.yml %v", err))
|
||||||
|
}
|
||||||
|
err = core.Configs.Connect(false, dir)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, fmt.Sprintf("could not connect to database: %v", err))
|
utils.Log(4, fmt.Sprintf("could not connect to database: %v", err))
|
||||||
}
|
}
|
||||||
|
|
||||||
core.RunDatabaseUpgrades()
|
core.RunDatabaseUpgrades()
|
||||||
core.InitApp()
|
core.InitApp()
|
||||||
|
|
||||||
if !core.SetupMode {
|
if !core.SetupMode {
|
||||||
LoadPlugins(false)
|
LoadPlugins(false)
|
||||||
fmt.Println(handlers.RunHTTPServer(ipAddress, port))
|
fmt.Println(handlers.RunHTTPServer(ipAddress, port))
|
||||||
|
@ -170,7 +170,7 @@ func LoadPlugins(debug bool) {
|
||||||
if debug {
|
if debug {
|
||||||
TestPlugin(plugActions)
|
TestPlugin(plugActions)
|
||||||
} else {
|
} else {
|
||||||
plugActions.OnLoad(core.DbSession)
|
plugActions.OnLoad(*core.DbSession)
|
||||||
core.CoreApp.Plugins = append(core.CoreApp.Plugins, plugActions.GetInfo())
|
core.CoreApp.Plugins = append(core.CoreApp.Plugins, plugActions.GetInfo())
|
||||||
core.CoreApp.AllPlugins = append(core.CoreApp.AllPlugins, plugActions)
|
core.CoreApp.AllPlugins = append(core.CoreApp.AllPlugins, plugActions)
|
||||||
}
|
}
|
||||||
|
|
176
cmd/main_test.go
176
cmd/main_test.go
|
@ -31,27 +31,30 @@ import (
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
route *mux.Router
|
route *mux.Router
|
||||||
testSession *sessions.Session
|
testSession *sessions.Session
|
||||||
dir string
|
dir string
|
||||||
|
SERVICE_SINCE, _ = time.Parse(time.RFC3339, "2018-08-30T10:42:08-07:00")
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
dir = utils.Directory
|
dir = utils.Directory
|
||||||
os.Remove(dir + "/statup.db")
|
}
|
||||||
//os.Remove(gopath+"/cmd/config.yml")
|
|
||||||
os.RemoveAll(dir + "/cmd/assets")
|
func Clean() {
|
||||||
os.RemoveAll(dir + "/logs")
|
utils.DeleteFile(dir + "/config.yml")
|
||||||
|
utils.DeleteFile(dir + "/statup.db")
|
||||||
|
utils.DeleteDirectory(dir + "/assets")
|
||||||
|
utils.DeleteDirectory(dir + "/logs")
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunInit(t *testing.T) {
|
func RunInit(t *testing.T) {
|
||||||
source.Assets()
|
source.Assets()
|
||||||
os.Remove(dir + "/statup.db")
|
Clean()
|
||||||
os.Remove(dir + "/cmd/config.yml")
|
|
||||||
os.Remove(dir + "/cmd/index.html")
|
|
||||||
route = handlers.Router()
|
route = handlers.Router()
|
||||||
LoadDotEnvs()
|
LoadDotEnvs()
|
||||||
core.CoreApp = core.NewCore()
|
core.CoreApp = core.NewCore()
|
||||||
|
@ -60,35 +63,56 @@ func RunInit(t *testing.T) {
|
||||||
func TestRunAll(t *testing.T) {
|
func TestRunAll(t *testing.T) {
|
||||||
//t.Parallel()
|
//t.Parallel()
|
||||||
|
|
||||||
databases := []string{"sqlite", "postgres", "mysql"}
|
databases := []string{"postgres", "sqlite", "mysql"}
|
||||||
if os.Getenv("ONLY_DB") != "" {
|
if os.Getenv("ONLY_DB") != "" {
|
||||||
databases = []string{os.Getenv("ONLY_DB")}
|
databases = []string{os.Getenv("ONLY_DB")}
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, dbt := range databases {
|
for _, dbt := range databases {
|
||||||
|
|
||||||
t.Run(dbt+" init", func(t *testing.T) {
|
t.Run(dbt+" init", func(t *testing.T) {
|
||||||
RunInit(t)
|
RunInit(t)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" load database config", func(t *testing.T) {
|
t.Run(dbt+" Save Config", func(t *testing.T) {
|
||||||
RunMakeDatabaseConfig(t, dbt)
|
RunSaveConfig(t, dbt)
|
||||||
})
|
|
||||||
t.Run(dbt+" run database migrations", func(t *testing.T) {
|
|
||||||
RunDatabaseMigrations(t, dbt)
|
|
||||||
})
|
|
||||||
t.Run(dbt+" Sample Data", func(t *testing.T) {
|
|
||||||
RunInsertSampleData(t)
|
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Load Configs", func(t *testing.T) {
|
t.Run(dbt+" Load Configs", func(t *testing.T) {
|
||||||
RunLoadConfig(t)
|
RunLoadConfig(t)
|
||||||
|
t.Log(core.Configs)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Connect to Database", func(t *testing.T) {
|
||||||
|
err := core.Configs.Connect(false, dir)
|
||||||
|
assert.Nil(t, err)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Drop Database", func(t *testing.T) {
|
||||||
|
RunDropDatabase(t)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Connect to Database Again", func(t *testing.T) {
|
||||||
|
err := core.Configs.Connect(false, dir)
|
||||||
|
assert.Nil(t, err)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Inserting Database Structure", func(t *testing.T) {
|
||||||
|
RunCreateSchema(t, dbt)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Inserting Seed Data", func(t *testing.T) {
|
||||||
|
RunInsertSampleData(t)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Connect to Database Again", func(t *testing.T) {
|
||||||
|
err := core.Configs.Connect(false, dir)
|
||||||
|
assert.Nil(t, err)
|
||||||
|
})
|
||||||
|
t.Run(dbt+" Run Database Migrations", func(t *testing.T) {
|
||||||
|
t.SkipNow()
|
||||||
|
RunDatabaseMigrations(t, dbt)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Select Core", func(t *testing.T) {
|
t.Run(dbt+" Select Core", func(t *testing.T) {
|
||||||
RunSelectCoreMYQL(t, dbt)
|
RunSelectCoreMYQL(t, dbt)
|
||||||
|
t.Log(core.CoreApp)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Select Services", func(t *testing.T) {
|
t.Run(dbt+" Select Services", func(t *testing.T) {
|
||||||
RunSelectAllMysqlServices(t)
|
RunSelectAllMysqlServices(t)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Select Comms", func(t *testing.T) {
|
t.Run(dbt+" Select Comms", func(t *testing.T) {
|
||||||
|
t.SkipNow()
|
||||||
RunSelectAllMysqlCommunications(t)
|
RunSelectAllMysqlCommunications(t)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Create Users", func(t *testing.T) {
|
t.Run(dbt+" Create Users", func(t *testing.T) {
|
||||||
|
@ -131,7 +155,7 @@ func TestRunAll(t *testing.T) {
|
||||||
t.Run(dbt+" Create Failing Service", func(t *testing.T) {
|
t.Run(dbt+" Create Failing Service", func(t *testing.T) {
|
||||||
RunBadService_Create(t)
|
RunBadService_Create(t)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Check Service", func(t *testing.T) {
|
t.Run(dbt+" Check Bad Service", func(t *testing.T) {
|
||||||
RunBadService_Check(t)
|
RunBadService_Check(t)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Select Hits", func(t *testing.T) {
|
t.Run(dbt+" Select Hits", func(t *testing.T) {
|
||||||
|
@ -183,35 +207,24 @@ func TestRunAll(t *testing.T) {
|
||||||
RunSettingsHandler(t)
|
RunSettingsHandler(t)
|
||||||
})
|
})
|
||||||
t.Run(dbt+" Cleanup", func(t *testing.T) {
|
t.Run(dbt+" Cleanup", func(t *testing.T) {
|
||||||
//Cleanup(t)
|
core.Configs.Close()
|
||||||
|
core.DbSession = nil
|
||||||
|
//Clean()
|
||||||
})
|
})
|
||||||
|
|
||||||
|
//<-done
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func Cleanup(t *testing.T) {
|
func RunSaveConfig(t *testing.T, db string) {
|
||||||
core.DbSession.ClearCache()
|
var err error
|
||||||
err := core.DbSession.Close()
|
|
||||||
assert.Nil(t, err)
|
|
||||||
}
|
|
||||||
|
|
||||||
func RunMakeDatabaseConfig(t *testing.T, db string) {
|
|
||||||
port := 5432
|
port := 5432
|
||||||
if db == "mysql" {
|
if db == "mysql" {
|
||||||
port = 3306
|
port = 3306
|
||||||
}
|
}
|
||||||
|
core.Configs = &core.DbConfig{DbConfig: &types.DbConfig{
|
||||||
//Project string `yaml:"-"`
|
|
||||||
//Description string `yaml:"-"`
|
|
||||||
//Domain string `yaml:"-"`
|
|
||||||
//Username string `yaml:"-"`
|
|
||||||
//Password string `yaml:"-"`
|
|
||||||
//Email string `yaml:"-"`
|
|
||||||
//Error error `yaml:"-"`
|
|
||||||
//Location string `yaml:"location"`
|
|
||||||
|
|
||||||
config := &core.DbConfig{&types.DbConfig{
|
|
||||||
DbConn: db,
|
DbConn: db,
|
||||||
DbHost: os.Getenv("DB_HOST"),
|
DbHost: os.Getenv("DB_HOST"),
|
||||||
DbUser: os.Getenv("DB_USER"),
|
DbUser: os.Getenv("DB_USER"),
|
||||||
|
@ -227,14 +240,19 @@ func RunMakeDatabaseConfig(t *testing.T, db string) {
|
||||||
Error: nil,
|
Error: nil,
|
||||||
Location: dir,
|
Location: dir,
|
||||||
}}
|
}}
|
||||||
err := config.Save()
|
core.Configs, err = core.Configs.Save()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
|
}
|
||||||
|
|
||||||
_, err = core.LoadConfig()
|
func RunCreateSchema(t *testing.T, db string) {
|
||||||
|
err := core.Configs.Connect(false, dir)
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, db, core.Configs.Connection)
|
err = core.Configs.CreateDatabase()
|
||||||
|
assert.Nil(t, err)
|
||||||
|
}
|
||||||
|
|
||||||
err = core.DbConnection(core.Configs.Connection, false, dir)
|
func RunConnectDatabase(t *testing.T) {
|
||||||
|
err := core.Configs.Connect(false, dir)
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -244,22 +262,32 @@ func RunDatabaseMigrations(t *testing.T, db string) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunInsertSampleData(t *testing.T) {
|
func RunInsertSampleData(t *testing.T) {
|
||||||
err := core.LoadSampleData()
|
_, _, err := core.Configs.SeedDatabase()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunLoadConfig(t *testing.T) {
|
func RunLoadConfig(t *testing.T) {
|
||||||
var err error
|
var err error
|
||||||
core.Configs, err = core.LoadConfig()
|
core.Configs, err = core.LoadConfig(dir)
|
||||||
|
t.Log(core.Configs)
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.NotNil(t, core.Configs)
|
assert.NotNil(t, core.Configs)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func RunDropDatabase(t *testing.T) {
|
||||||
|
err := core.Configs.DropDatabase()
|
||||||
|
assert.Nil(t, err)
|
||||||
|
}
|
||||||
|
|
||||||
func RunSelectCoreMYQL(t *testing.T, db string) {
|
func RunSelectCoreMYQL(t *testing.T, db string) {
|
||||||
var err error
|
var err error
|
||||||
core.CoreApp, err = core.SelectCore()
|
core.CoreApp, err = core.SelectCore()
|
||||||
|
if err != nil {
|
||||||
|
t.FailNow()
|
||||||
|
}
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, "Testing "+db, core.CoreApp.Name)
|
t.Log("core: ", core.CoreApp.Core)
|
||||||
|
assert.Equal(t, "Awesome Status", core.CoreApp.Name)
|
||||||
assert.Equal(t, db, core.CoreApp.DbConnection)
|
assert.Equal(t, db, core.CoreApp.DbConnection)
|
||||||
assert.NotEmpty(t, core.CoreApp.ApiKey)
|
assert.NotEmpty(t, core.CoreApp.ApiKey)
|
||||||
assert.NotEmpty(t, core.CoreApp.ApiSecret)
|
assert.NotEmpty(t, core.CoreApp.ApiSecret)
|
||||||
|
@ -270,12 +298,12 @@ func RunSelectAllMysqlServices(t *testing.T) {
|
||||||
var err error
|
var err error
|
||||||
services, err := core.CoreApp.SelectAllServices()
|
services, err := core.CoreApp.SelectAllServices()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 5, len(services))
|
assert.Equal(t, 18, len(services))
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunSelectAllMysqlCommunications(t *testing.T) {
|
func RunSelectAllMysqlCommunications(t *testing.T) {
|
||||||
var err error
|
var err error
|
||||||
notifiers.Collections = core.DbSession.Collection("communication")
|
notifiers.Collections = core.DbSession.Table("communication").Model(¬ifiers.Notification{})
|
||||||
comms := notifiers.Load()
|
comms := notifiers.Load()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 3, len(comms))
|
assert.Equal(t, 3, len(comms))
|
||||||
|
@ -284,19 +312,19 @@ func RunSelectAllMysqlCommunications(t *testing.T) {
|
||||||
func RunUser_SelectAll(t *testing.T) {
|
func RunUser_SelectAll(t *testing.T) {
|
||||||
users, err := core.SelectAllUsers()
|
users, err := core.SelectAllUsers()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 2, len(users))
|
assert.Equal(t, 3, len(users))
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunUser_Create(t *testing.T) {
|
func RunUser_Create(t *testing.T) {
|
||||||
user := core.ReturnUser(&types.User{
|
user := core.ReturnUser(&types.User{
|
||||||
Username: "admin",
|
Username: "hunterlong",
|
||||||
Password: "admin",
|
Password: "password123",
|
||||||
Email: "info@testuser.com",
|
Email: "info@gmail.com",
|
||||||
Admin: true,
|
Admin: true,
|
||||||
})
|
})
|
||||||
id, err := user.Create()
|
id, err := user.Create()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, int64(1), id)
|
assert.Equal(t, int64(2), id)
|
||||||
user2 := core.ReturnUser(&types.User{
|
user2 := core.ReturnUser(&types.User{
|
||||||
Username: "superadmin",
|
Username: "superadmin",
|
||||||
Password: "admin",
|
Password: "admin",
|
||||||
|
@ -305,7 +333,7 @@ func RunUser_Create(t *testing.T) {
|
||||||
})
|
})
|
||||||
id, err = user2.Create()
|
id, err = user2.Create()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, int64(2), id)
|
assert.Equal(t, int64(3), id)
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunUser_Update(t *testing.T) {
|
func RunUser_Update(t *testing.T) {
|
||||||
|
@ -342,7 +370,10 @@ func RunSelectAllServices(t *testing.T) {
|
||||||
var err error
|
var err error
|
||||||
services, err := core.CoreApp.SelectAllServices()
|
services, err := core.CoreApp.SelectAllServices()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 5, len(services))
|
assert.Equal(t, 18, len(services))
|
||||||
|
for _, s := range services {
|
||||||
|
assert.NotEmpty(t, s.CreatedAt)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunOneService_Check(t *testing.T) {
|
func RunOneService_Check(t *testing.T) {
|
||||||
|
@ -365,8 +396,7 @@ func RunService_Create(t *testing.T) {
|
||||||
})
|
})
|
||||||
id, err := service.Create()
|
id, err := service.Create()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, int64(6), id)
|
assert.Equal(t, int64(19), id)
|
||||||
t.Log(service)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunService_ToJSON(t *testing.T) {
|
func RunService_ToJSON(t *testing.T) {
|
||||||
|
@ -379,15 +409,20 @@ func RunService_ToJSON(t *testing.T) {
|
||||||
func RunService_AvgTime(t *testing.T) {
|
func RunService_AvgTime(t *testing.T) {
|
||||||
service := core.SelectService(1)
|
service := core.SelectService(1)
|
||||||
assert.NotNil(t, service)
|
assert.NotNil(t, service)
|
||||||
avg := service.AvgUptime()
|
avg := service.AvgUptime24()
|
||||||
assert.Equal(t, "100", avg)
|
assert.Equal(t, "100", avg)
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunService_Online24(t *testing.T) {
|
func RunService_Online24(t *testing.T) {
|
||||||
service := core.SelectService(1)
|
service := core.SelectService(1)
|
||||||
assert.NotNil(t, service)
|
assert.NotNil(t, service)
|
||||||
online := service.Online24()
|
online := service.OnlineSince(SERVICE_SINCE)
|
||||||
assert.Equal(t, float32(100), online)
|
assert.Equal(t, float32(80), online)
|
||||||
|
|
||||||
|
service = core.SelectService(18)
|
||||||
|
assert.NotNil(t, service)
|
||||||
|
online = service.OnlineSince(SERVICE_SINCE)
|
||||||
|
assert.Equal(t, float32(0), online)
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunService_GraphData(t *testing.T) {
|
func RunService_GraphData(t *testing.T) {
|
||||||
|
@ -413,13 +448,13 @@ func RunBadService_Create(t *testing.T) {
|
||||||
})
|
})
|
||||||
id, err := service.Create()
|
id, err := service.Create()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, int64(7), id)
|
assert.Equal(t, int64(20), id)
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunBadService_Check(t *testing.T) {
|
func RunBadService_Check(t *testing.T) {
|
||||||
service := core.SelectService(7)
|
service := core.SelectService(18)
|
||||||
assert.NotNil(t, service)
|
assert.NotNil(t, service)
|
||||||
assert.Equal(t, "Bad Service", service.Name)
|
assert.Equal(t, "Failing URL", service.Name)
|
||||||
for i := 0; i <= 10; i++ {
|
for i := 0; i <= 10; i++ {
|
||||||
service.Check(true)
|
service.Check(true)
|
||||||
}
|
}
|
||||||
|
@ -431,9 +466,7 @@ func RunDeleteService(t *testing.T) {
|
||||||
assert.NotNil(t, service)
|
assert.NotNil(t, service)
|
||||||
assert.Equal(t, "JSON API Tester", service.Name)
|
assert.Equal(t, "JSON API Tester", service.Name)
|
||||||
assert.True(t, service.IsRunning())
|
assert.True(t, service.IsRunning())
|
||||||
t.Log(service.Running)
|
|
||||||
err := service.Delete()
|
err := service.Delete()
|
||||||
t.Log(service.Running)
|
|
||||||
assert.False(t, service.IsRunning())
|
assert.False(t, service.IsRunning())
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
@ -441,14 +474,11 @@ func RunDeleteService(t *testing.T) {
|
||||||
func RunCreateService_Hits(t *testing.T) {
|
func RunCreateService_Hits(t *testing.T) {
|
||||||
services := core.CoreApp.Services()
|
services := core.CoreApp.Services()
|
||||||
assert.NotNil(t, services)
|
assert.NotNil(t, services)
|
||||||
assert.Equal(t, 6, len(services))
|
assert.Equal(t, 19, len(services))
|
||||||
for i := 0; i <= 15; i++ {
|
|
||||||
for _, s := range services {
|
for _, s := range services {
|
||||||
var service *core.Service
|
service := s.Check(true)
|
||||||
service = s.Check(true)
|
|
||||||
assert.NotNil(t, service)
|
assert.NotNil(t, service)
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunService_Hits(t *testing.T) {
|
func RunService_Hits(t *testing.T) {
|
||||||
|
@ -460,9 +490,9 @@ func RunService_Hits(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func RunService_Failures(t *testing.T) {
|
func RunService_Failures(t *testing.T) {
|
||||||
service := core.SelectService(7)
|
service := core.SelectService(18)
|
||||||
assert.NotNil(t, service)
|
assert.NotNil(t, service)
|
||||||
assert.Equal(t, "Bad Service", service.Name)
|
assert.Equal(t, "Failing URL", service.Name)
|
||||||
assert.NotEmpty(t, service.Failures)
|
assert.NotEmpty(t, service.Failures)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -479,7 +509,7 @@ func RunIndexHandler(t *testing.T) {
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
rr := httptest.NewRecorder()
|
rr := httptest.NewRecorder()
|
||||||
route.ServeHTTP(rr, req)
|
route.ServeHTTP(rr, req)
|
||||||
assert.True(t, strings.Contains(rr.Body.String(), "This is a test of Statup.io!"))
|
assert.True(t, strings.Contains(rr.Body.String(), "Awesome"))
|
||||||
assert.True(t, strings.Contains(rr.Body.String(), "footer"))
|
assert.True(t, strings.Contains(rr.Body.String(), "footer"))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -499,7 +529,7 @@ func RunPrometheusHandler(t *testing.T) {
|
||||||
rr := httptest.NewRecorder()
|
rr := httptest.NewRecorder()
|
||||||
route.ServeHTTP(rr, req)
|
route.ServeHTTP(rr, req)
|
||||||
t.Log(rr.Body.String())
|
t.Log(rr.Body.String())
|
||||||
assert.True(t, strings.Contains(rr.Body.String(), "statup_total_services 6"))
|
assert.True(t, strings.Contains(rr.Body.String(), "statup_total_services 19"))
|
||||||
assert.True(t, handlers.IsAuthenticated(req))
|
assert.True(t, handlers.IsAuthenticated(req))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -515,7 +545,7 @@ func RunFailingPrometheusHandler(t *testing.T) {
|
||||||
func RunLoginHandler(t *testing.T) {
|
func RunLoginHandler(t *testing.T) {
|
||||||
form := url.Values{}
|
form := url.Values{}
|
||||||
form.Add("username", "admin")
|
form.Add("username", "admin")
|
||||||
form.Add("password", "admin")
|
form.Add("password", "password123")
|
||||||
req, err := http.NewRequest("POST", "/dashboard", strings.NewReader(form.Encode()))
|
req, err := http.NewRequest("POST", "/dashboard", strings.NewReader(form.Encode()))
|
||||||
req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
|
req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
|
|
|
@ -210,7 +210,9 @@ func RecordSuccess(s *Service) {
|
||||||
s.Online = true
|
s.Online = true
|
||||||
s.LastOnline = time.Now()
|
s.LastOnline = time.Now()
|
||||||
data := &types.Hit{
|
data := &types.Hit{
|
||||||
|
Service: s.Id,
|
||||||
Latency: s.Latency,
|
Latency: s.Latency,
|
||||||
|
CreatedAt: time.Now(),
|
||||||
}
|
}
|
||||||
utils.Log(1, fmt.Sprintf("Service %v Successful: %0.2f ms", s.Name, data.Latency*1000))
|
utils.Log(1, fmt.Sprintf("Service %v Successful: %0.2f ms", s.Name, data.Latency*1000))
|
||||||
s.CreateHit(data)
|
s.CreateHit(data)
|
||||||
|
|
|
@ -48,26 +48,25 @@ func FindCheckin(api string) *types.Checkin {
|
||||||
|
|
||||||
func (s *Service) AllCheckins() []*types.Checkin {
|
func (s *Service) AllCheckins() []*types.Checkin {
|
||||||
var checkins []*types.Checkin
|
var checkins []*types.Checkin
|
||||||
col := DbSession.Collection("checkins").Find("service", s.Id).OrderBy("-id")
|
col := checkinDB().Where("service = ?", s.Id).Order("-id")
|
||||||
col.All(&checkins)
|
col.Scan(&checkins)
|
||||||
s.Checkins = checkins
|
s.Checkins = checkins
|
||||||
return checkins
|
return checkins
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Checkin) Create() (int64, error) {
|
func (u *Checkin) Create() (int64, error) {
|
||||||
u.CreatedAt = time.Now()
|
u.CreatedAt = time.Now()
|
||||||
uuid, err := DbSession.Collection("checkins").Insert(u)
|
row := checkinDB().Create(&u)
|
||||||
if uuid == nil {
|
if row.Error == nil {
|
||||||
utils.Log(2, err)
|
utils.Log(2, row.Error)
|
||||||
return 0, err
|
return 0, row.Error
|
||||||
}
|
}
|
||||||
fmt.Println("new checkin: ", uuid)
|
return u.Id, row.Error
|
||||||
return uuid.(int64), err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectCheckinApi(api string) *Checkin {
|
func SelectCheckinApi(api string) *Checkin {
|
||||||
var checkin *Checkin
|
var checkin *Checkin
|
||||||
DbSession.Collection("checkins").Find("api", api).One(&checkin)
|
checkinDB().Where("api = ?", api).Find(&checkin)
|
||||||
return checkin
|
return checkin
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -23,29 +23,28 @@ import (
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"os"
|
"os"
|
||||||
"time"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func LoadConfig() (*types.Config, error) {
|
func LoadConfig(directory string) (*DbConfig, error) {
|
||||||
|
var configs *types.DbConfig
|
||||||
if os.Getenv("DB_CONN") != "" {
|
if os.Getenv("DB_CONN") != "" {
|
||||||
utils.Log(1, "DB_CONN environment variable was found, waiting for database...")
|
utils.Log(1, "DB_CONN environment variable was found, waiting for database...")
|
||||||
return LoadUsingEnv()
|
return LoadUsingEnv()
|
||||||
}
|
}
|
||||||
Configs = new(types.Config)
|
file, err := ioutil.ReadFile(directory + "/config.yml")
|
||||||
file, err := ioutil.ReadFile(utils.Directory + "/config.yml")
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, errors.New("config.yml file not found - starting in setup mode")
|
return nil, errors.New("config.yml file not found at " + directory + "/config.yml - starting in setup mode")
|
||||||
}
|
}
|
||||||
err = yaml.Unmarshal(file, &Configs)
|
err = yaml.Unmarshal(file, &configs)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
CoreApp.DbConnection = Configs.Connection
|
Configs = &DbConfig{configs}
|
||||||
return Configs, err
|
return Configs, err
|
||||||
}
|
}
|
||||||
|
|
||||||
func LoadUsingEnv() (*types.Config, error) {
|
func LoadUsingEnv() (*DbConfig, error) {
|
||||||
Configs = new(types.Config)
|
Configs = new(DbConfig)
|
||||||
if os.Getenv("DB_CONN") == "" {
|
if os.Getenv("DB_CONN") == "" {
|
||||||
return nil, errors.New("Missing DB_CONN environment variable")
|
return nil, errors.New("Missing DB_CONN environment variable")
|
||||||
}
|
}
|
||||||
|
@ -61,12 +60,12 @@ func LoadUsingEnv() (*types.Config, error) {
|
||||||
if os.Getenv("DB_DATABASE") == "" {
|
if os.Getenv("DB_DATABASE") == "" {
|
||||||
return nil, errors.New("Missing DB_DATABASE environment variable")
|
return nil, errors.New("Missing DB_DATABASE environment variable")
|
||||||
}
|
}
|
||||||
Configs.Connection = os.Getenv("DB_CONN")
|
Configs.DbConn = os.Getenv("DB_CONN")
|
||||||
Configs.Host = os.Getenv("DB_HOST")
|
Configs.DbHost = os.Getenv("DB_HOST")
|
||||||
Configs.Port = os.Getenv("DB_PORT")
|
Configs.DbPort = int(utils.StringInt(os.Getenv("DB_PORT")))
|
||||||
Configs.User = os.Getenv("DB_USER")
|
Configs.DbUser = os.Getenv("DB_USER")
|
||||||
Configs.Password = os.Getenv("DB_PASS")
|
Configs.Password = os.Getenv("DB_PASS")
|
||||||
Configs.Database = os.Getenv("DB_DATABASE")
|
Configs.DbData = os.Getenv("DB_DATABASE")
|
||||||
CoreApp.DbConnection = os.Getenv("DB_CONN")
|
CoreApp.DbConnection = os.Getenv("DB_CONN")
|
||||||
CoreApp.Name = os.Getenv("NAME")
|
CoreApp.Name = os.Getenv("NAME")
|
||||||
CoreApp.Domain = os.Getenv("DOMAIN")
|
CoreApp.Domain = os.Getenv("DOMAIN")
|
||||||
|
@ -89,32 +88,19 @@ func LoadUsingEnv() (*types.Config, error) {
|
||||||
Email: "info@localhost.com",
|
Email: "info@localhost.com",
|
||||||
}}
|
}}
|
||||||
|
|
||||||
err := DbConnection(dbConfig.DbConn, true, utils.Directory)
|
err := dbConfig.Connect(true, utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, err)
|
utils.Log(4, err)
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
exists, err := DbSession.Collection("core").Find().Exists()
|
exists := DbSession.HasTable("core")
|
||||||
if !exists {
|
if !exists {
|
||||||
|
|
||||||
utils.Log(1, fmt.Sprintf("Core database does not exist, creating now!"))
|
utils.Log(1, fmt.Sprintf("Core database does not exist, creating now!"))
|
||||||
DropDatabase()
|
dbConfig.DropDatabase()
|
||||||
CreateDatabase()
|
dbConfig.CreateDatabase()
|
||||||
|
|
||||||
CoreApp = &Core{Core: &types.Core{
|
CoreApp, err = dbConfig.InsertCore()
|
||||||
Name: dbConfig.Project,
|
|
||||||
Description: dbConfig.Description,
|
|
||||||
Config: "config.yml",
|
|
||||||
ApiKey: utils.NewSHA1Hash(9),
|
|
||||||
ApiSecret: utils.NewSHA1Hash(16),
|
|
||||||
Domain: dbConfig.Domain,
|
|
||||||
MigrationId: time.Now().Unix(),
|
|
||||||
}}
|
|
||||||
|
|
||||||
CoreApp.DbConnection = dbConfig.DbConn
|
|
||||||
|
|
||||||
err := InsertCore(CoreApp)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
}
|
}
|
||||||
|
|
45
core/core.go
45
core/core.go
|
@ -22,7 +22,6 @@ import (
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
"os"
|
"os"
|
||||||
"sort"
|
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -34,7 +33,7 @@ type Core struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
var (
|
var (
|
||||||
Configs *types.Config
|
Configs *DbConfig
|
||||||
CoreApp *Core
|
CoreApp *Core
|
||||||
SetupMode bool
|
SetupMode bool
|
||||||
VERSION string
|
VERSION string
|
||||||
|
@ -51,12 +50,6 @@ func NewCore() *Core {
|
||||||
return CoreApp
|
return CoreApp
|
||||||
}
|
}
|
||||||
|
|
||||||
func InsertCore(c *Core) error {
|
|
||||||
col := DbSession.Collection("core")
|
|
||||||
_, err := col.Insert(c.Core)
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
func (c *Core) ToCore() *types.Core {
|
func (c *Core) ToCore() *types.Core {
|
||||||
return c.Core
|
return c.Core
|
||||||
}
|
}
|
||||||
|
@ -72,19 +65,18 @@ func InitApp() {
|
||||||
|
|
||||||
func InsertNotifierDB() error {
|
func InsertNotifierDB() error {
|
||||||
if DbSession == nil {
|
if DbSession == nil {
|
||||||
err := DbConnection(CoreApp.DbConnection, false, utils.Directory)
|
err := Configs.Connect(false, utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.New("database connection has not been created")
|
return errors.New("database connection has not been created")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
notifiers.Collections = DbSession.Collection("communication")
|
notifiers.Collections = commDB()
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func UpdateCore(c *Core) (*Core, error) {
|
func UpdateCore(c *Core) (*Core, error) {
|
||||||
res := DbSession.Collection("core").Find().Limit(1)
|
db := coreDB().Update(c)
|
||||||
err := res.Update(c.Core)
|
return c, db.Error
|
||||||
return c, err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Core) UsingAssets() bool {
|
func (c Core) UsingAssets() bool {
|
||||||
|
@ -122,36 +114,33 @@ func (c Core) AllOnline() bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectLastMigration() (int64, error) {
|
func SelectLastMigration() (int64, error) {
|
||||||
var c *types.Core
|
|
||||||
if DbSession == nil {
|
if DbSession == nil {
|
||||||
return 0, errors.New("Database connection has not been created yet")
|
return 0, errors.New("Database connection has not been created yet")
|
||||||
}
|
}
|
||||||
err := DbSession.Collection("core").Find().One(&c)
|
row := coreDB().Take(&CoreApp)
|
||||||
if err != nil {
|
return CoreApp.MigrationId, row.Error
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
return c.MigrationId, err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectCore() (*Core, error) {
|
func SelectCore() (*Core, error) {
|
||||||
var c *types.Core
|
if DbSession == nil {
|
||||||
exists := DbSession.Collection("core").Exists()
|
return nil, errors.New("database has not been initiated yet.")
|
||||||
|
}
|
||||||
|
exists := DbSession.HasTable("core")
|
||||||
if !exists {
|
if !exists {
|
||||||
return nil, errors.New("core database has not been setup yet.")
|
return nil, errors.New("core database has not been setup yet.")
|
||||||
}
|
}
|
||||||
err := DbSession.Collection("core").Find().One(&c)
|
db := coreDB().Take(&CoreApp)
|
||||||
if err != nil {
|
if db.Error != nil {
|
||||||
return nil, err
|
return nil, db.Error
|
||||||
}
|
}
|
||||||
CoreApp.Core = c
|
CoreApp.DbConnection = Configs.DbConn
|
||||||
CoreApp.DbConnection = Configs.Connection
|
|
||||||
CoreApp.Version = VERSION
|
CoreApp.Version = VERSION
|
||||||
CoreApp.SelectAllServices()
|
CoreApp.SelectAllServices()
|
||||||
if os.Getenv("USE_CDN") == "true" {
|
if os.Getenv("USE_CDN") == "true" {
|
||||||
CoreApp.UseCdn = true
|
CoreApp.UseCdn = true
|
||||||
}
|
}
|
||||||
//store = sessions.NewCookieStore([]byte(core.ApiSecret))
|
//store = sessions.NewCookieStore([]byte(core.ApiSecret))
|
||||||
return CoreApp, err
|
return CoreApp, db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
type ServiceOrder []*types.Service
|
type ServiceOrder []*types.Service
|
||||||
|
@ -163,7 +152,7 @@ func (c ServiceOrder) Less(i, j int) bool { return c[i].Order < c[j].Order }
|
||||||
func (c *Core) Services() []*Service {
|
func (c *Core) Services() []*Service {
|
||||||
var services []*Service
|
var services []*Service
|
||||||
servs := CoreApp.GetServices()
|
servs := CoreApp.GetServices()
|
||||||
sort.Sort(ServiceOrder(servs))
|
//sort.Sort(ServiceOrder(servs))
|
||||||
for _, ser := range servs {
|
for _, ser := range servs {
|
||||||
services = append(services, ReturnService(ser))
|
services = append(services, ReturnService(ser))
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,11 +24,13 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
testCore *Core
|
|
||||||
testConfig *DbConfig
|
|
||||||
dir string
|
dir string
|
||||||
)
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
SERVICE_SINCE = "2018-08-30T10:42:08-07:00" // "2006-01-02T15:04:05Z07:00"
|
||||||
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
dir = utils.Directory
|
dir = utils.Directory
|
||||||
utils.InitLogs()
|
utils.InitLogs()
|
||||||
|
@ -36,51 +38,65 @@ func init() {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestNewCore(t *testing.T) {
|
func TestNewCore(t *testing.T) {
|
||||||
testCore = NewCore()
|
utils.DeleteFile(dir + "/config.yml")
|
||||||
assert.NotNil(t, testCore)
|
utils.DeleteFile(dir + "/statup.db")
|
||||||
testCore.Name = "Tester"
|
CoreApp = NewCore()
|
||||||
|
assert.NotNil(t, CoreApp)
|
||||||
|
CoreApp.Name = "Tester"
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestDbConfig_Save(t *testing.T) {
|
func TestDbConfig_Save(t *testing.T) {
|
||||||
testConfig = &DbConfig{&types.DbConfig{
|
var err error
|
||||||
|
Configs = &DbConfig{&types.DbConfig{
|
||||||
DbConn: "sqlite",
|
DbConn: "sqlite",
|
||||||
Project: "Tester",
|
Project: "Tester",
|
||||||
Location: dir,
|
Location: dir,
|
||||||
}}
|
}}
|
||||||
err := testConfig.Save()
|
Configs, err = Configs.Save()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
|
assert.Equal(t, "sqlite", Configs.DbConn)
|
||||||
|
assert.NotEmpty(t, Configs.ApiKey)
|
||||||
|
assert.NotEmpty(t, Configs.ApiSecret)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestLoadDbConfig(t *testing.T) {
|
||||||
|
Configs, err := LoadConfig(dir)
|
||||||
|
assert.Nil(t, err)
|
||||||
|
assert.Equal(t, "sqlite", Configs.DbConn)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestDbConnection(t *testing.T) {
|
func TestDbConnection(t *testing.T) {
|
||||||
err := DbConnection(testConfig.DbConn, false, dir)
|
err := Configs.Connect(false, dir)
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestCreateDatabase(t *testing.T) {
|
func TestSeedSchemaDatabase(t *testing.T) {
|
||||||
err := CreateDatabase()
|
_, _, err := Configs.SeedSchema()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestInsertCore(t *testing.T) {
|
func TestSeedDatabase(t *testing.T) {
|
||||||
err := InsertCore(testCore)
|
_, _, err := Configs.SeedDatabase()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestReLoadDbConfig(t *testing.T) {
|
||||||
|
err := Configs.Connect(false, dir)
|
||||||
|
assert.Nil(t, err)
|
||||||
|
assert.Equal(t, "sqlite", Configs.DbConn)
|
||||||
|
}
|
||||||
|
|
||||||
func TestSelectCore(t *testing.T) {
|
func TestSelectCore(t *testing.T) {
|
||||||
core, err := SelectCore()
|
core, err := SelectCore()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, "Tester", core.Name)
|
assert.Equal(t, "Awesome Status", core.Name)
|
||||||
}
|
|
||||||
|
|
||||||
func TestSampleData(t *testing.T) {
|
|
||||||
err := LoadSampleData()
|
|
||||||
assert.Nil(t, err)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSelectLastMigration(t *testing.T) {
|
func TestSelectLastMigration(t *testing.T) {
|
||||||
id, err := SelectLastMigration()
|
id, err := SelectLastMigration()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.NotZero(t, id)
|
//assert.NotZero(t, id)
|
||||||
|
t.Log("Last migration id: ", id)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestInsertNotifierDB(t *testing.T) {
|
func TestInsertNotifierDB(t *testing.T) {
|
||||||
|
|
320
core/database.go
320
core/database.go
|
@ -17,94 +17,176 @@ package core
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
_ "github.com/go-sql-driver/mysql"
|
||||||
"github.com/go-yaml/yaml"
|
"github.com/go-yaml/yaml"
|
||||||
|
"github.com/hunterlong/statup/notifiers"
|
||||||
"github.com/hunterlong/statup/source"
|
"github.com/hunterlong/statup/source"
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
|
"github.com/jinzhu/gorm"
|
||||||
|
_ "github.com/jinzhu/gorm/dialects/mssql"
|
||||||
|
_ "github.com/jinzhu/gorm/dialects/mysql"
|
||||||
|
_ "github.com/jinzhu/gorm/dialects/postgres"
|
||||||
|
_ "github.com/jinzhu/gorm/dialects/sqlite"
|
||||||
|
_ "github.com/lib/pq"
|
||||||
|
_ "github.com/mattn/go-sqlite3"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
"upper.io/db.v3"
|
|
||||||
"upper.io/db.v3/lib/sqlbuilder"
|
|
||||||
"upper.io/db.v3/mysql"
|
|
||||||
"upper.io/db.v3/postgresql"
|
|
||||||
"upper.io/db.v3/sqlite"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
sqliteSettings sqlite.ConnectionURL
|
DbSession *gorm.DB
|
||||||
postgresSettings postgresql.ConnectionURL
|
|
||||||
mysqlSettings mysql.ConnectionURL
|
|
||||||
DbSession sqlbuilder.Database
|
|
||||||
currentMigration int64
|
currentMigration int64
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func failuresDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Model(&types.Failure{}).Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Model(&types.Failure{})
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Service) allHits() *gorm.DB {
|
||||||
|
var hits []*Hit
|
||||||
|
return servicesDB().Find(s).Related(&hits)
|
||||||
|
}
|
||||||
|
|
||||||
|
func hitsDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Model(&types.Hit{}).Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Model(&types.Hit{})
|
||||||
|
}
|
||||||
|
|
||||||
|
func servicesDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Model(&types.Service{}).Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Model(&types.Service{})
|
||||||
|
}
|
||||||
|
|
||||||
|
func coreDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Table("core").Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Table("core")
|
||||||
|
}
|
||||||
|
|
||||||
|
func usersDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Model(&types.User{}).Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Model(&types.User{})
|
||||||
|
}
|
||||||
|
|
||||||
|
func commDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Table("communication").Model(¬ifiers.Notification{}).Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Table("communication").Model(¬ifiers.Notification{})
|
||||||
|
}
|
||||||
|
|
||||||
|
func checkinDB() *gorm.DB {
|
||||||
|
if os.Getenv("GO_ENV") == "TEST" {
|
||||||
|
return DbSession.Model(&types.Checkin{}).Debug()
|
||||||
|
}
|
||||||
|
return DbSession.Model(&types.Checkin{})
|
||||||
|
}
|
||||||
|
|
||||||
type DbConfig struct {
|
type DbConfig struct {
|
||||||
*types.DbConfig
|
*types.DbConfig
|
||||||
}
|
}
|
||||||
|
|
||||||
func DbConnection(dbType string, retry bool, location string) error {
|
func (db *DbConfig) Close() error {
|
||||||
|
return DbSession.Close()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (db *DbConfig) InsertCore() (*Core, error) {
|
||||||
|
CoreApp = &Core{Core: &types.Core{
|
||||||
|
Name: db.Project,
|
||||||
|
Description: db.Description,
|
||||||
|
Config: "config.yml",
|
||||||
|
ApiKey: utils.NewSHA1Hash(9),
|
||||||
|
ApiSecret: utils.NewSHA1Hash(16),
|
||||||
|
Domain: db.Domain,
|
||||||
|
MigrationId: time.Now().Unix(),
|
||||||
|
}}
|
||||||
|
CoreApp.DbConnection = db.DbConn
|
||||||
|
query := coreDB().Create(&CoreApp)
|
||||||
|
return CoreApp, query.Error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (db *DbConfig) Connect(retry bool, location string) error {
|
||||||
var err error
|
var err error
|
||||||
if dbType == "sqlite" {
|
if DbSession != nil {
|
||||||
sqliteSettings = sqlite.ConnectionURL{
|
DbSession = nil
|
||||||
Database: location + "/statup.db",
|
|
||||||
}
|
}
|
||||||
DbSession, err = sqlite.Open(sqliteSettings)
|
switch Configs.DbConn {
|
||||||
|
case "sqlite":
|
||||||
|
DbSession, err = gorm.Open("sqlite3", utils.Directory+"/statup.db")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
} else if dbType == "mysql" {
|
case "mysql":
|
||||||
if Configs.Port == "" {
|
if Configs.DbPort == 0 {
|
||||||
Configs.Port = "3306"
|
Configs.DbPort = 3306
|
||||||
}
|
}
|
||||||
host := fmt.Sprintf("%v:%v", Configs.Host, Configs.Port)
|
host := fmt.Sprintf("%v:%v", Configs.DbHost, Configs.DbPort)
|
||||||
mysqlSettings = mysql.ConnectionURL{
|
conn := fmt.Sprintf("%v:%v@tcp(%v)/%v?charset=utf8&parseTime=True&loc=Local", Configs.DbUser, Configs.DbPass, host, Configs.DbData)
|
||||||
Database: Configs.Database,
|
DbSession, err = gorm.Open("mysql", conn)
|
||||||
Host: host,
|
DbSession.DB().SetConnMaxLifetime(time.Minute * 5)
|
||||||
User: Configs.User,
|
DbSession.DB().SetMaxIdleConns(0)
|
||||||
Password: Configs.Password,
|
DbSession.DB().SetMaxOpenConns(5)
|
||||||
Options: map[string]string{"parseTime": "true", "charset": "utf8"},
|
|
||||||
}
|
|
||||||
DbSession, err = mysql.Open(mysqlSettings)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
if retry {
|
if retry {
|
||||||
utils.Log(1, fmt.Sprintf("Database connection to '%v' is not available, trying again in 5 seconds...", host))
|
utils.Log(1, fmt.Sprintf("Database connection to '%v' is not available, trying again in 5 seconds...", host))
|
||||||
return waitForDb(dbType)
|
return db.waitForDb()
|
||||||
} else {
|
} else {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
case "postgres":
|
||||||
|
if Configs.DbPort == 0 {
|
||||||
|
Configs.DbPort = 5432
|
||||||
|
}
|
||||||
|
conn := fmt.Sprintf("host=%v port=%v user=%v dbname=%v password=%v sslmode=disable", Configs.DbHost, Configs.DbPort, Configs.DbUser, Configs.DbData, Configs.DbPass)
|
||||||
|
DbSession, err = gorm.Open("postgres", conn)
|
||||||
|
if err != nil {
|
||||||
|
if retry {
|
||||||
|
utils.Log(1, fmt.Sprintf("Database connection to '%v' is not available, trying again in 5 seconds...", Configs.DbHost))
|
||||||
|
return db.waitForDb()
|
||||||
} else {
|
} else {
|
||||||
if Configs.Port == "" {
|
fmt.Println("ERROR:", err)
|
||||||
Configs.Port = "5432"
|
return err
|
||||||
}
|
}
|
||||||
host := fmt.Sprintf("%v:%v", Configs.Host, Configs.Port)
|
|
||||||
postgresSettings = postgresql.ConnectionURL{
|
|
||||||
Database: Configs.Database,
|
|
||||||
Host: host,
|
|
||||||
User: Configs.User,
|
|
||||||
Password: Configs.Password,
|
|
||||||
}
|
}
|
||||||
DbSession, err = postgresql.Open(postgresSettings)
|
case "mssql":
|
||||||
|
if Configs.DbPort == 0 {
|
||||||
|
Configs.DbPort = 1433
|
||||||
|
}
|
||||||
|
host := fmt.Sprintf("%v:%v", Configs.DbHost, Configs.DbPort)
|
||||||
|
conn := fmt.Sprintf("sqlserver://%v:%v@%v?database=%v", Configs.DbUser, Configs.DbPass, host, Configs.DbData)
|
||||||
|
DbSession, err = gorm.Open("mssql", conn)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
if retry {
|
if retry {
|
||||||
utils.Log(1, fmt.Sprintf("Database connection to '%v' is not available, trying again in 5 seconds...", host))
|
utils.Log(1, fmt.Sprintf("Database connection to '%v' is not available, trying again in 5 seconds...", host))
|
||||||
return waitForDb(dbType)
|
return db.waitForDb()
|
||||||
} else {
|
} else {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
err = DbSession.Ping()
|
err = DbSession.DB().Ping()
|
||||||
if err == nil {
|
if err == nil {
|
||||||
utils.Log(1, fmt.Sprintf("Database connection to '%v' was successful.", DbSession.Name()))
|
utils.Log(1, fmt.Sprintf("Database connection to '%v' was successful.", Configs.DbData))
|
||||||
}
|
}
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
func waitForDb(dbType string) error {
|
func (db *DbConfig) waitForDb() error {
|
||||||
time.Sleep(5 * time.Second)
|
time.Sleep(5 * time.Second)
|
||||||
return DbConnection(dbType, true, utils.Directory)
|
return db.Connect(true, utils.Directory)
|
||||||
}
|
}
|
||||||
|
|
||||||
func DatabaseMaintence() {
|
func DatabaseMaintence() {
|
||||||
|
@ -118,9 +200,10 @@ func DatabaseMaintence() {
|
||||||
|
|
||||||
func DeleteAllSince(table string, date time.Time) {
|
func DeleteAllSince(table string, date time.Time) {
|
||||||
sql := fmt.Sprintf("DELETE FROM %v WHERE created_at < '%v';", table, date.Format("2006-01-02"))
|
sql := fmt.Sprintf("DELETE FROM %v WHERE created_at < '%v';", table, date.Format("2006-01-02"))
|
||||||
_, err := DbSession.Exec(db.Raw(sql))
|
db := DbSession.Raw(sql)
|
||||||
if err != nil {
|
defer db.Close()
|
||||||
utils.Log(2, err)
|
if db.Error != nil {
|
||||||
|
utils.Log(2, db.Error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -141,57 +224,44 @@ func (c *DbConfig) Update() error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *DbConfig) Save() error {
|
func (c *DbConfig) Save() (*DbConfig, error) {
|
||||||
var err error
|
var err error
|
||||||
config, err := os.Create(utils.Directory + "/config.yml")
|
config, err := os.Create(utils.Directory + "/config.yml")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, err)
|
utils.Log(4, err)
|
||||||
return err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
c.ApiKey = utils.NewSHA1Hash(16)
|
||||||
|
c.ApiSecret = utils.NewSHA1Hash(16)
|
||||||
data, err := yaml.Marshal(c.DbConfig)
|
data, err := yaml.Marshal(c.DbConfig)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
return err
|
return nil, err
|
||||||
}
|
}
|
||||||
config.WriteString(string(data))
|
config.WriteString(string(data))
|
||||||
config.Close()
|
defer config.Close()
|
||||||
|
return c, err
|
||||||
Configs, err = LoadConfig()
|
}
|
||||||
if err != nil {
|
|
||||||
utils.Log(3, err)
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
err = DbConnection(Configs.Connection, false, c.Location)
|
|
||||||
if err != nil {
|
|
||||||
utils.Log(4, err)
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
DropDatabase()
|
|
||||||
CreateDatabase()
|
|
||||||
|
|
||||||
|
func (c *DbConfig) CreateCore() *Core {
|
||||||
newCore := &types.Core{
|
newCore := &types.Core{
|
||||||
Name: c.Project,
|
Name: c.Project,
|
||||||
Description: c.Description,
|
Description: c.Description,
|
||||||
Config: "config.yml",
|
Config: "config.yml",
|
||||||
ApiKey: utils.NewSHA1Hash(9),
|
ApiKey: c.ApiKey,
|
||||||
ApiSecret: utils.NewSHA1Hash(16),
|
ApiSecret: c.ApiSecret,
|
||||||
Domain: c.Domain,
|
Domain: c.Domain,
|
||||||
MigrationId: time.Now().Unix(),
|
MigrationId: time.Now().Unix(),
|
||||||
}
|
}
|
||||||
col := DbSession.Collection("core")
|
db := coreDB().Create(&newCore)
|
||||||
_, err = col.Insert(newCore)
|
if db.Error == nil {
|
||||||
if err == nil {
|
|
||||||
CoreApp = &Core{Core: newCore}
|
CoreApp = &Core{Core: newCore}
|
||||||
}
|
}
|
||||||
|
CoreApp, err := SelectCore()
|
||||||
CoreApp, err = SelectCore()
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, err)
|
utils.Log(4, err)
|
||||||
}
|
}
|
||||||
CoreApp.DbConnection = c.DbConn
|
return CoreApp
|
||||||
c.ApiKey = CoreApp.ApiKey
|
|
||||||
c.ApiSecret = CoreApp.ApiSecret
|
|
||||||
return err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func versionHigher(migrate int64) bool {
|
func versionHigher(migrate int64) bool {
|
||||||
|
@ -239,10 +309,10 @@ func RunDatabaseUpgrades() error {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
utils.Log(1, fmt.Sprintf("Running Query: %v", m))
|
utils.Log(1, fmt.Sprintf("Running Query: %v", m))
|
||||||
_, err := DbSession.Exec(db.Raw(m + ";"))
|
db := DbSession.Raw(m)
|
||||||
ran++
|
ran++
|
||||||
if err != nil {
|
if db.Error != nil {
|
||||||
utils.Log(2, err)
|
utils.Log(2, db.Error)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -252,7 +322,7 @@ func RunDatabaseUpgrades() error {
|
||||||
utils.Log(1, fmt.Sprintf("Database Upgraded %v queries ran, current #%v", ran, currentMigration))
|
utils.Log(1, fmt.Sprintf("Database Upgraded %v queries ran, current #%v", ran, currentMigration))
|
||||||
CoreApp, err = SelectCore()
|
CoreApp, err = SelectCore()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
return err
|
||||||
}
|
}
|
||||||
CoreApp.MigrationId = currentMigration
|
CoreApp.MigrationId = currentMigration
|
||||||
UpdateCore(CoreApp)
|
UpdateCore(CoreApp)
|
||||||
|
@ -260,43 +330,77 @@ func RunDatabaseUpgrades() error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
func DropDatabase() error {
|
func (db *DbConfig) SeedSchema() (string, string, error) {
|
||||||
utils.Log(1, "Dropping Database Tables...")
|
utils.Log(1, "Seeding Schema Database with Dummy Data...")
|
||||||
down, err := source.SqlBox.String("down.sql")
|
dir := utils.Directory
|
||||||
|
var cmd string
|
||||||
|
switch db.DbConn {
|
||||||
|
case "sqlite":
|
||||||
|
cmd = fmt.Sprintf("cat %v/source/sql/sqlite_up.sql | sqlite3 %v/statup.db", dir, dir)
|
||||||
|
case "mysql":
|
||||||
|
cmd = fmt.Sprintf("mysql -h %v -P %v -u %v --password=%v %v < %v/source/sql/mysql_up.sql", Configs.DbHost, Configs.DbPort, Configs.DbUser, Configs.DbPass, Configs.DbData, dir)
|
||||||
|
case "postgres":
|
||||||
|
cmd = fmt.Sprintf("PGPASSWORD=%v psql -U %v -h %v -d %v -1 -f %v/source/sql/postgres_up.sql", db.DbPass, db.DbUser, db.DbHost, db.DbData, dir)
|
||||||
|
}
|
||||||
|
out, outErr, err := utils.Command(cmd)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return out, outErr, err
|
||||||
}
|
}
|
||||||
requests := strings.Split(down, ";")
|
return out, outErr, err
|
||||||
for _, request := range requests {
|
|
||||||
_, err := DbSession.Exec(request)
|
|
||||||
if err != nil {
|
|
||||||
utils.Log(2, err)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func CreateDatabase() error {
|
func (db *DbConfig) SeedDatabase() (string, string, error) {
|
||||||
|
utils.Log(1, "Seeding Database with Dummy Data...")
|
||||||
|
dir := utils.Directory
|
||||||
|
var cmd string
|
||||||
|
switch db.DbConn {
|
||||||
|
case "sqlite":
|
||||||
|
cmd = fmt.Sprintf("cat %v/dev/sqlite_seed.sql | sqlite3 %v/statup.db", dir, dir)
|
||||||
|
case "mysql":
|
||||||
|
cmd = fmt.Sprintf("mysql -h %v -P %v -u %v --password=%v %v < %v/dev/mysql_seed.sql", Configs.DbHost, Configs.DbPort, Configs.DbUser, Configs.DbPass, Configs.DbData, dir)
|
||||||
|
case "postgres":
|
||||||
|
cmd = fmt.Sprintf("PGPASSWORD=%v psql -U %v -h %v -d %v -1 -f %v/dev/postgres_seed.sql", db.DbPass, db.DbUser, db.DbHost, db.DbData, dir)
|
||||||
|
}
|
||||||
|
out, outErr, err := utils.Command(cmd)
|
||||||
|
return out, outErr, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func (db *DbConfig) DropDatabase() error {
|
||||||
|
utils.Log(1, "Dropping Database Tables...")
|
||||||
|
err := DbSession.DropTableIfExists("checkins")
|
||||||
|
err = DbSession.DropTableIfExists("communication")
|
||||||
|
err = DbSession.DropTableIfExists("core")
|
||||||
|
err = DbSession.DropTableIfExists("failures")
|
||||||
|
err = DbSession.DropTableIfExists("hits")
|
||||||
|
err = DbSession.DropTableIfExists("services")
|
||||||
|
err = DbSession.DropTableIfExists("users")
|
||||||
|
return err.Error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (db *DbConfig) CreateDatabase() error {
|
||||||
utils.Log(1, "Creating Database Tables...")
|
utils.Log(1, "Creating Database Tables...")
|
||||||
sql := "postgres_up.sql"
|
err := DbSession.CreateTable(&types.Checkin{})
|
||||||
if CoreApp.DbConnection == "mysql" {
|
err = DbSession.Table("communication").CreateTable(¬ifiers.Notification{})
|
||||||
sql = "mysql_up.sql"
|
err = DbSession.Table("core").CreateTable(&types.Core{})
|
||||||
} else if CoreApp.DbConnection == "sqlite" {
|
err = DbSession.CreateTable(&types.Failure{})
|
||||||
sql = "sqlite_up.sql"
|
err = DbSession.CreateTable(&types.Hit{})
|
||||||
}
|
err = DbSession.CreateTable(&types.Service{})
|
||||||
up, err := source.SqlBox.String(sql)
|
err = DbSession.CreateTable(&types.User{})
|
||||||
requests := strings.Split(up, ";")
|
utils.Log(1, "Statup Database Created")
|
||||||
for _, request := range requests {
|
return err.Error
|
||||||
_, err := DbSession.Exec(request)
|
}
|
||||||
if err != nil {
|
|
||||||
utils.Log(2, err)
|
func (db *DbConfig) MigrateDatabase() error {
|
||||||
}
|
utils.Log(1, "Migrating Database Tables...")
|
||||||
}
|
err := DbSession.AutoMigrate(&types.Checkin{})
|
||||||
//secret := NewSHA1Hash()
|
err = DbSession.Table("communication").AutoMigrate(¬ifiers.Notification{})
|
||||||
//db.QueryRow("INSERT INTO core (secret, version) VALUES ($1, $2);", secret, VERSION).Scan()
|
err = DbSession.Table("core").AutoMigrate(&types.Core{})
|
||||||
utils.Log(1, "Database Created")
|
err = DbSession.AutoMigrate(&types.Failure{})
|
||||||
//SampleData()
|
err = DbSession.AutoMigrate(&types.Hit{})
|
||||||
return err
|
err = DbSession.AutoMigrate(&types.Service{})
|
||||||
|
err = DbSession.AutoMigrate(&types.User{})
|
||||||
|
utils.Log(1, "Statup Database Migrated")
|
||||||
|
return err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *DbConfig) Clean() *DbConfig {
|
func (c *DbConfig) Clean() *DbConfig {
|
||||||
|
|
|
@ -19,12 +19,12 @@ import (
|
||||||
"github.com/fatih/structs"
|
"github.com/fatih/structs"
|
||||||
"github.com/hunterlong/statup/notifiers"
|
"github.com/hunterlong/statup/notifiers"
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"upper.io/db.v3/lib/sqlbuilder"
|
"github.com/jinzhu/gorm"
|
||||||
)
|
)
|
||||||
|
|
||||||
func OnLoad(db sqlbuilder.Database) {
|
func OnLoad(db *gorm.DB) {
|
||||||
for _, p := range CoreApp.AllPlugins {
|
for _, p := range CoreApp.AllPlugins {
|
||||||
p.OnLoad(db)
|
p.OnLoad(*db)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -25,7 +25,11 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
func injectDatabase() {
|
func injectDatabase() {
|
||||||
DbConnection(Configs.Connection, false, utils.Directory)
|
Configs.Connect(false, utils.Directory)
|
||||||
|
}
|
||||||
|
|
||||||
|
func GenerateSeed() {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func ExportIndexHTML() string {
|
func ExportIndexHTML() string {
|
||||||
|
|
|
@ -32,23 +32,19 @@ func (s *Service) CreateFailure(f *types.Failure) (int64, error) {
|
||||||
f.CreatedAt = time.Now()
|
f.CreatedAt = time.Now()
|
||||||
f.Service = s.Id
|
f.Service = s.Id
|
||||||
s.Failures = append(s.Failures, f)
|
s.Failures = append(s.Failures, f)
|
||||||
col := DbSession.Collection("failures")
|
row := failuresDB().Create(f)
|
||||||
uuid, err := col.Insert(f)
|
if row.Error != nil {
|
||||||
if err != nil {
|
utils.Log(3, row.Error)
|
||||||
utils.Log(3, err)
|
return 0, row.Error
|
||||||
return 0, err
|
|
||||||
}
|
}
|
||||||
if uuid == nil {
|
return f.Id, row.Error
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
return uuid.(int64), err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) AllFailures() []*types.Failure {
|
func (s *Service) AllFailures() []*types.Failure {
|
||||||
var fails []*types.Failure
|
var fails []*types.Failure
|
||||||
col := DbSession.Collection("failures").Find("service", s.Id).OrderBy("-id")
|
col := failuresDB().Where("service = ?", s.Id).Order("id desc")
|
||||||
err := col.All(&fails)
|
err := col.Find(&fails)
|
||||||
if err != nil {
|
if err.Error != nil {
|
||||||
utils.Log(3, fmt.Sprintf("Issue getting failures for service %v, %v", s.Name, err))
|
utils.Log(3, fmt.Sprintf("Issue getting failures for service %v, %v", s.Name, err))
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
@ -56,8 +52,8 @@ func (s *Service) AllFailures() []*types.Failure {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Service) DeleteFailures() {
|
func (u *Service) DeleteFailures() {
|
||||||
_, err := DbSession.Exec(`DELETE FROM failures WHERE service = ?`, u.Id)
|
err := DbSession.Exec(`DELETE FROM failures WHERE service = ?`, u.Id)
|
||||||
if err != nil {
|
if err.Error != nil {
|
||||||
utils.Log(3, fmt.Sprintf("failed to delete all failures: %v", err))
|
utils.Log(3, fmt.Sprintf("failed to delete all failures: %v", err))
|
||||||
}
|
}
|
||||||
u.Failures = nil
|
u.Failures = nil
|
||||||
|
@ -65,8 +61,8 @@ func (u *Service) DeleteFailures() {
|
||||||
|
|
||||||
func (s *Service) LimitedFailures() []*Failure {
|
func (s *Service) LimitedFailures() []*Failure {
|
||||||
var failArr []*Failure
|
var failArr []*Failure
|
||||||
col := DbSession.Collection("failures").Find("service", s.Id).OrderBy("-id").Limit(10)
|
col := failuresDB().Where("service = ?", s.Id).Order("id desc").Limit(10)
|
||||||
col.All(&failArr)
|
col.Find(&failArr)
|
||||||
return failArr
|
return failArr
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -83,30 +79,37 @@ func (f *Failure) Ago() string {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (f *Failure) Delete() error {
|
func (f *Failure) Delete() error {
|
||||||
col := DbSession.Collection("failures").Find("id", f.Id)
|
db := failuresDB().Delete(f)
|
||||||
return col.Delete()
|
return db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func CountFailures() uint64 {
|
func CountFailures() uint64 {
|
||||||
col := DbSession.Collection("failures").Find()
|
var count uint64
|
||||||
amount, err := col.Count()
|
err := failuresDB().Count(&count)
|
||||||
if err != nil {
|
if err.Error != nil {
|
||||||
utils.Log(2, err)
|
utils.Log(2, err.Error)
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
return amount
|
return count
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Service) TotalFailures24() (uint64, error) {
|
||||||
|
ago := time.Now().Add(-24 * time.Hour)
|
||||||
|
return s.TotalFailuresSince(ago)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) TotalFailures() (uint64, error) {
|
func (s *Service) TotalFailures() (uint64, error) {
|
||||||
col := DbSession.Collection("failures").Find("service", s.Id)
|
var count uint64
|
||||||
amount, err := col.Count()
|
rows := failuresDB().Where("service = ?", s.Id)
|
||||||
return amount, err
|
err := rows.Count(count)
|
||||||
|
return count, err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) TotalFailures24Hours() (uint64, error) {
|
func (s *Service) TotalFailuresSince(ago time.Time) (uint64, error) {
|
||||||
col := DbSession.Collection("failures").Find("service", s.Id)
|
var count uint64
|
||||||
amount, err := col.Count()
|
rows := failuresDB().Where("service = ? AND created_at > ?", s.Id, ago.Format("2006-01-02 15:04:05"))
|
||||||
return amount, err
|
err := rows.Count(&count)
|
||||||
|
return count, err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (f *Failure) ParseError() string {
|
func (f *Failure) ParseError() string {
|
||||||
|
|
53
core/hits.go
53
core/hits.go
|
@ -19,40 +19,33 @@ import (
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
"time"
|
"time"
|
||||||
"upper.io/db.v3"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type Hit struct {
|
type Hit struct {
|
||||||
*types.Hit
|
*types.Hit
|
||||||
}
|
}
|
||||||
|
|
||||||
func hitCol() db.Collection {
|
|
||||||
return DbSession.Collection("hits")
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *Service) CreateHit(h *types.Hit) (int64, error) {
|
func (s *Service) CreateHit(h *types.Hit) (int64, error) {
|
||||||
h.CreatedAt = time.Now()
|
db := hitsDB().Create(&h)
|
||||||
h.Service = s.Id
|
if db.Error != nil {
|
||||||
uuid, err := hitCol().Insert(h)
|
utils.Log(2, db.Error)
|
||||||
if uuid == nil {
|
return 0, db.Error
|
||||||
utils.Log(2, err)
|
|
||||||
return 0, err
|
|
||||||
}
|
}
|
||||||
return uuid.(int64), err
|
return h.Id, db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) Hits() ([]*Hit, error) {
|
func (s *Service) Hits() ([]*Hit, error) {
|
||||||
var hits []*Hit
|
var hits []*Hit
|
||||||
col := hitCol().Find("service", s.Id).OrderBy("-id")
|
col := hitsDB().Where("service = ?", s.Id).Order("id desc")
|
||||||
err := col.All(&hits)
|
err := col.Find(&hits)
|
||||||
return hits, err
|
return hits, err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) LimitedHits() ([]*Hit, error) {
|
func (s *Service) LimitedHits() ([]*Hit, error) {
|
||||||
var hits []*Hit
|
var hits []*Hit
|
||||||
col := hitCol().Find("service", s.Id).OrderBy("-id").Limit(1024)
|
col := hitsDB().Where("service = ?", s.Id).Order("id desc").Limit(1024)
|
||||||
err := col.All(&hits)
|
err := col.Find(&hits)
|
||||||
return reverseHits(hits), err
|
return reverseHits(hits), err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func reverseHits(input []*Hit) []*Hit {
|
func reverseHits(input []*Hit) []*Hit {
|
||||||
|
@ -64,15 +57,27 @@ func reverseHits(input []*Hit) []*Hit {
|
||||||
|
|
||||||
func (s *Service) SelectHitsGroupBy(group string) ([]*Hit, error) {
|
func (s *Service) SelectHitsGroupBy(group string) ([]*Hit, error) {
|
||||||
var hits []*Hit
|
var hits []*Hit
|
||||||
col := hitCol().Find("service", s.Id)
|
col := hitsDB().Where("service = ?", s.Id)
|
||||||
err := col.All(&hits)
|
err := col.Find(&hits)
|
||||||
return hits, err
|
return hits, err.Error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Service) hits() {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) TotalHits() (uint64, error) {
|
func (s *Service) TotalHits() (uint64, error) {
|
||||||
col := hitCol().Find("service", s.Id)
|
var count uint64
|
||||||
amount, err := col.Count()
|
col := hitsDB().Where("service = ?", s.Id)
|
||||||
return amount, err
|
err := col.Count(&count)
|
||||||
|
return count, err.Error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Service) TotalHitsSince(ago time.Time) (uint64, error) {
|
||||||
|
var count uint64
|
||||||
|
rows := hitsDB().Where("service = ? AND created_at > ?", s.Id, ago.Format("2006-01-02 15:04:05"))
|
||||||
|
err := rows.Count(&count)
|
||||||
|
return count, err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) Sum() (float64, error) {
|
func (s *Service) Sum() (float64, error) {
|
||||||
|
|
|
@ -22,7 +22,6 @@ import (
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
"strconv"
|
"strconv"
|
||||||
"time"
|
"time"
|
||||||
"upper.io/db.v3"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type Service struct {
|
type Service struct {
|
||||||
|
@ -30,16 +29,12 @@ type Service struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
func ReturnService(s *types.Service) *Service {
|
func ReturnService(s *types.Service) *Service {
|
||||||
return &Service{Service: s}
|
return &Service{s}
|
||||||
}
|
|
||||||
|
|
||||||
func serviceCol() db.Collection {
|
|
||||||
return DbSession.Collection("services")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectService(id int64) *Service {
|
func SelectService(id int64) *Service {
|
||||||
for _, s := range CoreApp.Services() {
|
for _, s := range CoreApp.Services() {
|
||||||
if s.Id == id {
|
if s.Service.Id == id {
|
||||||
return s
|
return s
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -49,11 +44,10 @@ func SelectService(id int64) *Service {
|
||||||
func (c *Core) SelectAllServices() ([]*types.Service, error) {
|
func (c *Core) SelectAllServices() ([]*types.Service, error) {
|
||||||
var services []*types.Service
|
var services []*types.Service
|
||||||
var servs []*types.Service
|
var servs []*types.Service
|
||||||
col := serviceCol().Find().OrderBy("order_id")
|
db := servicesDB().Find(&services)
|
||||||
err := col.All(&services)
|
if db.Error != nil {
|
||||||
if err != nil {
|
utils.Log(3, fmt.Sprintf("service error: %v", db.Error))
|
||||||
utils.Log(3, fmt.Sprintf("service error: %v", err))
|
return nil, db.Error
|
||||||
return nil, err
|
|
||||||
}
|
}
|
||||||
for _, ser := range services {
|
for _, ser := range services {
|
||||||
single := ReturnService(ser)
|
single := ReturnService(ser)
|
||||||
|
@ -63,7 +57,7 @@ func (c *Core) SelectAllServices() ([]*types.Service, error) {
|
||||||
servs = append(servs, single.Service)
|
servs = append(servs, single.Service)
|
||||||
}
|
}
|
||||||
CoreApp.SetServices(servs)
|
CoreApp.SetServices(servs)
|
||||||
return services, err
|
return services, db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) ToJSON() string {
|
func (s *Service) ToJSON() string {
|
||||||
|
@ -84,12 +78,17 @@ func (s *Service) AvgTime() float64 {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) Online24() float32 {
|
func (s *Service) Online24() float32 {
|
||||||
total, _ := s.TotalHits()
|
ago := time.Now().Add(-24 * time.Hour)
|
||||||
failed, _ := s.TotalFailures24Hours()
|
return s.OnlineSince(ago)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Service) OnlineSince(ago time.Time) float32 {
|
||||||
|
failed, _ := s.TotalFailuresSince(ago)
|
||||||
if failed == 0 {
|
if failed == 0 {
|
||||||
s.Online24Hours = 100.00
|
s.Online24Hours = 100.00
|
||||||
return s.Online24Hours
|
return s.Online24Hours
|
||||||
}
|
}
|
||||||
|
total, _ := s.TotalHitsSince(ago)
|
||||||
if total == 0 {
|
if total == 0 {
|
||||||
s.Online24Hours = 0
|
s.Online24Hours = 0
|
||||||
return s.Online24Hours
|
return s.Online24Hours
|
||||||
|
@ -150,16 +149,17 @@ func (s *Service) GraphData() string {
|
||||||
var d []*DateScan
|
var d []*DateScan
|
||||||
since := time.Now().Add(time.Hour*-24 + time.Minute*0 + time.Second*0)
|
since := time.Now().Add(time.Hour*-24 + time.Minute*0 + time.Second*0)
|
||||||
sql := GroupDataBy("hits", s.Id, since, "minute")
|
sql := GroupDataBy("hits", s.Id, since, "minute")
|
||||||
dated, err := DbSession.Query(db.Raw(sql))
|
rows, err := DbSession.Raw(sql).Rows()
|
||||||
|
defer rows.Close()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(2, err)
|
utils.Log(2, err)
|
||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
for dated.Next() {
|
for rows.Next() {
|
||||||
gd := new(DateScan)
|
gd := new(DateScan)
|
||||||
var tt string
|
var tt string
|
||||||
var ff float64
|
var ff float64
|
||||||
err := dated.Scan(&tt, &ff)
|
err := rows.Scan(&tt, &ff)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(2, fmt.Sprintf("Issue loading chart data for service %v, %v", s.Name, err))
|
utils.Log(2, fmt.Sprintf("Issue loading chart data for service %v, %v", s.Name, err))
|
||||||
}
|
}
|
||||||
|
@ -178,13 +178,18 @@ func (s *Service) GraphData() string {
|
||||||
return string(data)
|
return string(data)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) AvgUptime() string {
|
func (s *Service) AvgUptime24() string {
|
||||||
failed, _ := s.TotalFailures()
|
ago := time.Now().Add(-24 * time.Hour)
|
||||||
total, _ := s.TotalHits()
|
return s.AvgUptime(ago)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Service) AvgUptime(ago time.Time) string {
|
||||||
|
failed, _ := s.TotalFailuresSince(ago)
|
||||||
if failed == 0 {
|
if failed == 0 {
|
||||||
s.TotalUptime = "100"
|
s.TotalUptime = "100"
|
||||||
return s.TotalUptime
|
return s.TotalUptime
|
||||||
}
|
}
|
||||||
|
total, _ := s.TotalHitsSince(ago)
|
||||||
if total == 0 {
|
if total == 0 {
|
||||||
s.TotalUptime = "0"
|
s.TotalUptime = "0"
|
||||||
return s.TotalUptime
|
return s.TotalUptime
|
||||||
|
@ -217,25 +222,27 @@ func updateService(service *Service) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Service) Delete() error {
|
func (u *Service) Delete() error {
|
||||||
res := serviceCol().Find("id", u.Id)
|
err := servicesDB().Delete(u)
|
||||||
err := res.Delete()
|
if err.Error != nil {
|
||||||
if err != nil {
|
utils.Log(3, fmt.Sprintf("Failed to delete service %v. %v", u.Name, err.Error))
|
||||||
utils.Log(3, fmt.Sprintf("Failed to delete service %v. %v", u.Name, err))
|
return err.Error
|
||||||
return err
|
|
||||||
}
|
}
|
||||||
u.Close()
|
u.Close()
|
||||||
CoreApp.RemoveService(u.index())
|
CoreApp.RemoveService(u.index())
|
||||||
OnDeletedService(u)
|
OnDeletedService(u)
|
||||||
return err
|
return err.Error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (u *Service) UpdateSingle(attr ...interface{}) error {
|
||||||
|
return servicesDB().Model(u).Update(attr).Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Service) Update(restart bool) error {
|
func (u *Service) Update(restart bool) error {
|
||||||
u.CreatedAt = time.Now()
|
u.CreatedAt = time.Now()
|
||||||
res := serviceCol().Find("id", u.Id)
|
err := servicesDB().Update(u)
|
||||||
err := res.Update(u)
|
if err.Error != nil {
|
||||||
if err != nil {
|
|
||||||
utils.Log(3, fmt.Sprintf("Failed to update service %v. %v", u.Name, err))
|
utils.Log(3, fmt.Sprintf("Failed to update service %v. %v", u.Name, err))
|
||||||
return err
|
return err.Error
|
||||||
}
|
}
|
||||||
if restart {
|
if restart {
|
||||||
u.Close()
|
u.Close()
|
||||||
|
@ -245,20 +252,19 @@ func (u *Service) Update(restart bool) error {
|
||||||
go u.CheckQueue(true)
|
go u.CheckQueue(true)
|
||||||
}
|
}
|
||||||
OnUpdateService(u)
|
OnUpdateService(u)
|
||||||
return err
|
return err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Service) Create() (int64, error) {
|
func (u *Service) Create() (int64, error) {
|
||||||
u.CreatedAt = time.Now()
|
u.CreatedAt = time.Now()
|
||||||
uuid, err := serviceCol().Insert(u)
|
db := servicesDB().Create(u)
|
||||||
if uuid == nil {
|
if db.Error != nil {
|
||||||
utils.Log(3, fmt.Sprintf("Failed to create service %v. %v", u.Name, err))
|
utils.Log(3, fmt.Sprintf("Failed to create service %v #%v: %v", u.Name, u.Id, db.Error))
|
||||||
return 0, err
|
return 0, db.Error
|
||||||
}
|
}
|
||||||
u.Id = uuid.(int64)
|
|
||||||
u.Start()
|
u.Start()
|
||||||
CoreApp.AddService(u.Service)
|
CoreApp.AddService(u.Service)
|
||||||
return uuid.(int64), err
|
return u.Id, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func CountOnline() int {
|
func CountOnline() int {
|
||||||
|
|
|
@ -26,23 +26,29 @@ var (
|
||||||
newServiceId int64
|
newServiceId int64
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func TestSelectHTTPService(t *testing.T) {
|
||||||
|
services, err := CoreApp.SelectAllServices()
|
||||||
|
assert.Nil(t, err)
|
||||||
|
assert.Equal(t, 18, len(services))
|
||||||
|
assert.Equal(t, "Google", services[0].Name)
|
||||||
|
assert.Equal(t, "http", services[0].Type)
|
||||||
|
}
|
||||||
|
|
||||||
func TestSelectAllServices(t *testing.T) {
|
func TestSelectAllServices(t *testing.T) {
|
||||||
services := CoreApp.Services()
|
services := CoreApp.Services()
|
||||||
for _, s := range services {
|
for _, s := range services {
|
||||||
service := s.Check(true)
|
service := s.Check(true)
|
||||||
assert.True(t, service.Online)
|
assert.True(t, service.IsRunning())
|
||||||
|
t.Logf("ID: %v %v\n", s.Id, s.Name)
|
||||||
}
|
}
|
||||||
assert.Equal(t, 5, len(services))
|
assert.Equal(t, 18, len(services))
|
||||||
}
|
|
||||||
|
|
||||||
func TestSelectHTTPService(t *testing.T) {
|
|
||||||
service := SelectService(1)
|
|
||||||
assert.Equal(t, "Google", service.Name)
|
|
||||||
assert.Equal(t, "http", service.Type)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSelectTCPService(t *testing.T) {
|
func TestSelectTCPService(t *testing.T) {
|
||||||
|
services := CoreApp.Services()
|
||||||
|
assert.Equal(t, 18, len(services))
|
||||||
service := SelectService(5)
|
service := SelectService(5)
|
||||||
|
assert.NotNil(t, service)
|
||||||
assert.Equal(t, "Google DNS", service.Name)
|
assert.Equal(t, "Google DNS", service.Name)
|
||||||
assert.Equal(t, "tcp", service.Type)
|
assert.Equal(t, "tcp", service.Type)
|
||||||
}
|
}
|
||||||
|
@ -105,9 +111,14 @@ func TestCheckTCPService(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceOnline24Hours(t *testing.T) {
|
func TestServiceOnline24Hours(t *testing.T) {
|
||||||
service := SelectService(5)
|
since, err := time.Parse(time.RFC3339, SERVICE_SINCE)
|
||||||
amount := service.Online24()
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, float32(100), amount)
|
service := SelectService(1)
|
||||||
|
assert.Equal(t, float32(83.33), service.OnlineSince(since))
|
||||||
|
service2 := SelectService(5)
|
||||||
|
assert.Equal(t, float32(100), service2.OnlineSince(since))
|
||||||
|
service3 := SelectService(18)
|
||||||
|
assert.Equal(t, float32(0), service3.OnlineSince(since))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceSmallText(t *testing.T) {
|
func TestServiceSmallText(t *testing.T) {
|
||||||
|
@ -117,30 +128,35 @@ func TestServiceSmallText(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceAvgUptime(t *testing.T) {
|
func TestServiceAvgUptime(t *testing.T) {
|
||||||
service := SelectService(5)
|
since, err := time.Parse(time.RFC3339, SERVICE_SINCE)
|
||||||
uptime := service.AvgUptime()
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, "100", uptime)
|
service := SelectService(1)
|
||||||
|
assert.Equal(t, "83.33", service.AvgUptime(since))
|
||||||
|
service2 := SelectService(5)
|
||||||
|
assert.Equal(t, "100", service2.AvgUptime(since))
|
||||||
|
service3 := SelectService(18)
|
||||||
|
assert.Equal(t, "0.00", service3.AvgUptime(since))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceHits(t *testing.T) {
|
func TestServiceHits(t *testing.T) {
|
||||||
service := SelectService(5)
|
service := SelectService(5)
|
||||||
hits, err := service.Hits()
|
hits, err := service.Hits()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, int(2), len(hits))
|
assert.Equal(t, int(5), len(hits))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceLimitedHits(t *testing.T) {
|
func TestServiceLimitedHits(t *testing.T) {
|
||||||
service := SelectService(5)
|
service := SelectService(5)
|
||||||
hits, err := service.LimitedHits()
|
hits, err := service.LimitedHits()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, int(2), len(hits))
|
assert.Equal(t, int(5), len(hits))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceTotalHits(t *testing.T) {
|
func TestServiceTotalHits(t *testing.T) {
|
||||||
service := SelectService(5)
|
service := SelectService(5)
|
||||||
hits, err := service.TotalHits()
|
hits, err := service.TotalHits()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, uint64(0x2), hits)
|
assert.Equal(t, uint64(0x5), hits)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceSum(t *testing.T) {
|
func TestServiceSum(t *testing.T) {
|
||||||
|
@ -176,7 +192,6 @@ func TestCreateService(t *testing.T) {
|
||||||
func TestViewNewService(t *testing.T) {
|
func TestViewNewService(t *testing.T) {
|
||||||
newService := SelectService(newServiceId)
|
newService := SelectService(newServiceId)
|
||||||
assert.Equal(t, "That'll do 🐢", newService.Name)
|
assert.Equal(t, "That'll do 🐢", newService.Name)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestCreateFailingHTTPService(t *testing.T) {
|
func TestCreateFailingHTTPService(t *testing.T) {
|
||||||
|
@ -195,10 +210,12 @@ func TestCreateFailingHTTPService(t *testing.T) {
|
||||||
assert.NotZero(t, newServiceId)
|
assert.NotZero(t, newServiceId)
|
||||||
newService := SelectService(newServiceId)
|
newService := SelectService(newServiceId)
|
||||||
assert.Equal(t, "Bad URL", newService.Name)
|
assert.Equal(t, "Bad URL", newService.Name)
|
||||||
|
t.Log("new service ID: ", newServiceId)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceFailedCheck(t *testing.T) {
|
func TestServiceFailedCheck(t *testing.T) {
|
||||||
service := SelectService(7)
|
service := SelectService(20)
|
||||||
|
assert.Equal(t, "Bad URL", service.Name)
|
||||||
checked := service.Check(true)
|
checked := service.Check(true)
|
||||||
assert.Equal(t, "Bad URL", checked.Name)
|
assert.Equal(t, "Bad URL", checked.Name)
|
||||||
assert.False(t, checked.Online)
|
assert.False(t, checked.Online)
|
||||||
|
@ -219,10 +236,11 @@ func TestCreateFailingTCPService(t *testing.T) {
|
||||||
assert.NotZero(t, newServiceId)
|
assert.NotZero(t, newServiceId)
|
||||||
newService := SelectService(newServiceId)
|
newService := SelectService(newServiceId)
|
||||||
assert.Equal(t, "Bad TCP", newService.Name)
|
assert.Equal(t, "Bad TCP", newService.Name)
|
||||||
|
t.Log("new failing tcp service ID: ", newServiceId)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceFailedTCPCheck(t *testing.T) {
|
func TestServiceFailedTCPCheck(t *testing.T) {
|
||||||
service := SelectService(8)
|
service := SelectService(21)
|
||||||
checked := service.Check(true)
|
checked := service.Check(true)
|
||||||
assert.Equal(t, "Bad TCP", checked.Name)
|
assert.Equal(t, "Bad TCP", checked.Name)
|
||||||
assert.False(t, checked.Online)
|
assert.False(t, checked.Online)
|
||||||
|
@ -244,13 +262,13 @@ func TestDeleteService(t *testing.T) {
|
||||||
|
|
||||||
count, err := CoreApp.SelectAllServices()
|
count, err := CoreApp.SelectAllServices()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 8, len(count))
|
assert.Equal(t, 21, len(count))
|
||||||
|
|
||||||
err = service.Delete()
|
err = service.Delete()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
|
|
||||||
services := CoreApp.Services()
|
services := CoreApp.Services()
|
||||||
assert.Equal(t, 7, len(services))
|
assert.Equal(t, 20, len(services))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServiceCloseRoutine(t *testing.T) {
|
func TestServiceCloseRoutine(t *testing.T) {
|
||||||
|
|
|
@ -28,36 +28,29 @@ type User struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
func ReturnUser(u *types.User) *User {
|
func ReturnUser(u *types.User) *User {
|
||||||
return &User{User: u}
|
return &User{u}
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectUser(id int64) (*User, error) {
|
func SelectUser(id int64) (*User, error) {
|
||||||
var user *User
|
var user User
|
||||||
col := DbSession.Collection("users")
|
err := usersDB().First(&user, id)
|
||||||
res := col.Find("id", id)
|
return &user, err.Error
|
||||||
err := res.One(&user)
|
|
||||||
return user, err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectUsername(username string) (*User, error) {
|
func SelectUsername(username string) (*User, error) {
|
||||||
var user *User
|
var user User
|
||||||
col := DbSession.Collection("users")
|
res := usersDB().Where("username = ?", username)
|
||||||
res := col.Find("username", username)
|
err := res.First(&user)
|
||||||
err := res.One(&user)
|
return &user, err.Error
|
||||||
return user, err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *User) Delete() error {
|
func (u *User) Delete() error {
|
||||||
col := DbSession.Collection("users")
|
return usersDB().Delete(u).Error
|
||||||
user := col.Find("id", u.Id)
|
|
||||||
return user.Delete()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *User) Update() error {
|
func (u *User) Update() error {
|
||||||
u.CreatedAt = time.Now()
|
u.CreatedAt = time.Now()
|
||||||
col := DbSession.Collection("users")
|
return usersDB().Update(u).Error
|
||||||
user := col.Find("id", u.Id)
|
|
||||||
return user.Update(u)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *User) Create() (int64, error) {
|
func (u *User) Create() (int64, error) {
|
||||||
|
@ -65,39 +58,36 @@ func (u *User) Create() (int64, error) {
|
||||||
u.Password = utils.HashPassword(u.Password)
|
u.Password = utils.HashPassword(u.Password)
|
||||||
u.ApiKey = utils.NewSHA1Hash(5)
|
u.ApiKey = utils.NewSHA1Hash(5)
|
||||||
u.ApiSecret = utils.NewSHA1Hash(10)
|
u.ApiSecret = utils.NewSHA1Hash(10)
|
||||||
col := DbSession.Collection("users")
|
db := usersDB().Create(u)
|
||||||
uuid, err := col.Insert(u)
|
if db.Error != nil {
|
||||||
if err != nil {
|
return 0, db.Error
|
||||||
return 0, err
|
|
||||||
}
|
}
|
||||||
if uuid == nil {
|
if u.Id == 0 {
|
||||||
utils.Log(3, fmt.Sprintf("Failed to create user %v. %v", u.Username, err))
|
utils.Log(3, fmt.Sprintf("Failed to create user %v. %v", u.Username, db.Error))
|
||||||
return 0, err
|
return 0, db.Error
|
||||||
}
|
}
|
||||||
return uuid.(int64), err
|
return u.Id, db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectAllUsers() ([]*User, error) {
|
func SelectAllUsers() ([]*User, error) {
|
||||||
var users []*User
|
var users []*User
|
||||||
col := DbSession.Collection("users").Find()
|
db := usersDB().Find(&users)
|
||||||
err := col.All(&users)
|
if db.Error != nil {
|
||||||
if err != nil {
|
utils.Log(3, fmt.Sprintf("Failed to load all users. %v", db.Error))
|
||||||
utils.Log(3, fmt.Sprintf("Failed to load all users. %v", err))
|
|
||||||
}
|
}
|
||||||
return users, err
|
return users, db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func AuthUser(username, password string) (*User, bool) {
|
func AuthUser(username, password string) (*User, bool) {
|
||||||
var auth bool
|
|
||||||
user, err := SelectUsername(username)
|
user, err := SelectUsername(username)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(2, err)
|
utils.Log(2, err)
|
||||||
return nil, false
|
return nil, false
|
||||||
}
|
}
|
||||||
if CheckHash(password, user.Password) {
|
if CheckHash(password, user.Password) {
|
||||||
auth = true
|
return user, true
|
||||||
}
|
}
|
||||||
return user, auth
|
return nil, false
|
||||||
}
|
}
|
||||||
|
|
||||||
func CheckHash(password, hash string) bool {
|
func CheckHash(password, hash string) bool {
|
||||||
|
|
|
@ -36,13 +36,13 @@ func TestCreateUser(t *testing.T) {
|
||||||
func TestSelectAllUsers(t *testing.T) {
|
func TestSelectAllUsers(t *testing.T) {
|
||||||
users, err := SelectAllUsers()
|
users, err := SelectAllUsers()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 1, len(users))
|
assert.Equal(t, 2, len(users))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSelectUser(t *testing.T) {
|
func TestSelectUser(t *testing.T) {
|
||||||
user, err := SelectUser(1)
|
user, err := SelectUser(1)
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, "test@email.com", user.Email)
|
assert.Equal(t, "info@statup.io", user.Email)
|
||||||
assert.True(t, user.Admin)
|
assert.True(t, user.Admin)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -50,7 +50,7 @@ func TestSelectUsername(t *testing.T) {
|
||||||
user, err := SelectUsername("hunter")
|
user, err := SelectUsername("hunter")
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, "test@email.com", user.Email)
|
assert.Equal(t, "test@email.com", user.Email)
|
||||||
assert.Equal(t, int64(1), user.Id)
|
assert.Equal(t, int64(2), user.Id)
|
||||||
assert.True(t, user.Admin)
|
assert.True(t, user.Admin)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -80,7 +80,7 @@ func TestCreateUser2(t *testing.T) {
|
||||||
func TestSelectAllUsersAgain(t *testing.T) {
|
func TestSelectAllUsersAgain(t *testing.T) {
|
||||||
users, err := SelectAllUsers()
|
users, err := SelectAllUsers()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, 2, len(users))
|
assert.Equal(t, 3, len(users))
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestAuthUser(t *testing.T) {
|
func TestAuthUser(t *testing.T) {
|
||||||
|
@ -88,12 +88,12 @@ func TestAuthUser(t *testing.T) {
|
||||||
assert.True(t, auth)
|
assert.True(t, auth)
|
||||||
assert.NotNil(t, user)
|
assert.NotNil(t, user)
|
||||||
assert.Equal(t, "user@email.com", user.Email)
|
assert.Equal(t, "user@email.com", user.Email)
|
||||||
assert.Equal(t, int64(2), user.Id)
|
assert.Equal(t, int64(3), user.Id)
|
||||||
assert.True(t, user.Admin)
|
assert.True(t, user.Admin)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestFailedAuthUser(t *testing.T) {
|
func TestFailedAuthUser(t *testing.T) {
|
||||||
user, auth := AuthUser("hunter", "wrongpassword")
|
user, auth := AuthUser("hunterlong", "wrongpassword")
|
||||||
assert.False(t, auth)
|
assert.False(t, auth)
|
||||||
assert.Nil(t, user)
|
assert.Nil(t, user)
|
||||||
}
|
}
|
||||||
|
@ -111,3 +111,8 @@ func TestDeleteUser(t *testing.T) {
|
||||||
err = user.Delete()
|
err = user.Delete()
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestDbConfig_Close(t *testing.T) {
|
||||||
|
err := Configs.Close()
|
||||||
|
assert.Nil(t, err)
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,142 @@
|
||||||
|
INSERT INTO core (name,description,config,api_key,api_secret,style,footer,domain,version,migration_id,use_cdn) VALUES ('Awesome Status','This is from the seed file!','config.yml','d2fead3e459bd14f570cf08527175b88b32d7faa','e351393306ea245de5f9588cbe8627c74db007c6','','Created by Hunter Long','','',0,false);
|
||||||
|
INSERT INTO services (name,domain,check_type,method,port,expected,expected_status,check_interval,post_data,order_id,timeout,created_at) VALUES
|
||||||
|
('Google','https://google.com','http','GET',0,'',200,10,'',0,10,'2018-08-31 10:42:08'),
|
||||||
|
('Statup Github','https://github.com/hunterlong/statup','http','GET',0,'',200,30,'',0,20,'2018-08-31 10:42:08'),
|
||||||
|
('JSON Users Test','https://jsonplaceholder.typicode.com/users','http','GET',0,'',200,60,'',0,30,'2018-08-31 10:42:08'),
|
||||||
|
('JSON API Tester','https://jsonplaceholder.typicode.com/posts','http','POST',0,'(title)": "((\\"|[statup])*)"',201,30,'{ "title": "statup", "body": "bar", "userId": 19999 }',0,30,'2018-08-31 10:42:08'),
|
||||||
|
('Google DNS','8.8.8.8','tcp','',53,'',0,20,'',0,120,'2018-08-31 10:42:08'),
|
||||||
|
('The Bravery - An Honest Mistake','https://www.youtube.com/watch?v=O8vzbezVru4','http','GET',0,'',0,30,'',0,15,'2018-08-31 10:42:14'),
|
||||||
|
('Upper.io','https://upper.io/db.v3/','http','GET',0,'',0,30,'',0,15,'2018-08-31 10:42:14'),
|
||||||
|
('CoinApp Status','https://status.coinapp.io','http','GET',0,'',200,1,'',0,30,'2018-08-31 10:42:16'),
|
||||||
|
('Demo Page','https://demo.statup.io','http','GET',0,'',200,2,'',0,30,'2018-08-31 10:42:16'),
|
||||||
|
('Golang','https://golang.org','http','GET',0,'',200,3,'',0,30,'2018-08-31 10:42:16'),
|
||||||
|
('Github','https://github.com/hunterlong','http','GET',0,'',200,4,'',0,30,'2018-08-31 10:42:17'),
|
||||||
|
('Santa Monica','https://www.santamonica.com','http','GET',0,'',200,5,'',0,30,'2018-08-31 10:42:17'),
|
||||||
|
('Oeschs Die Dritten','https://www.oeschs-die-dritten.ch/en/','http','GET',0,'',200,6,'',0,30,'2018-08-31 10:42:18'),
|
||||||
|
('EtherScan.io','https://etherscan.io','http','GET',0,'',200,7,'',0,30,'2018-08-31 10:42:20'),
|
||||||
|
('Test Service 7','https://www.youtube.com/watch?v=ipvEIZMMILA','http','GET',0,'',200,8,'',0,30,'2018-08-31 10:42:20'),
|
||||||
|
('Test Service 8','https://www.youtube.com/watch?v=UdaYVxYF1Ok','http','GET',0,'',200,9,'',0,30,'2018-08-31 10:42:20'),
|
||||||
|
('Test Service 9','https://www.youtube.com/watch?v=yydZbVoCbn0&t=870s','http','GET',0,'',200,10,'',0,30,'2018-08-31 10:42:20'),
|
||||||
|
('Failing URL','http://failingdomainsarenofunatall.com','http','GET',0,'',200,11,'',0,30,'2018-08-31 10:42:20');
|
||||||
|
INSERT INTO users (username,password,email,api_key,api_secret,administrator,created_at) VALUES
|
||||||
|
('admin','$2a$14$Aye3yHae0ml6WRtvdgkRnO19OFze0IKF6IOHrdLpETtwLjnPelMUm','info@statup.io','27aa701119fb561d734eb4469cf13ba2550007e2','29de07014d32fbbbb80053ef3c19b464b2b72f64',1,'2018-08-31 10:42:07');
|
||||||
|
INSERT INTO hits (service,latency,created_at) VALUES
|
||||||
|
(5,0.006504081,'2018-08-29 10:42:08'),
|
||||||
|
(3,0.202164333,'2018-08-29 10:42:08'),
|
||||||
|
(4,0.376675172,'2018-08-29 10:42:09'),
|
||||||
|
(1,0.413912204,'2018-08-29 10:42:09'),
|
||||||
|
(1,0.473912204,'2018-08-29 10:42:09'),
|
||||||
|
(2,0.528427935,'2018-08-29 10:42:09'),
|
||||||
|
(6,0.11930188,'2018-08-29 10:42:09'),
|
||||||
|
(7,0.001062722,'2018-08-29 10:42:09'),
|
||||||
|
(7,0.004046882,'2018-08-29 10:42:09'),
|
||||||
|
(6,0.063360069,'2018-08-29 10:42:09'),
|
||||||
|
(8,0.168951416,'2018-08-29 10:42:16'),
|
||||||
|
(8,0.069032763,'2018-08-29 10:42:16'),
|
||||||
|
(9,0.47712966,'2018-08-29 10:42:16'),
|
||||||
|
(10,0.104510482,'2018-08-29 10:42:17'),
|
||||||
|
(10,0.062536146,'2018-08-29 10:42:17'),
|
||||||
|
(9,0.352823197,'2018-08-29 10:42:09'),
|
||||||
|
(8,0.38226374,'2018-08-29 10:42:09'),
|
||||||
|
(11,0.857324393,'2018-08-29 10:42:17'),
|
||||||
|
(12,0.113320285,'2018-08-29 10:42:18'),
|
||||||
|
(12,0.038532321,'2018-08-29 10:42:18'),
|
||||||
|
(8,0.123430059,'2018-08-29 10:42:18'),
|
||||||
|
(11,0.625290389,'2018-08-29 10:42:18'),
|
||||||
|
(1,0.091823417,'2018-08-29 10:42:18'),
|
||||||
|
(9,0.246651097,'2018-08-29 10:42:19'),
|
||||||
|
(8,0.222901604,'2018-08-29 10:42:19'),
|
||||||
|
(13,1.600367041,'2018-08-29 10:42:20'),
|
||||||
|
(10,0.050076397,'2018-08-29 10:42:20'),
|
||||||
|
(14,0.460363958,'2018-08-29 10:42:20'),
|
||||||
|
(8,0.252590543,'2018-08-29 10:42:20'),
|
||||||
|
(15,0.144109113,'2018-08-29 10:42:20'),
|
||||||
|
(15,0.059993314,'2018-08-29 10:42:20'),
|
||||||
|
(16,0.058810662,'2018-08-29 10:42:20'),
|
||||||
|
(17,0.061824594,'2018-08-29 10:42:20'),
|
||||||
|
(16,0.074584583,'2018-08-29 10:42:20'),
|
||||||
|
(17,0.057086551,'2018-08-29 10:42:20'),
|
||||||
|
(18,0.020983572,'2018-08-29 10:42:20'),
|
||||||
|
(5,0.006504081,'2018-08-30 10:42:08'),
|
||||||
|
(3,0.202164333,'2018-08-30 10:42:08'),
|
||||||
|
(4,0.376675172,'2018-08-30 10:42:09'),
|
||||||
|
(1,0.413912204,'2018-08-30 10:42:09'),
|
||||||
|
(2,0.528427935,'2018-08-30 10:42:09'),
|
||||||
|
(6,0.11930188,'2018-08-30 10:42:14'),
|
||||||
|
(7,0.001062722,'2018-08-30 10:42:14'),
|
||||||
|
(7,0.004046882,'2018-08-30 10:42:14'),
|
||||||
|
(6,0.063360069,'2018-08-30 10:42:14'),
|
||||||
|
(8,0.168951416,'2018-08-30 10:42:16'),
|
||||||
|
(8,0.069032763,'2018-08-30 10:42:16'),
|
||||||
|
(9,0.47712966,'2018-08-30 10:42:16'),
|
||||||
|
(10,0.104510482,'2018-08-30 10:42:17'),
|
||||||
|
(10,0.062536146,'2018-08-30 10:42:17'),
|
||||||
|
(9,0.352823197,'2018-08-30 10:42:17'),
|
||||||
|
(8,0.38226374,'2018-08-30 10:42:17'),
|
||||||
|
(11,0.857324393,'2018-08-30 10:42:17'),
|
||||||
|
(12,0.113320285,'2018-08-30 10:42:18'),
|
||||||
|
(12,0.038532321,'2018-08-30 10:42:18'),
|
||||||
|
(8,0.123430059,'2018-08-30 10:42:18'),
|
||||||
|
(11,0.625290389,'2018-08-30 10:42:18'),
|
||||||
|
(1,0.091823417,'2018-08-30 10:42:18'),
|
||||||
|
(9,0.246651097,'2018-08-30 10:42:19'),
|
||||||
|
(8,0.222901604,'2018-08-30 10:42:19'),
|
||||||
|
(13,1.600367041,'2018-08-30 10:42:20'),
|
||||||
|
(10,0.050076397,'2018-08-30 10:42:20'),
|
||||||
|
(14,0.460363958,'2018-08-30 10:42:20'),
|
||||||
|
(8,0.252590543,'2018-08-30 10:42:20'),
|
||||||
|
(15,0.144109113,'2018-08-30 10:42:20'),
|
||||||
|
(15,0.059993314,'2018-08-30 10:42:20'),
|
||||||
|
(16,0.058810662,'2018-08-30 10:42:20'),
|
||||||
|
(17,0.061824594,'2018-08-30 10:42:20'),
|
||||||
|
(16,0.074584583,'2018-08-30 10:42:20'),
|
||||||
|
(17,0.057086551,'2018-08-30 10:42:20'),
|
||||||
|
(18,0.020983572,'2018-08-30 10:42:20'),
|
||||||
|
(5,0.006504081,'2018-08-31 10:42:08'),
|
||||||
|
(3,0.202164333,'2018-08-31 10:42:08'),
|
||||||
|
(4,0.376675172,'2018-08-31 10:42:09'),
|
||||||
|
(1,0.413912204,'2018-08-31 10:42:09'),
|
||||||
|
(2,0.528427935,'2018-08-31 10:42:09'),
|
||||||
|
(6,0.11930188,'2018-08-31 10:42:14'),
|
||||||
|
(7,0.001062722,'2018-08-31 10:42:14'),
|
||||||
|
(7,0.004046882,'2018-08-31 10:42:14'),
|
||||||
|
(6,0.063360069,'2018-08-31 10:42:14'),
|
||||||
|
(8,0.168951416,'2018-08-31 10:42:16'),
|
||||||
|
(8,0.069032763,'2018-08-31 10:42:16'),
|
||||||
|
(9,0.47712966,'2018-08-31 10:42:16'),
|
||||||
|
(10,0.104510482,'2018-08-31 10:42:17'),
|
||||||
|
(10,0.062536146,'2018-08-31 10:42:17'),
|
||||||
|
(9,0.352823197,'2018-08-31 10:42:17'),
|
||||||
|
(8,0.38226374,'2018-08-31 10:42:17'),
|
||||||
|
(11,0.857324393,'2018-08-31 10:42:17'),
|
||||||
|
(12,0.113320285,'2018-08-31 10:42:18'),
|
||||||
|
(12,0.038532321,'2018-08-31 10:42:18'),
|
||||||
|
(8,0.123430059,'2018-08-31 10:42:18'),
|
||||||
|
(11,0.625290389,'2018-08-31 10:42:18'),
|
||||||
|
(1,0.091823417,'2018-08-31 10:42:18'),
|
||||||
|
(9,0.246651097,'2018-08-31 10:42:19'),
|
||||||
|
(8,0.222901604,'2018-08-31 10:42:19'),
|
||||||
|
(13,1.600367041,'2018-08-31 10:42:20'),
|
||||||
|
(10,0.050076397,'2018-08-31 10:42:20'),
|
||||||
|
(14,0.460363958,'2018-08-31 10:42:20'),
|
||||||
|
(8,0.252590543,'2018-08-31 10:42:20'),
|
||||||
|
(15,0.144109113,'2018-08-31 10:42:20'),
|
||||||
|
(15,0.059993314,'2018-08-31 10:42:20'),
|
||||||
|
(16,0.058810662,'2018-08-31 10:42:20'),
|
||||||
|
(17,0.061824594,'2018-08-31 10:42:20'),
|
||||||
|
(16,0.074584583,'2018-08-31 10:42:20'),
|
||||||
|
(17,0.057086551,'2018-08-31 10:42:20'),
|
||||||
|
(18,0.020983572,'2018-08-31 10:42:20');
|
||||||
|
INSERT INTO failures (issue,method,service,created_at) VALUES
|
||||||
|
('HTTP Status Code 200 did not match 0','',18,'2018-08-28 10:42:14'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-28 10:42:14'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-29 10:42:14'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-30 10:42:14'),
|
||||||
|
('Incorrect Response','',1,'2018-08-31 10:40:14'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-31 10:42:14'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-31 10:42:14'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',18,'2018-08-31 10:42:14');
|
||||||
|
INSERT INTO communication (id,method,host,port,username,password,var1,var2,api_key,api_secret,enabled,removable,limits,created_at) VALUES
|
||||||
|
(1,'email','smtp.emailer.com',587,'exampleuser','password123','info@betatude.com','sendto@gmail.com','','',1,0,7,'2018-08-31 10:42:15'),
|
||||||
|
(2,'slack','https://webhooksurl.slack.com/***',0,'','','','','','',0,0,3,'2018-08-31 10:42:08'),
|
||||||
|
(3,'twilio','',0,'','','','','','',0,0,3,'2018-08-31 10:42:08');
|
|
@ -0,0 +1,142 @@
|
||||||
|
INSERT INTO core (name,description,config,api_key,api_secret,style,footer,domain,version,migration_id,use_cdn) VALUES ('Awesome Status','This is from the seed file!','config.yml','d2fead3e459bd14f570cf08527175b88b32d7faa','e351393306ea245de5f9588cbe8627c74db007c6','','Created by Hunter Long','DEV','',0,false);
|
||||||
|
INSERT INTO services (name,domain,check_type,method,port,expected,expected_status,check_interval,post_data,order_id,timeout,created_at) VALUES
|
||||||
|
('Google','https://google.com','http','GET',0,'',200,10,'',0,10,'2018-08-31 10:42:08.76390584-07:00'),
|
||||||
|
('Statup Github','https://github.com/hunterlong/statup','http','GET',0,'',200,30,'',0,20,'2018-08-31 10:42:08.764977938-07:00'),
|
||||||
|
('JSON Users Test','https://jsonplaceholder.typicode.com/users','http','GET',0,'',200,60,'',0,30,'2018-08-31 10:42:08.765794226-07:00'),
|
||||||
|
('JSON API Tester','https://jsonplaceholder.typicode.com/posts','http','POST',0,'(title)": "((\\"|[statup])*)"',201,30,'{ "title": "statup", "body": "bar", "userId": 19999 }',0,30,'2018-08-31 10:42:08.766542311-07:00'),
|
||||||
|
('Google DNS','8.8.8.8','tcp','',53,'',0,20,'',0,120,'2018-08-31 10:42:08.767327346-07:00'),
|
||||||
|
('The Bravery - An Honest Mistake','https://www.youtube.com/watch?v=O8vzbezVru4','http','GET',0,'',0,30,'',0,15,'2018-08-31 10:42:14.201305666-07:00'),
|
||||||
|
('Upper.io','https://upper.io/db.v3/','http','GET',0,'',0,30,'',0,15,'2018-08-31 10:42:14.201305666-07:00'),
|
||||||
|
('CoinApp Status','https://status.coinapp.io','http','GET',0,'',200,1,'',0,30,'2018-08-31 10:42:16.097416218-07:00'),
|
||||||
|
('Demo Page','https://demo.statup.io','http','GET',0,'',200,2,'',0,30,'2018-08-31 10:42:16.360051225-07:00'),
|
||||||
|
('Golang','https://golang.org','http','GET',0,'',200,3,'',0,30,'2018-08-31 10:42:16.923478722-07:00'),
|
||||||
|
('Github','https://github.com/hunterlong','http','GET',0,'',200,4,'',0,30,'2018-08-31 10:42:17.075544885-07:00'),
|
||||||
|
('Santa Monica','https://www.santamonica.com','http','GET',0,'',200,5,'',0,30,'2018-08-31 10:42:17.946947674-07:00'),
|
||||||
|
('Oeschs Die Dritten','https://www.oeschs-die-dritten.ch/en/','http','GET',0,'',200,6,'',0,30,'2018-08-31 10:42:18.083709297-07:00'),
|
||||||
|
('EtherScan.io','https://etherscan.io','http','GET',0,'',200,7,'',0,30,'2018-08-31 10:42:20.020969513-07:00'),
|
||||||
|
('Test Service 7','https://www.youtube.com/watch?v=ipvEIZMMILA','http','GET',0,'',200,8,'',0,30,'2018-08-31 10:42:20.50135711-07:00'),
|
||||||
|
('Test Service 8','https://www.youtube.com/watch?v=UdaYVxYF1Ok','http','GET',0,'',200,9,'',0,30,'2018-08-31 10:42:20.651218082-07:00'),
|
||||||
|
('Test Service 9','https://www.youtube.com/watch?v=yydZbVoCbn0&t=870s','http','GET',0,'',200,10,'',0,30,'2018-08-31 10:42:20.725479695-07:00'),
|
||||||
|
('Failing URL','http://failingdomainsarenofunatall.com','http','GET',0,'',200,11,'',0,30,'2018-08-31 10:42:20.799471402-07:00');
|
||||||
|
INSERT INTO users (username,password,email,api_key,api_secret,administrator,created_at) VALUES
|
||||||
|
('admin','$2a$14$Aye3yHae0ml6WRtvdgkRnO19OFze0IKF6IOHrdLpETtwLjnPelMUm','info@statup.io','27aa701119fb561d734eb4469cf13ba2550007e2','29de07014d32fbbbb80053ef3c19b464b2b72f64',true,'2018-08-31 10:42:07.684406458-07:00');
|
||||||
|
INSERT INTO hits (service,latency,created_at) VALUES
|
||||||
|
(5,0.006504081,'2018-08-29 10:42:08.779875117-07:00'),
|
||||||
|
(3,0.202164333,'2018-08-29 10:42:08.977187173-07:00'),
|
||||||
|
(4,0.376675172,'2018-08-29 10:42:09.151858662-07:00'),
|
||||||
|
(1,0.413912204,'2018-08-29 10:42:09.188850317-07:00'),
|
||||||
|
(1,0.473912204,'2018-08-29 10:42:10.118850317-07:00'),
|
||||||
|
(2,0.528427935,'2018-08-29 10:42:09.310642068-07:00'),
|
||||||
|
(6,0.11930188,'2018-08-29 10:42:14.133392018-07:00'),
|
||||||
|
(7,0.001062722,'2018-08-29 10:42:14.148258553-07:00'),
|
||||||
|
(7,0.004046882,'2018-08-29 10:42:14.156087817-07:00'),
|
||||||
|
(6,0.063360069,'2018-08-29 10:42:14.205383358-07:00'),
|
||||||
|
(8,0.168951416,'2018-08-29 10:42:16.346340211-07:00'),
|
||||||
|
(8,0.069032763,'2018-08-29 10:42:16.421634189-07:00'),
|
||||||
|
(9,0.47712966,'2018-08-29 10:42:16.91309317-07:00'),
|
||||||
|
(10,0.104510482,'2018-08-29 10:42:17.065673146-07:00'),
|
||||||
|
(10,0.062536146,'2018-08-29 10:42:17.134754949-07:00'),
|
||||||
|
(9,0.352823197,'2018-08-29 10:42:17.272174866-07:00'),
|
||||||
|
(8,0.38226374,'2018-08-29 10:42:17.738731999-07:00'),
|
||||||
|
(11,0.857324393,'2018-08-29 10:42:17.939738264-07:00'),
|
||||||
|
(12,0.113320285,'2018-08-29 10:42:18.073586363-07:00'),
|
||||||
|
(12,0.038532321,'2018-08-29 10:42:18.119730063-07:00'),
|
||||||
|
(8,0.123430059,'2018-08-29 10:42:18.479407581-07:00'),
|
||||||
|
(11,0.625290389,'2018-08-29 10:42:18.5715553-07:00'),
|
||||||
|
(1,0.091823417,'2018-08-29 10:42:18.868788983-07:00'),
|
||||||
|
(9,0.246651097,'2018-08-29 10:42:19.165697332-07:00'),
|
||||||
|
(8,0.222901604,'2018-08-29 10:42:19.57929225-07:00'),
|
||||||
|
(13,1.600367041,'2018-08-29 10:42:20.010203546-07:00'),
|
||||||
|
(10,0.050076397,'2018-08-29 10:42:20.12391038-07:00'),
|
||||||
|
(14,0.460363958,'2018-08-29 10:42:20.495937751-07:00'),
|
||||||
|
(8,0.252590543,'2018-08-29 10:42:20.609139136-07:00'),
|
||||||
|
(15,0.144109113,'2018-08-29 10:42:20.64756516-07:00'),
|
||||||
|
(15,0.059993314,'2018-08-29 10:42:20.710322678-07:00'),
|
||||||
|
(16,0.058810662,'2018-08-29 10:42:20.712087274-07:00'),
|
||||||
|
(17,0.061824594,'2018-08-29 10:42:20.791266761-07:00'),
|
||||||
|
(16,0.074584583,'2018-08-29 10:42:20.797581163-07:00'),
|
||||||
|
(17,0.057086551,'2018-08-29 10:42:20.854020864-07:00'),
|
||||||
|
(18,0.020983572,'2018-08-29 10:42:20.864610424-07:00'),
|
||||||
|
(5,0.006504081,'2018-08-30 10:42:08.779875117-07:00'),
|
||||||
|
(3,0.202164333,'2018-08-30 10:42:08.977187173-07:00'),
|
||||||
|
(4,0.376675172,'2018-08-30 10:42:09.151858662-07:00'),
|
||||||
|
(1,0.413912204,'2018-08-30 10:42:09.188850317-07:00'),
|
||||||
|
(2,0.528427935,'2018-08-30 10:42:09.310642068-07:00'),
|
||||||
|
(6,0.11930188,'2018-08-30 10:42:14.133392018-07:00'),
|
||||||
|
(7,0.001062722,'2018-08-30 10:42:14.148258553-07:00'),
|
||||||
|
(7,0.004046882,'2018-08-30 10:42:14.156087817-07:00'),
|
||||||
|
(6,0.063360069,'2018-08-30 10:42:14.205383358-07:00'),
|
||||||
|
(8,0.168951416,'2018-08-30 10:42:16.346340211-07:00'),
|
||||||
|
(8,0.069032763,'2018-08-30 10:42:16.421634189-07:00'),
|
||||||
|
(9,0.47712966,'2018-08-30 10:42:16.91309317-07:00'),
|
||||||
|
(10,0.104510482,'2018-08-30 10:42:17.065673146-07:00'),
|
||||||
|
(10,0.062536146,'2018-08-30 10:42:17.134754949-07:00'),
|
||||||
|
(9,0.352823197,'2018-08-30 10:42:17.272174866-07:00'),
|
||||||
|
(8,0.38226374,'2018-08-30 10:42:17.738731999-07:00'),
|
||||||
|
(11,0.857324393,'2018-08-30 10:42:17.939738264-07:00'),
|
||||||
|
(12,0.113320285,'2018-08-30 10:42:18.073586363-07:00'),
|
||||||
|
(12,0.038532321,'2018-08-30 10:42:18.119730063-07:00'),
|
||||||
|
(8,0.123430059,'2018-08-30 10:42:18.479407581-07:00'),
|
||||||
|
(11,0.625290389,'2018-08-30 10:42:18.5715553-07:00'),
|
||||||
|
(1,0.091823417,'2018-08-30 10:42:18.868788983-07:00'),
|
||||||
|
(9,0.246651097,'2018-08-30 10:42:19.165697332-07:00'),
|
||||||
|
(8,0.222901604,'2018-08-30 10:42:19.57929225-07:00'),
|
||||||
|
(13,1.600367041,'2018-08-30 10:42:20.010203546-07:00'),
|
||||||
|
(10,0.050076397,'2018-08-30 10:42:20.12391038-07:00'),
|
||||||
|
(14,0.460363958,'2018-08-30 10:42:20.495937751-07:00'),
|
||||||
|
(8,0.252590543,'2018-08-30 10:42:20.609139136-07:00'),
|
||||||
|
(15,0.144109113,'2018-08-30 10:42:20.64756516-07:00'),
|
||||||
|
(15,0.059993314,'2018-08-30 10:42:20.710322678-07:00'),
|
||||||
|
(16,0.058810662,'2018-08-30 10:42:20.712087274-07:00'),
|
||||||
|
(17,0.061824594,'2018-08-30 10:42:20.791266761-07:00'),
|
||||||
|
(16,0.074584583,'2018-08-30 10:42:20.797581163-07:00'),
|
||||||
|
(17,0.057086551,'2018-08-30 10:42:20.854020864-07:00'),
|
||||||
|
(18,0.020983572,'2018-08-30 10:42:20.864610424-07:00'),
|
||||||
|
(5,0.006504081,'2018-08-31 10:42:08.779875117-07:00'),
|
||||||
|
(3,0.202164333,'2018-08-31 10:42:08.977187173-07:00'),
|
||||||
|
(4,0.376675172,'2018-08-31 10:42:09.151858662-07:00'),
|
||||||
|
(1,0.413912204,'2018-08-31 10:42:09.188850317-07:00'),
|
||||||
|
(2,0.528427935,'2018-08-31 10:42:09.310642068-07:00'),
|
||||||
|
(6,0.11930188,'2018-08-31 10:42:14.133392018-07:00'),
|
||||||
|
(7,0.001062722,'2018-08-31 10:42:14.148258553-07:00'),
|
||||||
|
(7,0.004046882,'2018-08-31 10:42:14.156087817-07:00'),
|
||||||
|
(6,0.063360069,'2018-08-31 10:42:14.205383358-07:00'),
|
||||||
|
(8,0.168951416,'2018-08-31 10:42:16.346340211-07:00'),
|
||||||
|
(8,0.069032763,'2018-08-31 10:42:16.421634189-07:00'),
|
||||||
|
(9,0.47712966,'2018-08-31 10:42:16.91309317-07:00'),
|
||||||
|
(10,0.104510482,'2018-08-31 10:42:17.065673146-07:00'),
|
||||||
|
(10,0.062536146,'2018-08-31 10:42:17.134754949-07:00'),
|
||||||
|
(9,0.352823197,'2018-08-31 10:42:17.272174866-07:00'),
|
||||||
|
(8,0.38226374,'2018-08-31 10:42:17.738731999-07:00'),
|
||||||
|
(11,0.857324393,'2018-08-31 10:42:17.939738264-07:00'),
|
||||||
|
(12,0.113320285,'2018-08-31 10:42:18.073586363-07:00'),
|
||||||
|
(12,0.038532321,'2018-08-31 10:42:18.119730063-07:00'),
|
||||||
|
(8,0.123430059,'2018-08-31 10:42:18.479407581-07:00'),
|
||||||
|
(11,0.625290389,'2018-08-31 10:42:18.5715553-07:00'),
|
||||||
|
(1,0.091823417,'2018-08-31 10:42:18.868788983-07:00'),
|
||||||
|
(9,0.246651097,'2018-08-31 10:42:19.165697332-07:00'),
|
||||||
|
(8,0.222901604,'2018-08-31 10:42:19.57929225-07:00'),
|
||||||
|
(13,1.600367041,'2018-08-31 10:42:20.010203546-07:00'),
|
||||||
|
(10,0.050076397,'2018-08-31 10:42:20.12391038-07:00'),
|
||||||
|
(14,0.460363958,'2018-08-31 10:42:20.495937751-07:00'),
|
||||||
|
(8,0.252590543,'2018-08-31 10:42:20.609139136-07:00'),
|
||||||
|
(15,0.144109113,'2018-08-31 10:42:20.64756516-07:00'),
|
||||||
|
(15,0.059993314,'2018-08-31 10:42:20.710322678-07:00'),
|
||||||
|
(16,0.058810662,'2018-08-31 10:42:20.712087274-07:00'),
|
||||||
|
(17,0.061824594,'2018-08-31 10:42:20.791266761-07:00'),
|
||||||
|
(16,0.074584583,'2018-08-31 10:42:20.797581163-07:00'),
|
||||||
|
(17,0.057086551,'2018-08-31 10:42:20.854020864-07:00'),
|
||||||
|
(18,0.020983572,'2018-08-31 10:42:20.864610424-07:00');
|
||||||
|
INSERT INTO failures (issue,method,service,created_at) VALUES
|
||||||
|
('HTTP Status Code 200 did not match 0','',18,'2018-08-28 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-28 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-29 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-30 10:42:14.271162743-07:00'),
|
||||||
|
('Incorrect Response','',1,'2018-08-31 10:40:14.272209564-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-31 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-31 10:42:14.272209564-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',18,'2018-08-31 10:42:14.271162743-07:00');
|
||||||
|
INSERT INTO communication (id,method,host,port,username,password,var1,var2,api_key,api_secret,enabled,removable,limits,created_at) VALUES
|
||||||
|
(1,'email','smtp.emailer.com',587,'exampleuser','password123','info@betatude.com','sendto@gmail.com','','',true,false,7,'2018-08-31 10:42:15.000829706-07:00'),
|
||||||
|
(2,'slack','https://webhooksurl.slack.com/***',0,'','','','','','',false,false,3,'2018-08-31 10:42:08.775366824-07:00'),
|
||||||
|
(3,'twilio','',0,'','','','','','',false,false,3,'2018-08-31 10:42:08.776944923-07:00');
|
|
@ -0,0 +1,142 @@
|
||||||
|
INSERT INTO core (name,description,config,api_key,api_secret,style,footer,domain,version,migration_id,use_cdn) VALUES ('Awesome Status','This is from the seed file!','config.yml','d2fead3e459bd14f570cf08527175b88b32d7faa','e351393306ea245de5f9588cbe8627c74db007c6','','Created by Hunter Long','','',0,0);
|
||||||
|
INSERT INTO services (id,name,domain,check_type,method,port,expected,expected_status,check_interval,post_data,order_id,timeout,created_at) VALUES
|
||||||
|
(1,'Google','https://google.com','http','GET',0,'',200,10,'',0,10,'2018-08-31 10:42:08.76390584-07:00'),
|
||||||
|
(2,'Statup Github','https://github.com/hunterlong/statup','http','GET',0,'',200,30,'',0,20,'2018-08-31 10:42:08.764977938-07:00'),
|
||||||
|
(3,'JSON Users Test','https://jsonplaceholder.typicode.com/users','http','GET',0,'',200,60,'',0,30,'2018-08-31 10:42:08.765794226-07:00'),
|
||||||
|
(4,'JSON API Tester','https://jsonplaceholder.typicode.com/posts','http','POST',0,'(title)": "((\\"|[statup])*)"',201,30,'{ "title": "statup", "body": "bar", "userId": 19999 }',0,30,'2018-08-31 10:42:08.766542311-07:00'),
|
||||||
|
(5,'Google DNS','8.8.8.8','tcp','',53,'',0,20,'',0,120,'2018-08-31 10:42:08.767327346-07:00'),
|
||||||
|
(6,'The Bravery - An Honest Mistake','https://www.youtube.com/watch?v=O8vzbezVru4','http','GET',0,'',0,30,'',0,15,'2018-08-31 10:42:14.201305666-07:00'),
|
||||||
|
(7,'Upper.io','https://upper.io/db.v3/','http','GET',0,'',0,30,'',0,15,'2018-08-31 10:42:14.201305666-07:00'),
|
||||||
|
(8,'CoinApp Status','https://status.coinapp.io','http','GET',0,'',200,1,'',0,30,'2018-08-31 10:42:16.097416218-07:00'),
|
||||||
|
(9,'Demo Page','https://demo.statup.io','http','GET',0,'',200,2,'',0,30,'2018-08-31 10:42:16.360051225-07:00'),
|
||||||
|
(10,'Golang','https://golang.org','http','GET',0,'',200,3,'',0,30,'2018-08-31 10:42:16.923478722-07:00'),
|
||||||
|
(11,'Github','https://github.com/hunterlong','http','GET',0,'',200,4,'',0,30,'2018-08-31 10:42:17.075544885-07:00'),
|
||||||
|
(12,'Santa Monica','https://www.santamonica.com','http','GET',0,'',200,5,'',0,30,'2018-08-31 10:42:17.946947674-07:00'),
|
||||||
|
(13,'Oeschs Die Dritten','https://www.oeschs-die-dritten.ch/en/','http','GET',0,'',200,6,'',0,30,'2018-08-31 10:42:18.083709297-07:00'),
|
||||||
|
(14,'EtherScan.io','https://etherscan.io','http','GET',0,'',200,7,'',0,30,'2018-08-31 10:42:20.020969513-07:00'),
|
||||||
|
(15,'Test Service 7','https://www.youtube.com/watch?v=ipvEIZMMILA','http','GET',0,'',200,8,'',0,30,'2018-08-31 10:42:20.50135711-07:00'),
|
||||||
|
(16,'Test Service 8','https://www.youtube.com/watch?v=UdaYVxYF1Ok','http','GET',0,'',200,9,'',0,30,'2018-08-31 10:42:20.651218082-07:00'),
|
||||||
|
(17,'Test Service 9','https://www.youtube.com/watch?v=yydZbVoCbn0&t=870s','http','GET',0,'',200,10,'',0,30,'2018-08-31 10:42:20.725479695-07:00'),
|
||||||
|
(18,'Failing URL','http://failingdomainsarenofunatall.com','http','GET',0,'',200,11,'',0,30,'2018-08-31 10:42:20.799471402-07:00');
|
||||||
|
INSERT INTO users (username,password,email,api_key,api_secret,administrator,created_at) VALUES
|
||||||
|
('admin','$2a$14$Aye3yHae0ml6WRtvdgkRnO19OFze0IKF6IOHrdLpETtwLjnPelMUm','info@statup.io','27aa701119fb561d734eb4469cf13ba2550007e2','29de07014d32fbbbb80053ef3c19b464b2b72f64',1,'2018-08-31 10:42:07.684406458-07:00');
|
||||||
|
INSERT INTO hits (service,latency,created_at) VALUES
|
||||||
|
(5,0.006504081,'2018-08-29 10:42:08.779875117-07:00'),
|
||||||
|
(3,0.202164333,'2018-08-29 10:42:08.977187173-07:00'),
|
||||||
|
(4,0.376675172,'2018-08-29 10:42:09.151858662-07:00'),
|
||||||
|
(1,0.413912204,'2018-08-29 10:42:09.188850317-07:00'),
|
||||||
|
(1,0.473912204,'2018-08-29 10:42:10.118850317-07:00'),
|
||||||
|
(2,0.528427935,'2018-08-29 10:42:09.310642068-07:00'),
|
||||||
|
(6,0.11930188,'2018-08-29 10:42:14.133392018-07:00'),
|
||||||
|
(7,0.001062722,'2018-08-29 10:42:14.148258553-07:00'),
|
||||||
|
(7,0.004046882,'2018-08-29 10:42:14.156087817-07:00'),
|
||||||
|
(6,0.063360069,'2018-08-29 10:42:14.205383358-07:00'),
|
||||||
|
(8,0.168951416,'2018-08-29 10:42:16.346340211-07:00'),
|
||||||
|
(8,0.069032763,'2018-08-29 10:42:16.421634189-07:00'),
|
||||||
|
(9,0.47712966,'2018-08-29 10:42:16.91309317-07:00'),
|
||||||
|
(10,0.104510482,'2018-08-29 10:42:17.065673146-07:00'),
|
||||||
|
(10,0.062536146,'2018-08-29 10:42:17.134754949-07:00'),
|
||||||
|
(9,0.352823197,'2018-08-29 10:42:17.272174866-07:00'),
|
||||||
|
(8,0.38226374,'2018-08-29 10:42:17.738731999-07:00'),
|
||||||
|
(11,0.857324393,'2018-08-29 10:42:17.939738264-07:00'),
|
||||||
|
(12,0.113320285,'2018-08-29 10:42:18.073586363-07:00'),
|
||||||
|
(12,0.038532321,'2018-08-29 10:42:18.119730063-07:00'),
|
||||||
|
(8,0.123430059,'2018-08-29 10:42:18.479407581-07:00'),
|
||||||
|
(11,0.625290389,'2018-08-29 10:42:18.5715553-07:00'),
|
||||||
|
(1,0.091823417,'2018-08-29 10:42:18.868788983-07:00'),
|
||||||
|
(9,0.246651097,'2018-08-29 10:42:19.165697332-07:00'),
|
||||||
|
(8,0.222901604,'2018-08-29 10:42:19.57929225-07:00'),
|
||||||
|
(13,1.600367041,'2018-08-29 10:42:20.010203546-07:00'),
|
||||||
|
(10,0.050076397,'2018-08-29 10:42:20.12391038-07:00'),
|
||||||
|
(14,0.460363958,'2018-08-29 10:42:20.495937751-07:00'),
|
||||||
|
(8,0.252590543,'2018-08-29 10:42:20.609139136-07:00'),
|
||||||
|
(15,0.144109113,'2018-08-29 10:42:20.64756516-07:00'),
|
||||||
|
(15,0.059993314,'2018-08-29 10:42:20.710322678-07:00'),
|
||||||
|
(16,0.058810662,'2018-08-29 10:42:20.712087274-07:00'),
|
||||||
|
(17,0.061824594,'2018-08-29 10:42:20.791266761-07:00'),
|
||||||
|
(16,0.074584583,'2018-08-29 10:42:20.797581163-07:00'),
|
||||||
|
(17,0.057086551,'2018-08-29 10:42:20.854020864-07:00'),
|
||||||
|
(18,0.020983572,'2018-08-29 10:42:20.864610424-07:00'),
|
||||||
|
(5,0.006504081,'2018-08-30 10:42:08.779875117-07:00'),
|
||||||
|
(3,0.202164333,'2018-08-30 10:42:08.977187173-07:00'),
|
||||||
|
(4,0.376675172,'2018-08-30 10:42:09.151858662-07:00'),
|
||||||
|
(1,0.413912204,'2018-08-30 10:42:09.188850317-07:00'),
|
||||||
|
(2,0.528427935,'2018-08-30 10:42:09.310642068-07:00'),
|
||||||
|
(6,0.11930188,'2018-08-30 10:42:14.133392018-07:00'),
|
||||||
|
(7,0.001062722,'2018-08-30 10:42:14.148258553-07:00'),
|
||||||
|
(7,0.004046882,'2018-08-30 10:42:14.156087817-07:00'),
|
||||||
|
(6,0.063360069,'2018-08-30 10:42:14.205383358-07:00'),
|
||||||
|
(8,0.168951416,'2018-08-30 10:42:16.346340211-07:00'),
|
||||||
|
(8,0.069032763,'2018-08-30 10:42:16.421634189-07:00'),
|
||||||
|
(9,0.47712966,'2018-08-30 10:42:16.91309317-07:00'),
|
||||||
|
(10,0.104510482,'2018-08-30 10:42:17.065673146-07:00'),
|
||||||
|
(10,0.062536146,'2018-08-30 10:42:17.134754949-07:00'),
|
||||||
|
(9,0.352823197,'2018-08-30 10:42:17.272174866-07:00'),
|
||||||
|
(8,0.38226374,'2018-08-30 10:42:17.738731999-07:00'),
|
||||||
|
(11,0.857324393,'2018-08-30 10:42:17.939738264-07:00'),
|
||||||
|
(12,0.113320285,'2018-08-30 10:42:18.073586363-07:00'),
|
||||||
|
(12,0.038532321,'2018-08-30 10:42:18.119730063-07:00'),
|
||||||
|
(8,0.123430059,'2018-08-30 10:42:18.479407581-07:00'),
|
||||||
|
(11,0.625290389,'2018-08-30 10:42:18.5715553-07:00'),
|
||||||
|
(1,0.091823417,'2018-08-30 10:42:18.868788983-07:00'),
|
||||||
|
(9,0.246651097,'2018-08-30 10:42:19.165697332-07:00'),
|
||||||
|
(8,0.222901604,'2018-08-30 10:42:19.57929225-07:00'),
|
||||||
|
(13,1.600367041,'2018-08-30 10:42:20.010203546-07:00'),
|
||||||
|
(10,0.050076397,'2018-08-30 10:42:20.12391038-07:00'),
|
||||||
|
(14,0.460363958,'2018-08-30 10:42:20.495937751-07:00'),
|
||||||
|
(8,0.252590543,'2018-08-30 10:42:20.609139136-07:00'),
|
||||||
|
(15,0.144109113,'2018-08-30 10:42:20.64756516-07:00'),
|
||||||
|
(15,0.059993314,'2018-08-30 10:42:20.710322678-07:00'),
|
||||||
|
(16,0.058810662,'2018-08-30 10:42:20.712087274-07:00'),
|
||||||
|
(17,0.061824594,'2018-08-30 10:42:20.791266761-07:00'),
|
||||||
|
(16,0.074584583,'2018-08-30 10:42:20.797581163-07:00'),
|
||||||
|
(17,0.057086551,'2018-08-30 10:42:20.854020864-07:00'),
|
||||||
|
(18,0.020983572,'2018-08-30 10:42:20.864610424-07:00'),
|
||||||
|
(5,0.006504081,'2018-08-31 10:42:08.779875117-07:00'),
|
||||||
|
(3,0.202164333,'2018-08-31 10:42:08.977187173-07:00'),
|
||||||
|
(4,0.376675172,'2018-08-31 10:42:09.151858662-07:00'),
|
||||||
|
(1,0.413912204,'2018-08-31 10:42:09.188850317-07:00'),
|
||||||
|
(2,0.528427935,'2018-08-31 10:42:09.310642068-07:00'),
|
||||||
|
(6,0.11930188,'2018-08-31 10:42:14.133392018-07:00'),
|
||||||
|
(7,0.001062722,'2018-08-31 10:42:14.148258553-07:00'),
|
||||||
|
(7,0.004046882,'2018-08-31 10:42:14.156087817-07:00'),
|
||||||
|
(6,0.063360069,'2018-08-31 10:42:14.205383358-07:00'),
|
||||||
|
(8,0.168951416,'2018-08-31 10:42:16.346340211-07:00'),
|
||||||
|
(8,0.069032763,'2018-08-31 10:42:16.421634189-07:00'),
|
||||||
|
(9,0.47712966,'2018-08-31 10:42:16.91309317-07:00'),
|
||||||
|
(10,0.104510482,'2018-08-31 10:42:17.065673146-07:00'),
|
||||||
|
(10,0.062536146,'2018-08-31 10:42:17.134754949-07:00'),
|
||||||
|
(9,0.352823197,'2018-08-31 10:42:17.272174866-07:00'),
|
||||||
|
(8,0.38226374,'2018-08-31 10:42:17.738731999-07:00'),
|
||||||
|
(11,0.857324393,'2018-08-31 10:42:17.939738264-07:00'),
|
||||||
|
(12,0.113320285,'2018-08-31 10:42:18.073586363-07:00'),
|
||||||
|
(12,0.038532321,'2018-08-31 10:42:18.119730063-07:00'),
|
||||||
|
(8,0.123430059,'2018-08-31 10:42:18.479407581-07:00'),
|
||||||
|
(11,0.625290389,'2018-08-31 10:42:18.5715553-07:00'),
|
||||||
|
(1,0.091823417,'2018-08-31 10:42:18.868788983-07:00'),
|
||||||
|
(9,0.246651097,'2018-08-31 10:42:19.165697332-07:00'),
|
||||||
|
(8,0.222901604,'2018-08-31 10:42:19.57929225-07:00'),
|
||||||
|
(13,1.600367041,'2018-08-31 10:42:20.010203546-07:00'),
|
||||||
|
(10,0.050076397,'2018-08-31 10:42:20.12391038-07:00'),
|
||||||
|
(14,0.460363958,'2018-08-31 10:42:20.495937751-07:00'),
|
||||||
|
(8,0.252590543,'2018-08-31 10:42:20.609139136-07:00'),
|
||||||
|
(15,0.144109113,'2018-08-31 10:42:20.64756516-07:00'),
|
||||||
|
(15,0.059993314,'2018-08-31 10:42:20.710322678-07:00'),
|
||||||
|
(16,0.058810662,'2018-08-31 10:42:20.712087274-07:00'),
|
||||||
|
(17,0.061824594,'2018-08-31 10:42:20.791266761-07:00'),
|
||||||
|
(16,0.074584583,'2018-08-31 10:42:20.797581163-07:00'),
|
||||||
|
(17,0.057086551,'2018-08-31 10:42:20.854020864-07:00'),
|
||||||
|
(18,0.020983572,'2018-08-31 10:42:20.864610424-07:00');
|
||||||
|
INSERT INTO failures (issue,method,service,created_at) VALUES
|
||||||
|
('HTTP Status Code 200 did not match 0','',18,'2018-08-28 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-28 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-29 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-30 10:42:14.271162743-07:00'),
|
||||||
|
('Incorrect Response','',1,'2018-08-31 10:40:14.272209564-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-31 10:42:14.271162743-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',6,'2018-08-31 10:42:14.272209564-07:00'),
|
||||||
|
('HTTP Status Code 200 did not match 0','',18,'2018-08-31 10:42:14.271162743-07:00');
|
||||||
|
INSERT INTO communication (id,method,host,port,username,password,var1,var2,api_key,api_secret,enabled,removable,limits,created_at) VALUES
|
||||||
|
(1,'email','smtp.emailer.com',587,'exampleuser','password123','info@betatude.com','sendto@gmail.com','','',1,0,7,'2018-08-31 10:42:15.000829706-07:00'),
|
||||||
|
(2,'slack','https://webhooksurl.slack.com/***',0,'','','','','','',0,0,3,'2018-08-31 10:42:08.775366824-07:00'),
|
||||||
|
(3,'twilio','',0,'','','','','','',0,0,3,'2018-08-31 10:42:08.776944923-07:00');
|
|
@ -36,17 +36,23 @@ const (
|
||||||
|
|
||||||
func injectDatabase() {
|
func injectDatabase() {
|
||||||
core.NewCore()
|
core.NewCore()
|
||||||
core.Configs = new(types.Config)
|
core.Configs = new(core.DbConfig)
|
||||||
core.Configs.Connection = "sqlite"
|
core.Configs.DbConn = "sqlite"
|
||||||
core.CoreApp.DbConnection = "sqlite"
|
core.CoreApp.DbConnection = "sqlite"
|
||||||
core.CoreApp.Version = "DEV"
|
core.CoreApp.Version = "DEV"
|
||||||
core.DbConnection("sqlite", false, utils.Directory)
|
core.Configs.Connect(false, utils.Directory)
|
||||||
core.InitApp()
|
core.InitApp()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func Clean() {
|
||||||
|
utils.DeleteFile(dir + "/config.yml")
|
||||||
|
utils.DeleteFile(dir + "/statup.db")
|
||||||
|
utils.DeleteDirectory(dir + "/assets")
|
||||||
|
utils.DeleteDirectory(dir + "/logs")
|
||||||
|
}
|
||||||
|
|
||||||
func TestInit(t *testing.T) {
|
func TestInit(t *testing.T) {
|
||||||
t.SkipNow()
|
Clean()
|
||||||
injectDatabase()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func formatJSON(res string, out interface{}) {
|
func formatJSON(res string, out interface{}) {
|
||||||
|
|
|
@ -97,6 +97,8 @@ func TestProcessSetupHandler(t *testing.T) {
|
||||||
rr := httptest.NewRecorder()
|
rr := httptest.NewRecorder()
|
||||||
Router().ServeHTTP(rr, req)
|
Router().ServeHTTP(rr, req)
|
||||||
assert.Equal(t, 303, rr.Code)
|
assert.Equal(t, 303, rr.Code)
|
||||||
|
assert.FileExists(t, dir+"/config.yml")
|
||||||
|
assert.FileExists(t, dir+"/statup.db")
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestCheckSetupHandler(t *testing.T) {
|
func TestCheckSetupHandler(t *testing.T) {
|
||||||
|
@ -143,7 +145,9 @@ func TestServiceChartHandler(t *testing.T) {
|
||||||
assert.Equal(t, 200, rr.Code)
|
assert.Equal(t, 200, rr.Code)
|
||||||
t.Log(body)
|
t.Log(body)
|
||||||
assert.Contains(t, body, "var ctx_1")
|
assert.Contains(t, body, "var ctx_1")
|
||||||
|
assert.Contains(t, body, "var ctx_2")
|
||||||
assert.Contains(t, body, "var ctx_3")
|
assert.Contains(t, body, "var ctx_3")
|
||||||
|
assert.Contains(t, body, "var ctx_4")
|
||||||
assert.Contains(t, body, "var ctx_5")
|
assert.Contains(t, body, "var ctx_5")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -27,7 +27,7 @@ type index struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
func IndexHandler(w http.ResponseWriter, r *http.Request) {
|
func IndexHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
if core.CoreApp.DbConnection == "" {
|
if core.Configs == nil {
|
||||||
http.Redirect(w, r, "/setup", http.StatusSeeOther)
|
http.Redirect(w, r, "/setup", http.StatusSeeOther)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -42,12 +42,12 @@ func DesktopInit(ip string, port int) {
|
||||||
var err error
|
var err error
|
||||||
exists := utils.FileExists(utils.Directory + "/statup.db")
|
exists := utils.FileExists(utils.Directory + "/statup.db")
|
||||||
if exists {
|
if exists {
|
||||||
core.Configs, err = core.LoadConfig()
|
core.Configs, err = core.LoadConfig(utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
err = core.DbConnection(core.Configs.Connection, false, utils.Directory)
|
err = core.Configs.Connect(false, utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
return
|
return
|
||||||
|
@ -68,24 +68,28 @@ func DesktopInit(ip string, port int) {
|
||||||
Location: utils.Directory,
|
Location: utils.Directory,
|
||||||
}}
|
}}
|
||||||
|
|
||||||
err = config.Save()
|
config, err = config.Save()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, err)
|
utils.Log(4, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
config.DropDatabase()
|
||||||
|
config.CreateDatabase()
|
||||||
|
core.CoreApp = config.CreateCore()
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
core.Configs, err = core.LoadConfig()
|
core.Configs, err = core.LoadConfig(utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
config.Error = err
|
config.Error = err
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
err = core.DbConnection(core.Configs.Connection, false, utils.Directory)
|
err = core.Configs.Connect(false, utils.Directory)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
core.DeleteConfig()
|
core.DeleteConfig()
|
||||||
|
|
|
@ -16,7 +16,6 @@
|
||||||
package handlers
|
package handlers
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/hunterlong/statup/core"
|
|
||||||
"net/http"
|
"net/http"
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
@ -53,6 +52,6 @@ func PluginsDownloadHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
//vars := mux.Vars(router)
|
//vars := mux.Vars(router)
|
||||||
//name := vars["name"]
|
//name := vars["name"]
|
||||||
//DownloadPlugin(name)
|
//DownloadPlugin(name)
|
||||||
core.LoadConfig()
|
//core.LoadConfig(utils.Directory)
|
||||||
http.Redirect(w, r, "/plugins", http.StatusSeeOther)
|
http.Redirect(w, r, "/plugins", http.StatusSeeOther)
|
||||||
}
|
}
|
||||||
|
|
|
@ -61,13 +61,6 @@ func PrometheusHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
w.Write([]byte(output))
|
w.Write([]byte(output))
|
||||||
}
|
}
|
||||||
|
|
||||||
func ResetDbHandler(w http.ResponseWriter, r *http.Request) {
|
|
||||||
utils.Log(1, fmt.Sprintf("Prometheus /metrics Request From IP: %v\n", r.RemoteAddr))
|
|
||||||
core.DropDatabase()
|
|
||||||
core.CoreApp = nil
|
|
||||||
w.WriteHeader(http.StatusOK)
|
|
||||||
}
|
|
||||||
|
|
||||||
func isAuthorized(r *http.Request) bool {
|
func isAuthorized(r *http.Request) bool {
|
||||||
var token string
|
var token string
|
||||||
tokens, ok := r.Header["Authorization"]
|
tokens, ok := r.Header["Authorization"]
|
||||||
|
|
|
@ -51,7 +51,6 @@ func Router() *mux.Router {
|
||||||
r.Handle("/setup", http.HandlerFunc(SetupHandler)).Methods("GET")
|
r.Handle("/setup", http.HandlerFunc(SetupHandler)).Methods("GET")
|
||||||
r.Handle("/setup", http.HandlerFunc(ProcessSetupHandler)).Methods("POST")
|
r.Handle("/setup", http.HandlerFunc(ProcessSetupHandler)).Methods("POST")
|
||||||
r.Handle("/dashboard", http.HandlerFunc(DashboardHandler)).Methods("GET")
|
r.Handle("/dashboard", http.HandlerFunc(DashboardHandler)).Methods("GET")
|
||||||
//r.Handle("/backups/create", http.HandlerFunc(BackupCreateHandler)).Methods("GET")
|
|
||||||
r.Handle("/dashboard", http.HandlerFunc(LoginHandler)).Methods("POST")
|
r.Handle("/dashboard", http.HandlerFunc(LoginHandler)).Methods("POST")
|
||||||
r.Handle("/logout", http.HandlerFunc(LogoutHandler))
|
r.Handle("/logout", http.HandlerFunc(LogoutHandler))
|
||||||
r.Handle("/services", http.HandlerFunc(ServicesHandler)).Methods("GET")
|
r.Handle("/services", http.HandlerFunc(ServicesHandler)).Methods("GET")
|
||||||
|
|
|
@ -60,8 +60,7 @@ func ReorderServiceHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
decoder.Decode(&newOrder)
|
decoder.Decode(&newOrder)
|
||||||
for _, s := range newOrder {
|
for _, s := range newOrder {
|
||||||
service := core.SelectService(s.Id)
|
service := core.SelectService(s.Id)
|
||||||
service.Order = s.Order
|
service.UpdateSingle("order_id", s.Order)
|
||||||
service.Update(false)
|
|
||||||
}
|
}
|
||||||
w.WriteHeader(http.StatusOK)
|
w.WriteHeader(http.StatusOK)
|
||||||
}
|
}
|
||||||
|
|
|
@ -16,7 +16,6 @@
|
||||||
package handlers
|
package handlers
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
|
||||||
"github.com/hunterlong/statup/core"
|
"github.com/hunterlong/statup/core"
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
|
@ -56,6 +55,7 @@ func SetupHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func ProcessSetupHandler(w http.ResponseWriter, r *http.Request) {
|
func ProcessSetupHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
|
var err error
|
||||||
if core.CoreApp.Services() != nil {
|
if core.CoreApp.Services() != nil {
|
||||||
http.Redirect(w, r, "/", http.StatusSeeOther)
|
http.Redirect(w, r, "/", http.StatusSeeOther)
|
||||||
return
|
return
|
||||||
|
@ -75,7 +75,9 @@ func ProcessSetupHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
domain := r.PostForm.Get("domain")
|
domain := r.PostForm.Get("domain")
|
||||||
email := r.PostForm.Get("email")
|
email := r.PostForm.Get("email")
|
||||||
|
|
||||||
config := &core.DbConfig{&types.DbConfig{
|
dir := utils.Directory
|
||||||
|
|
||||||
|
config := &core.DbConfig{DbConfig: &types.DbConfig{
|
||||||
DbConn: dbConn,
|
DbConn: dbConn,
|
||||||
DbHost: dbHost,
|
DbHost: dbHost,
|
||||||
DbUser: dbUser,
|
DbUser: dbUser,
|
||||||
|
@ -92,13 +94,15 @@ func ProcessSetupHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
Location: utils.Directory,
|
Location: utils.Directory,
|
||||||
}}
|
}}
|
||||||
|
|
||||||
fmt.Println(config)
|
core.Configs, err = config.Save()
|
||||||
|
|
||||||
err := config.Save()
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(4, err)
|
utils.Log(4, err)
|
||||||
|
config.Error = err
|
||||||
|
SetupResponseError(w, r, config)
|
||||||
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
core.Configs, err = core.LoadConfig(dir)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(3, err)
|
||||||
config.Error = err
|
config.Error = err
|
||||||
|
@ -106,23 +110,26 @@ func ProcessSetupHandler(w http.ResponseWriter, r *http.Request) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
core.Configs, err = core.LoadConfig()
|
err = core.Configs.Connect(false, dir)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
utils.Log(3, err)
|
utils.Log(4, err)
|
||||||
config.Error = err
|
|
||||||
SetupResponseError(w, r, config)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
err = core.DbConnection(core.Configs.Connection, false, utils.Directory)
|
|
||||||
if err != nil {
|
|
||||||
utils.Log(3, err)
|
|
||||||
core.DeleteConfig()
|
core.DeleteConfig()
|
||||||
config.Error = err
|
config.Error = err
|
||||||
SetupResponseError(w, r, config)
|
SetupResponseError(w, r, config)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
config.DropDatabase()
|
||||||
|
config.CreateDatabase()
|
||||||
|
|
||||||
|
core.CoreApp, err = config.InsertCore()
|
||||||
|
if err != nil {
|
||||||
|
utils.Log(4, err)
|
||||||
|
config.Error = err
|
||||||
|
SetupResponseError(w, r, config)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
admin := core.ReturnUser(&types.User{
|
admin := core.ReturnUser(&types.User{
|
||||||
Username: config.Username,
|
Username: config.Username,
|
||||||
Password: config.Password,
|
Password: config.Password,
|
||||||
|
|
|
@ -215,7 +215,7 @@ func (u *Email) OnSave() error {
|
||||||
|
|
||||||
// ON SERVICE FAILURE, DO YOUR OWN FUNCTIONS
|
// ON SERVICE FAILURE, DO YOUR OWN FUNCTIONS
|
||||||
func (u *Email) Install() error {
|
func (u *Email) Install() error {
|
||||||
inDb, err := emailer.Notification.IsInDatabase()
|
inDb := emailer.Notification.IsInDatabase()
|
||||||
if !inDb {
|
if !inDb {
|
||||||
newNotifer, err := InsertDatabase(u.Notification)
|
newNotifer, err := InsertDatabase(u.Notification)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -224,7 +224,7 @@ func (u *Email) Install() error {
|
||||||
}
|
}
|
||||||
utils.Log(1, fmt.Sprintf("new notifier #%v installed: %v", newNotifer, u.Method))
|
utils.Log(1, fmt.Sprintf("new notifier #%v installed: %v", newNotifer, u.Method))
|
||||||
}
|
}
|
||||||
return err
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Email) dialSend(email *EmailOutgoing) error {
|
func (u *Email) dialSend(email *EmailOutgoing) error {
|
||||||
|
|
|
@ -19,34 +19,34 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
|
"github.com/jinzhu/gorm"
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
"upper.io/db.v3"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
AllCommunications []types.AllNotifiers
|
AllCommunications []types.AllNotifiers
|
||||||
Collections db.Collection
|
Collections *gorm.DB
|
||||||
Logs []*NotificationLog
|
Logs []*NotificationLog
|
||||||
)
|
)
|
||||||
|
|
||||||
type Notification struct {
|
type Notification struct {
|
||||||
Id int64 `db:"id,omitempty" json:"id"`
|
Id int64 `gorm:"primary_key column:id" json:"id"`
|
||||||
Method string `db:"method" json:"method"`
|
Method string `gorm:"column:method" json:"method"`
|
||||||
Host string `db:"host" json:"-"`
|
Host string `gorm:"column:host" json:"-"`
|
||||||
Port int `db:"port" json:"-"`
|
Port int `gorm:"column:port" json:"-"`
|
||||||
Username string `db:"username" json:"-"`
|
Username string `gorm:"column:username" json:"-"`
|
||||||
Password string `db:"password" json:"-"`
|
Password string `gorm:"column:password" json:"-"`
|
||||||
Var1 string `db:"var1" json:"-"`
|
Var1 string `gorm:"column:var1" json:"-"`
|
||||||
Var2 string `db:"var2" json:"-"`
|
Var2 string `gorm:"column:var2" json:"-"`
|
||||||
ApiKey string `db:"api_key" json:"-"`
|
ApiKey string `gorm:"column:api_key" json:"-"`
|
||||||
ApiSecret string `db:"api_secret" json:"-"`
|
ApiSecret string `gorm:"column:api_secret" json:"-"`
|
||||||
Enabled bool `db:"enabled" json:"enabled"`
|
Enabled bool `gorm:"column:enabled" json:"enabled"`
|
||||||
Limits int `db:"limits" json:"-"`
|
Limits int `gorm:"column:limits" json:"-"`
|
||||||
Removable bool `db:"removable" json:"-"`
|
Removable bool `gorm:"column:removable" json:"-"`
|
||||||
CreatedAt time.Time `db:"created_at" json:"created_at"`
|
CreatedAt time.Time `gorm:"column:created_at" json:"created_at"`
|
||||||
Form []NotificationForm
|
Form []NotificationForm `gorm:"-" json:"-"`
|
||||||
Routine chan struct{}
|
Routine chan struct{} `gorm:"-" json:"-"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Notifier interface {
|
type Notifier interface {
|
||||||
|
@ -115,30 +115,30 @@ func reverseLogs(input []*NotificationLog) []*NotificationLog {
|
||||||
return append(reverseLogs(input[1:]), input[0])
|
return append(reverseLogs(input[1:]), input[0])
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *Notification) IsInDatabase() (bool, error) {
|
func (n *Notification) IsInDatabase() bool {
|
||||||
return Collections.Find("id", n.Id).Exists()
|
return !Collections.Find(n).RecordNotFound()
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectNotification(id int64) (*Notification, error) {
|
func SelectNotification(id int64) (*Notification, error) {
|
||||||
var notifier *Notification
|
var notifier Notification
|
||||||
err := Collections.Find("id", id).One(¬ifier)
|
err := Collections.Find(¬ifier, id)
|
||||||
return notifier, err
|
return ¬ifier, err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func (n *Notification) Update() (*Notification, error) {
|
func (n *Notification) Update() (*Notification, error) {
|
||||||
n.CreatedAt = time.Now()
|
n.CreatedAt = time.Now()
|
||||||
err := Collections.Find("id", n.Id).Update(n)
|
err := Collections.Update(n)
|
||||||
return n, err
|
return n, err.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func InsertDatabase(n *Notification) (int64, error) {
|
func InsertDatabase(n *Notification) (int64, error) {
|
||||||
n.CreatedAt = time.Now()
|
n.CreatedAt = time.Now()
|
||||||
n.Limits = 3
|
n.Limits = 3
|
||||||
newId, err := Collections.Insert(n)
|
db := Collections.Create(n)
|
||||||
if err != nil {
|
if db.Error != nil {
|
||||||
return 0, err
|
return 0, db.Error
|
||||||
}
|
}
|
||||||
return newId.(int64), err
|
return n.Id, db.Error
|
||||||
}
|
}
|
||||||
|
|
||||||
func SelectNotifier(id int64) Notifier {
|
func SelectNotifier(id int64) Notifier {
|
||||||
|
|
|
@ -18,10 +18,12 @@ package notifiers
|
||||||
import (
|
import (
|
||||||
"github.com/hunterlong/statup/types"
|
"github.com/hunterlong/statup/types"
|
||||||
"github.com/hunterlong/statup/utils"
|
"github.com/hunterlong/statup/utils"
|
||||||
|
"github.com/jinzhu/gorm"
|
||||||
|
_ "github.com/jinzhu/gorm/dialects/sqlite"
|
||||||
|
_ "github.com/mattn/go-sqlite3"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
"testing"
|
"testing"
|
||||||
"upper.io/db.v3/sqlite"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
|
@ -67,11 +69,8 @@ func init() {
|
||||||
}
|
}
|
||||||
|
|
||||||
func injectDatabase() {
|
func injectDatabase() {
|
||||||
sqliteDb := sqlite.ConnectionURL{
|
dbSession, _ := gorm.Open("sqlite3", dir+"/statup.db")
|
||||||
Database: dir + "/statup.db",
|
Collections = dbSession.Table("communication").Model(&Notification{})
|
||||||
}
|
|
||||||
dbSession, _ := sqlite.Open(sqliteDb)
|
|
||||||
Collections = dbSession.Collection("communication")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
type Tester struct {
|
type Tester struct {
|
||||||
|
@ -100,8 +99,7 @@ func TestAdd(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestIsInDatabase(t *testing.T) {
|
func TestIsInDatabase(t *testing.T) {
|
||||||
in, err := testNotifier.IsInDatabase()
|
in := testNotifier.IsInDatabase()
|
||||||
assert.Nil(t, err)
|
|
||||||
assert.False(t, in)
|
assert.False(t, in)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -110,8 +108,7 @@ func TestInsertDatabase(t *testing.T) {
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.NotZero(t, newId)
|
assert.NotZero(t, newId)
|
||||||
|
|
||||||
in, err := testNotifier.IsInDatabase()
|
in := testNotifier.IsInDatabase()
|
||||||
assert.Nil(t, err)
|
|
||||||
assert.True(t, in)
|
assert.True(t, in)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -165,7 +165,7 @@ func (u *Slack) OnSave() error {
|
||||||
|
|
||||||
// ON SERVICE FAILURE, DO YOUR OWN FUNCTIONS
|
// ON SERVICE FAILURE, DO YOUR OWN FUNCTIONS
|
||||||
func (u *Slack) Install() error {
|
func (u *Slack) Install() error {
|
||||||
inDb, err := slacker.Notification.IsInDatabase()
|
inDb := slacker.Notification.IsInDatabase()
|
||||||
if !inDb {
|
if !inDb {
|
||||||
newNotifer, err := InsertDatabase(u.Notification)
|
newNotifer, err := InsertDatabase(u.Notification)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -174,5 +174,5 @@ func (u *Slack) Install() error {
|
||||||
}
|
}
|
||||||
utils.Log(1, fmt.Sprintf("new notifier #%v installed: %v", newNotifer, u.Method))
|
utils.Log(1, fmt.Sprintf("new notifier #%v installed: %v", newNotifer, u.Method))
|
||||||
}
|
}
|
||||||
return err
|
return nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -179,7 +179,7 @@ func (u *Twilio) OnSave() error {
|
||||||
|
|
||||||
// ON SERVICE FAILURE, DO YOUR OWN FUNCTIONS
|
// ON SERVICE FAILURE, DO YOUR OWN FUNCTIONS
|
||||||
func (u *Twilio) Install() error {
|
func (u *Twilio) Install() error {
|
||||||
inDb, err := twilio.Notification.IsInDatabase()
|
inDb := twilio.Notification.IsInDatabase()
|
||||||
if !inDb {
|
if !inDb {
|
||||||
newNotifer, err := InsertDatabase(u.Notification)
|
newNotifer, err := InsertDatabase(u.Notification)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -188,5 +188,5 @@ func (u *Twilio) Install() error {
|
||||||
}
|
}
|
||||||
utils.Log(1, fmt.Sprintf("new notifier #%v installed: %v", newNotifer, u.Method))
|
utils.Log(1, fmt.Sprintf("new notifier #%v installed: %v", newNotifer, u.Method))
|
||||||
}
|
}
|
||||||
return err
|
return nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,21 +10,20 @@ CREATE TABLE core (
|
||||||
version VARCHAR(50),
|
version VARCHAR(50),
|
||||||
migration_id INT(6) NOT NULL DEFAULT 0,
|
migration_id INT(6) NOT NULL DEFAULT 0,
|
||||||
use_cdn BOOL NOT NULL DEFAULT '0'
|
use_cdn BOOL NOT NULL DEFAULT '0'
|
||||||
);
|
) ENGINE=INNODB;
|
||||||
CREATE TABLE users (
|
CREATE TABLE users (
|
||||||
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
|
id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT, PRIMARY KEY(id),
|
||||||
username VARCHAR(50) NOT NULL UNIQUE,
|
username VARCHAR(50) NOT NULL UNIQUE,
|
||||||
password text,
|
password text,
|
||||||
email VARCHAR (50),
|
email VARCHAR (50),
|
||||||
api_key VARCHAR(50),
|
api_key VARCHAR(50),
|
||||||
api_secret VARCHAR(50),
|
api_secret VARCHAR(50),
|
||||||
administrator BOOL NOT NULL DEFAULT '0',
|
administrator BOOL NOT NULL DEFAULT '0',
|
||||||
created_at DATETIME DEFAULT CURRENT_TIMESTAMP,
|
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
||||||
INDEX (id),
|
|
||||||
UNIQUE (username, email)
|
UNIQUE (username, email)
|
||||||
);
|
) ENGINE=INNODB;
|
||||||
CREATE TABLE services (
|
CREATE TABLE services (
|
||||||
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
|
id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT, PRIMARY KEY(id),
|
||||||
name VARCHAR(50),
|
name VARCHAR(50),
|
||||||
domain text,
|
domain text,
|
||||||
check_type text,
|
check_type text,
|
||||||
|
@ -35,38 +34,34 @@ CREATE TABLE services (
|
||||||
check_interval int(11),
|
check_interval int(11),
|
||||||
post_data text,
|
post_data text,
|
||||||
order_id integer default 0,
|
order_id integer default 0,
|
||||||
created_at DATETIME DEFAULT CURRENT_TIMESTAMP,
|
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
||||||
timeout INT(6) DEFAULT 30,
|
timeout INT(6) DEFAULT 30
|
||||||
INDEX (id)
|
) ENGINE=INNODB;
|
||||||
);
|
|
||||||
CREATE TABLE hits (
|
CREATE TABLE hits (
|
||||||
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
|
id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT, PRIMARY KEY(id),
|
||||||
service INTEGER NOT NULL,
|
service BIGINT(20) UNSIGNED NOT NULL,
|
||||||
latency float,
|
latency float,
|
||||||
created_at DATETIME,
|
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
||||||
INDEX (id, service),
|
|
||||||
FOREIGN KEY (service) REFERENCES services(id) ON DELETE CASCADE
|
FOREIGN KEY (service) REFERENCES services(id) ON DELETE CASCADE
|
||||||
);
|
) ENGINE=INNODB;
|
||||||
CREATE TABLE failures (
|
CREATE TABLE failures (
|
||||||
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
|
id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT, PRIMARY KEY(id),
|
||||||
issue text,
|
issue text,
|
||||||
method text,
|
method text,
|
||||||
service INTEGER NOT NULL,
|
service BIGINT(20) UNSIGNED NOT NULL,
|
||||||
created_at DATETIME,
|
created_at TIMESTAMP,
|
||||||
INDEX (id, service),
|
|
||||||
FOREIGN KEY (service) REFERENCES services(id) ON DELETE CASCADE
|
FOREIGN KEY (service) REFERENCES services(id) ON DELETE CASCADE
|
||||||
);
|
) ENGINE=INNODB;
|
||||||
CREATE TABLE checkins (
|
CREATE TABLE checkins (
|
||||||
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
|
id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT, PRIMARY KEY(id),
|
||||||
service INTEGER NOT NULL,
|
service BIGINT(20) UNSIGNED NOT NULL,
|
||||||
check_interval integer,
|
check_interval integer,
|
||||||
api text,
|
api text,
|
||||||
created_at DATETIME,
|
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
||||||
INDEX (id, service),
|
|
||||||
FOREIGN KEY (service) REFERENCES services(id) ON DELETE CASCADE
|
FOREIGN KEY (service) REFERENCES services(id) ON DELETE CASCADE
|
||||||
);
|
) ENGINE=INNODB;
|
||||||
CREATE TABLE communication (
|
CREATE TABLE communication (
|
||||||
id SERIAL PRIMARY KEY,
|
id BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT, PRIMARY KEY(id),
|
||||||
method text,
|
method text,
|
||||||
host text,
|
host text,
|
||||||
port integer,
|
port integer,
|
||||||
|
@ -79,5 +74,5 @@ CREATE TABLE communication (
|
||||||
enabled BOOL NOT NULL DEFAULT '0',
|
enabled BOOL NOT NULL DEFAULT '0',
|
||||||
removable BOOL NOT NULL DEFAULT '0',
|
removable BOOL NOT NULL DEFAULT '0',
|
||||||
limits integer,
|
limits integer,
|
||||||
created_at DATETIME
|
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
|
||||||
);
|
) ENGINE=INNODB;
|
||||||
|
|
|
@ -11,21 +11,19 @@ CREATE TABLE core (
|
||||||
migration_id integer default 0,
|
migration_id integer default 0,
|
||||||
use_cdn bool default false
|
use_cdn bool default false
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE users (
|
CREATE TABLE users (
|
||||||
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
id INTEGER PRIMARY KEY,
|
||||||
username text NOT NULL UNIQUE,
|
username text NOT NULL UNIQUE,
|
||||||
password text,
|
password text,
|
||||||
email text,
|
email text,
|
||||||
api_key text,
|
api_key text,
|
||||||
api_secret text,
|
api_secret text,
|
||||||
administrator bool,
|
administrator bool,
|
||||||
created_at DATETIME,
|
created_at TIMESTAMP,
|
||||||
UNIQUE (username, email)
|
UNIQUE (username, email)
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE services (
|
CREATE TABLE services (
|
||||||
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
id INTEGER PRIMARY KEY,
|
||||||
name text,
|
name text,
|
||||||
domain text,
|
domain text,
|
||||||
check_type text,
|
check_type text,
|
||||||
|
@ -37,34 +35,34 @@ CREATE TABLE services (
|
||||||
post_data text,
|
post_data text,
|
||||||
order_id integer default 0,
|
order_id integer default 0,
|
||||||
timeout integer default 30,
|
timeout integer default 30,
|
||||||
created_at DATETIME
|
created_at TIMESTAMP
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE hits (
|
CREATE TABLE hits (
|
||||||
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
id INTEGER PRIMARY KEY,
|
||||||
service INTEGER NOT NULL REFERENCES services(id) ON DELETE CASCADE ON UPDATE CASCADE,
|
service INTEGER NOT NULL REFERENCES services(id) ON DELETE CASCADE ON UPDATE CASCADE,
|
||||||
latency float,
|
latency float,
|
||||||
created_at DATETIME
|
created_at TIMESTAMP
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE failures (
|
CREATE TABLE failures (
|
||||||
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
id INTEGER PRIMARY KEY,
|
||||||
issue text,
|
issue text,
|
||||||
method text,
|
method text,
|
||||||
service INTEGER NOT NULL REFERENCES services(id) ON DELETE CASCADE ON UPDATE CASCADE,
|
service INTEGER NOT NULL REFERENCES services(id) ON DELETE CASCADE ON UPDATE CASCADE,
|
||||||
created_at DATETIME
|
created_at TIMESTAMP
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE checkins (
|
CREATE TABLE checkins (
|
||||||
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
id INTEGER PRIMARY KEY,
|
||||||
service INTEGER NOT NULL REFERENCES services(id) ON DELETE CASCADE ON UPDATE CASCADE,
|
service INTEGER NOT NULL REFERENCES services(id) ON DELETE CASCADE ON UPDATE CASCADE,
|
||||||
check_interval integer,
|
check_interval integer,
|
||||||
api text,
|
api text,
|
||||||
created_at DATETIME
|
created_at TIMESTAMP
|
||||||
);
|
);
|
||||||
|
|
||||||
CREATE TABLE communication (
|
CREATE TABLE communication (
|
||||||
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
id INTEGER PRIMARY KEY,
|
||||||
method text,
|
method text,
|
||||||
host text,
|
host text,
|
||||||
port integer,
|
port integer,
|
||||||
|
@ -77,7 +75,7 @@ CREATE TABLE communication (
|
||||||
enabled boolean,
|
enabled boolean,
|
||||||
removable boolean,
|
removable boolean,
|
||||||
limits integer,
|
limits integer,
|
||||||
created_at DATETIME
|
created_at TIMESTAMP
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -73,14 +73,14 @@
|
||||||
Average Response
|
Average Response
|
||||||
</div>
|
</div>
|
||||||
<div class="col-4">
|
<div class="col-4">
|
||||||
<span class="lg_number">{{.AvgUptime}}%</span>
|
<span class="lg_number">{{.AvgUptime24}}%</span>
|
||||||
Total Uptime
|
Uptime last 24 Hours
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{ if .AvgTime }}
|
{{ if .AvgUptime24 }}
|
||||||
<div class="chart-container">
|
<div class="chart-container">
|
||||||
<canvas id="service_{{ .Id }}"></canvas>
|
<canvas id="service_{{ .Id }}"></canvas>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -51,7 +51,7 @@
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="col-4">
|
<div class="col-4">
|
||||||
<span class="lg_number">{{.AvgUptime}}%</span>
|
<span class="lg_number">{{.AvgUptime24}}%</span>
|
||||||
Total Uptime
|
Total Uptime
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -1,13 +1,15 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import "time"
|
import (
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
type Checkin struct {
|
type Checkin struct {
|
||||||
Id int `db:"id,omitempty"`
|
Id int64 `gorm:"primary_key;column:id"`
|
||||||
Service int64 `db:"service"`
|
Service int64 `gorm:"index;column:service"`
|
||||||
Interval int64 `db:"check_interval"`
|
Interval int64 `gorm:"column:check_interval"`
|
||||||
Api string `db:"api"`
|
Api string `gorm:"column:api"`
|
||||||
CreatedAt time.Time `db:"created_at"`
|
CreatedAt time.Time `gorm:"column:created_at"`
|
||||||
Hits int64 `json:"hits"`
|
Hits int64 `json:"hits"`
|
||||||
Last time.Time `json:"last"`
|
Last time.Time `json:"last"`
|
||||||
CheckinInterface `json:"-"`
|
CheckinInterface `json:"-"`
|
||||||
|
|
|
@ -1,27 +1,29 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import "time"
|
import (
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
type Core struct {
|
type Core struct {
|
||||||
Name string `db:"name" json:"name"`
|
Name string `gorm:"column:name" json:"name"`
|
||||||
Description string `db:"description" json:"description,omitempty"`
|
Description string `gorm:"column:description" json:"description,omitempty"`
|
||||||
Config string `db:"config" json:"-"`
|
Config string `gorm:"column:config" json:"-"`
|
||||||
ApiKey string `db:"api_key" json:"-"`
|
ApiKey string `gorm:"column:api_key" json:"-"`
|
||||||
ApiSecret string `db:"api_secret" json:"-"`
|
ApiSecret string `gorm:"column:api_secret" json:"-"`
|
||||||
Style string `db:"style" json:"style,omitempty"`
|
Style string `gorm:"column:style" json:"style,omitempty"`
|
||||||
Footer string `db:"footer" json:"footer,omitempty"`
|
Footer string `gorm:"column:footer" json:"footer,omitempty"`
|
||||||
Domain string `db:"domain" json:"domain,omitempty"`
|
Domain string `gorm:"column:domain" json:"domain,omitempty"`
|
||||||
Version string `db:"version" json:"version"`
|
Version string `gorm:"column:version" json:"version"`
|
||||||
MigrationId int64 `db:"migration_id" json:"migration_id,omitempty"`
|
MigrationId int64 `gorm:"column:migration_id" json:"migration_id,omitempty"`
|
||||||
UseCdn bool `db:"use_cdn" json:"using_cdn,omitempty"`
|
UseCdn bool `gorm:"column:use_cdn" json:"using_cdn,omitempty"`
|
||||||
DbConnection string `json:"database"`
|
DbConnection string `gorm:"-" json:database"`
|
||||||
Started time.Time `json:"started_on"`
|
Started time.Time `gorm:"-" json:started_on"`
|
||||||
dbServices []*Service `json:"services,omitempty"`
|
dbServices []*Service `gorm:"-" json:services,omitempty"`
|
||||||
Plugins []Info `json:"-"`
|
Plugins []Info `gorm:"-" json:-"`
|
||||||
Repos []PluginJSON `json:"-"`
|
Repos []PluginJSON `gorm:"-" json:-"`
|
||||||
AllPlugins []PluginActions `json:"-"`
|
AllPlugins []PluginActions `gorm:"-" json:-"`
|
||||||
Communications []AllNotifiers `json:"-"`
|
Communications []AllNotifiers `gorm:"-" json:-"`
|
||||||
CoreInterface `json:"-"`
|
CoreInterface `gorm:"-" json:-"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Core) SetServices(s []*Service) {
|
func (c *Core) SetServices(s []*Service) {
|
||||||
|
|
|
@ -1,14 +1,16 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import "time"
|
import (
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
type Failure struct {
|
type Failure struct {
|
||||||
Id int `db:"id,omitempty" json:"id"`
|
Id int64 `gorm:"primary_key;column:id" json:"id"`
|
||||||
Issue string `db:"issue" json:"issue"`
|
Issue string `gorm:"column:issue" json:"issue"`
|
||||||
Method string `db:"method" json:"method,omitempty"`
|
Method string `gorm:"column:method" json:"method,omitempty"`
|
||||||
Service int64 `db:"service" json:"service_id"`
|
Service int64 `gorm:"index;column:service" json:"service_id"`
|
||||||
CreatedAt time.Time `db:"created_at" json:"created_at"`
|
CreatedAt time.Time `gorm:"column:created_at" json:"created_at"`
|
||||||
FailureInterface `json:"-"`
|
FailureInterface `gorm:"-" json:"-"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type FailureInterface interface {
|
type FailureInterface interface {
|
||||||
|
|
|
@ -20,33 +20,33 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
type Service struct {
|
type Service struct {
|
||||||
Id int64 `db:"id,omitempty" json:"id"`
|
Id int64 `gorm:"primary_key;column:id" json:"id"`
|
||||||
Name string `db:"name" json:"name"`
|
Name string `gorm:"column:name" json:"name"`
|
||||||
Domain string `db:"domain" json:"domain"`
|
Domain string `gorm:"column:domain" json:"domain"`
|
||||||
Expected string `db:"expected" json:"expected"`
|
Expected string `gorm:"column:expected" json:"expected"`
|
||||||
ExpectedStatus int `db:"expected_status" json:"expected_status"`
|
ExpectedStatus int `gorm:"column:expected_status" json:"expected_status"`
|
||||||
Interval int `db:"check_interval" json:"check_interval"`
|
Interval int `gorm:"column:check_interval" json:"check_interval"`
|
||||||
Type string `db:"check_type" json:"type"`
|
Type string `gorm:"column:check_type" json:"type"`
|
||||||
Method string `db:"method" json:"method"`
|
Method string `gorm:"column:method" json:"method"`
|
||||||
PostData string `db:"post_data" json:"post_data"`
|
PostData string `gorm:"column:post_data" json:"post_data"`
|
||||||
Port int `db:"port" json:"port"`
|
Port int `gorm:"column:port" json:"port"`
|
||||||
CreatedAt time.Time `db:"created_at" json:"created_at"`
|
CreatedAt time.Time `gorm:"column:created_at" json:"created_at"`
|
||||||
Timeout int `db:"timeout" json:"timeout"`
|
Timeout int `gorm:"column:timeout" json:"timeout"`
|
||||||
Order int `db:"order_id" json:"order_id"`
|
Order int `gorm:"column:order_id" json:"order_id"`
|
||||||
Online bool `json:"online"`
|
Online bool `gorm:"-" json:"online"`
|
||||||
Latency float64 `json:"latency"`
|
Latency float64 `gorm:"-" json:"latency"`
|
||||||
Online24Hours float32 `json:"24_hours_online"`
|
Online24Hours float32 `gorm:"-" json:"24_hours_online"`
|
||||||
AvgResponse string `json:"avg_response"`
|
AvgResponse string `gorm:"-" json:"avg_response"`
|
||||||
TotalUptime string `json:"uptime"`
|
TotalUptime string `gorm:"-" json:"uptime"`
|
||||||
Failures []*Failure `json:"failures"`
|
Failures []*Failure `gorm:"-" json:"failures"`
|
||||||
Checkins []*Checkin `json:"checkins"`
|
Checkins []*Checkin `gorm:"-" json:"checkins"`
|
||||||
Running chan bool `json:"-"`
|
Running chan bool `gorm:"-" json:"-"`
|
||||||
Checkpoint time.Time `json:"-"`
|
Checkpoint time.Time `gorm:"-" json:"-"`
|
||||||
LastResponse string `json:"-"`
|
LastResponse string `gorm:"-" json:"-"`
|
||||||
LastStatusCode int `json:"status_code"`
|
LastStatusCode int `gorm:"-" json:"status_code"`
|
||||||
LastOnline time.Time `json:"last_online"`
|
LastOnline time.Time `gorm:"-" json:"last_online"`
|
||||||
DnsLookup float64 `json:"dns_lookup_time"`
|
DnsLookup float64 `gorm:"-" json:"dns_lookup_time"`
|
||||||
ServiceInterface `json:"-"`
|
ServiceInterface `gorm:"-" json:"-"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type ServiceInterface interface {
|
type ServiceInterface interface {
|
||||||
|
@ -56,6 +56,7 @@ type ServiceInterface interface {
|
||||||
Delete() error
|
Delete() error
|
||||||
// Basic Method functions
|
// Basic Method functions
|
||||||
AvgTime() float64
|
AvgTime() float64
|
||||||
|
OnlineSince(time.Time) float32
|
||||||
Online24() float32
|
Online24() float32
|
||||||
SmallText() string
|
SmallText() string
|
||||||
GraphData() string
|
GraphData() string
|
||||||
|
@ -65,13 +66,15 @@ type ServiceInterface interface {
|
||||||
CreateFailure(*Failure) (int64, error)
|
CreateFailure(*Failure) (int64, error)
|
||||||
LimitedFailures() []*Failure
|
LimitedFailures() []*Failure
|
||||||
AllFailures() []*Failure
|
AllFailures() []*Failure
|
||||||
|
TotalFailuresSince(time.Time) (uint64, error)
|
||||||
|
TotalFailures24() (uint64, error)
|
||||||
TotalFailures() (uint64, error)
|
TotalFailures() (uint64, error)
|
||||||
TotalFailures24Hours() (uint64, error)
|
|
||||||
DeleteFailures()
|
DeleteFailures()
|
||||||
// Hits functions (successful responses)
|
// Hits functions (successful responses)
|
||||||
CreateHit(*Hit) (int64, error)
|
CreateHit(*Hit) (int64, error)
|
||||||
Hits() ([]*Hit, error)
|
Hits() ([]*Hit, error)
|
||||||
TotalHits() (uint64, error)
|
TotalHits() (uint64, error)
|
||||||
|
TotalHitsSince(time.Time) (uint64, error)
|
||||||
Sum() (float64, error)
|
Sum() (float64, error)
|
||||||
LimitedHits() ([]*Hit, error)
|
LimitedHits() ([]*Hit, error)
|
||||||
SelectHitsGroupBy(string) ([]*Hit, error)
|
SelectHitsGroupBy(string) ([]*Hit, error)
|
||||||
|
|
|
@ -16,9 +16,9 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"github.com/jinzhu/gorm"
|
||||||
"net/http"
|
"net/http"
|
||||||
"time"
|
"time"
|
||||||
"upper.io/db.v3/lib/sqlbuilder"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type PluginInfo struct {
|
type PluginInfo struct {
|
||||||
|
@ -41,7 +41,7 @@ type Info struct {
|
||||||
type PluginActions interface {
|
type PluginActions interface {
|
||||||
GetInfo() Info
|
GetInfo() Info
|
||||||
GetForm() string
|
GetForm() string
|
||||||
OnLoad(sqlbuilder.Database)
|
OnLoad(db gorm.DB)
|
||||||
SetInfo(map[string]interface{}) Info
|
SetInfo(map[string]interface{}) Info
|
||||||
Routes() []Routing
|
Routes() []Routing
|
||||||
OnSave(map[string]interface{})
|
OnSave(map[string]interface{})
|
||||||
|
@ -62,20 +62,10 @@ type PluginActions interface {
|
||||||
type AllNotifiers interface{}
|
type AllNotifiers interface{}
|
||||||
|
|
||||||
type Hit struct {
|
type Hit struct {
|
||||||
Id int `db:"id,omitempty"`
|
Id int64 `gorm:"primary_key;column:id"`
|
||||||
Service int64 `db:"service"`
|
Service int64 `gorm:"index;column:service"`
|
||||||
Latency float64 `db:"latency"`
|
Latency float64 `gorm:"column:latency"`
|
||||||
CreatedAt time.Time `db:"created_at"`
|
CreatedAt time.Time `gorm:"column:created_at"`
|
||||||
}
|
|
||||||
|
|
||||||
type Config struct {
|
|
||||||
Connection string `yaml:"connection"`
|
|
||||||
Host string `yaml:"host"`
|
|
||||||
Database string `yaml:"database"`
|
|
||||||
User string `yaml:"user"`
|
|
||||||
Password string `yaml:"password"`
|
|
||||||
Port string `yaml:"port"`
|
|
||||||
Secret string `yaml:"secret"`
|
|
||||||
}
|
}
|
||||||
|
|
||||||
type DbConfig struct {
|
type DbConfig struct {
|
||||||
|
|
|
@ -1,17 +1,19 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import "time"
|
import (
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
type User struct {
|
type User struct {
|
||||||
Id int64 `db:"id,omitempty" json:"id"`
|
Id int64 `gorm:"primary_key;column:id" json:"id"`
|
||||||
Username string `db:"username" json:"username"`
|
Username string `gorm:"type:varchar(100);unique;column:username;" json:"username"`
|
||||||
Password string `db:"password" json:"-"`
|
Password string `gorm:"column:password" json:"-"`
|
||||||
Email string `db:"email" json:"-"`
|
Email string `gorm:"type:varchar(100);unique;column:email" json:"-"`
|
||||||
ApiKey string `db:"api_key" json:"api_key"`
|
ApiKey string `gorm:"column:api_key" json:"api_key"`
|
||||||
ApiSecret string `db:"api_secret" json:"-"`
|
ApiSecret string `gorm:"column:api_secret" json:"-"`
|
||||||
Admin bool `db:"administrator" json:"admin"`
|
Admin bool `gorm:"column:administrator" json:"admin"`
|
||||||
CreatedAt time.Time `db:"created_at" json:"created_at"`
|
CreatedAt time.Time `gorm:"column:created_at" json:"created_at"`
|
||||||
UserInterface `json:"-"`
|
UserInterface `gorm:"-" json:"-"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type UserInterface interface {
|
type UserInterface interface {
|
||||||
|
|
|
@ -34,6 +34,10 @@ var (
|
||||||
LockLines sync.Mutex
|
LockLines sync.Mutex
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func Logger() *lumberjack.Logger {
|
||||||
|
return ljLogger
|
||||||
|
}
|
||||||
|
|
||||||
func createLog(dir string) error {
|
func createLog(dir string) error {
|
||||||
var err error
|
var err error
|
||||||
_, err = os.Stat(dir + "/logs")
|
_, err = os.Stat(dir + "/logs")
|
||||||
|
|
|
@ -16,8 +16,11 @@
|
||||||
package utils
|
package utils
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"errors"
|
||||||
"github.com/ararog/timeago"
|
"github.com/ararog/timeago"
|
||||||
|
"io"
|
||||||
"os"
|
"os"
|
||||||
|
"os/exec"
|
||||||
"regexp"
|
"regexp"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
|
@ -97,6 +100,7 @@ func FileExists(name string) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func DeleteFile(file string) error {
|
func DeleteFile(file string) error {
|
||||||
|
Log(1, "deleting file: "+file)
|
||||||
err := os.Remove(file)
|
err := os.Remove(file)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
@ -107,3 +111,56 @@ func DeleteFile(file string) error {
|
||||||
func DeleteDirectory(directory string) error {
|
func DeleteDirectory(directory string) error {
|
||||||
return os.RemoveAll(directory)
|
return os.RemoveAll(directory)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func Command(cmd string) (string, string, error) {
|
||||||
|
Log(1, "running command: "+cmd)
|
||||||
|
testCmd := exec.Command("sh", "-c", cmd)
|
||||||
|
var stdout, stderr []byte
|
||||||
|
var errStdout, errStderr error
|
||||||
|
stdoutIn, _ := testCmd.StdoutPipe()
|
||||||
|
stderrIn, _ := testCmd.StderrPipe()
|
||||||
|
testCmd.Start()
|
||||||
|
|
||||||
|
go func() {
|
||||||
|
stdout, errStdout = copyAndCapture(os.Stdout, stdoutIn)
|
||||||
|
}()
|
||||||
|
|
||||||
|
go func() {
|
||||||
|
stderr, errStderr = copyAndCapture(os.Stderr, stderrIn)
|
||||||
|
}()
|
||||||
|
|
||||||
|
err := testCmd.Wait()
|
||||||
|
if err != nil {
|
||||||
|
return "", "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
if errStdout != nil || errStderr != nil {
|
||||||
|
return "", "", errors.New("failed to capture stdout or stderr")
|
||||||
|
}
|
||||||
|
|
||||||
|
outStr, errStr := string(stdout), string(stderr)
|
||||||
|
return outStr, errStr, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func copyAndCapture(w io.Writer, r io.Reader) ([]byte, error) {
|
||||||
|
var out []byte
|
||||||
|
buf := make([]byte, 1024, 1024)
|
||||||
|
for {
|
||||||
|
n, err := r.Read(buf[:])
|
||||||
|
if n > 0 {
|
||||||
|
d := buf[:n]
|
||||||
|
out = append(out, d...)
|
||||||
|
_, err := w.Write(d)
|
||||||
|
if err != nil {
|
||||||
|
return out, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
// Read returns io.EOF at the end of file, which is not an error for us
|
||||||
|
if err == io.EOF {
|
||||||
|
err = nil
|
||||||
|
}
|
||||||
|
return out, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue