diff --git a/README.md b/README.md index de1452df5..732526061 100644 --- a/README.md +++ b/README.md @@ -85,6 +85,8 @@ $ adm init web - [mssql](https://raw.githubusercontent.com/GoAdminGroup/go-admin/master/data/admin.mssql) - [postgresql](https://raw.githubusercontent.com/GoAdminGroup/go-admin/master/data/admin.pgsql) - [sqlite](https://raw.githubusercontent.com/GoAdminGroup/go-admin/master/data/admin.db) +- [OceanBase](https://raw.githubusercontent.com/GoAdminGroup/go-admin/master/data/admin.sql) + ### Step 2: create main.go diff --git a/adm/cli.go b/adm/cli.go index 64838e2db..17e34ac76 100644 --- a/adm/cli.go +++ b/adm/cli.go @@ -5,11 +5,11 @@ package main import ( + "fmt" _ "github.com/GoAdminGroup/go-admin/modules/db/drivers/mysql" + _ "github.com/GoAdminGroup/go-admin/modules/db/drivers/oceanbase" _ "github.com/GoAdminGroup/go-admin/modules/db/drivers/postgres" _ "github.com/GoAdminGroup/go-admin/modules/db/drivers/sqlite" - - "fmt" "os" "runtime" "runtime/debug" diff --git a/adm/project_web.go b/adm/project_web.go index 4a34ae26f..80d4c57c7 100644 --- a/adm/project_web.go +++ b/adm/project_web.go @@ -138,6 +138,14 @@ func buildProjectWeb(port string) { _, _ = w.Write([]byte(`{"code": 400, "msg": "` + local(lang)("web.wrong parameter") + `: ` + field + `"}`)) return } + } else if r.PostFormValue("db_type") == "oceanbase" { + if field, ok := checkEmpty([]string{"db_port", "db_host", "db_user", "db_name"}, r); !ok { + w.WriteHeader(http.StatusOK) + w.Header().Add("Content-Type", "application/json") + _, _ = w.Write([]byte(`{"code": 400, "msg": "` + local(lang)("web.wrong parameter") + `: ` + field + `"}`)) + return + } + } else { if field, ok := checkEmpty([]string{"db_port", "db_host", "db_user", "db_passwd", "db_name"}, r); !ok { w.WriteHeader(http.StatusOK) @@ -242,6 +250,8 @@ func buildProjectWeb(port string) { if err := http.Serve(l, nil); err != nil { log.Fatal("ListenAndServe: ", err) } + fmt.Println("GoAdmin web install program start.") + }(startChan) <-startChan diff --git a/adm/project_web.tmpl.go b/adm/project_web.tmpl.go index 899999f93..706542b17 100644 --- a/adm/project_web.tmpl.go +++ b/adm/project_web.tmpl.go @@ -191,6 +191,8 @@ var projectWebTmpl = `
PostgreSQL
MSSQL
SQLite3
+
OceanBase
+ @@ -233,7 +235,29 @@ var projectWebTmpl = ` {{local "web.the file path of sqlite3 database"}}
{{local "web.please use absolute path when you start as service"}}
- +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + + {{local "web.where the framework sql data install to"}} +
+

{{local "web.installation settings"}}

@@ -370,6 +394,9 @@ var projectWebTmpl = `
  • SQLite3
  • +
  • + OceanBase +
  • 2. 依次执行以下命令: @@ -455,6 +482,10 @@ var projectWebTmpl = ` SQLite3 +

  • + OceanBase +
  • 2. Execute the following command in turn @@ -587,6 +618,11 @@ var projectWebTmpl = ` "addr": "127.0.0.1", "port": "1433", "user": "sa" + }, + "oceanbase": { + "addr": "127.0.0.1", + "port": "2881", + "user": "root@sys" } }; diff --git a/engine/engine.go b/engine/engine.go index 12bf128ee..e09347099 100644 --- a/engine/engine.go +++ b/engine/engine.go @@ -260,6 +260,11 @@ func (eng *Engine) SqliteConnection() db.Connection { return db.GetConnectionFromService(eng.Services.Get(db.DriverSqlite)) } +// OceanBaseConnection return the OceanBase db connection of given driver. +func (eng *Engine) OceanBaseConnection() db.Connection { + return db.GetConnectionFromService(eng.Services.Get(db.DriverOceanBase)) +} + type ConnectionSetter func(db.Connection) // ResolveConnection resolve the specified driver connection. diff --git a/go.mod b/go.mod index df1e52a03..29b8458a7 100644 --- a/go.mod +++ b/go.mod @@ -4,11 +4,14 @@ go 1.13 require ( github.com/360EntSecGroup-Skylar/excelize v1.4.1 + github.com/AlecAivazis/survey/v2 v2.3.6 // indirect github.com/GoAdminGroup/html v0.0.1 github.com/NebulousLabs/fastrand v0.0.0-20181203155948-6fb6489aac4e github.com/denisenkom/go-mssqldb v0.0.0-20200206145737-bbfc9a55622e github.com/go-sql-driver/mysql v1.5.0 github.com/google/uuid v1.3.0 // indirect + github.com/jawher/mow.cli v1.2.0 // indirect + github.com/jteeuwen/go-bindata v3.0.7+incompatible // indirect github.com/konsorten/go-windows-terminal-sequences v1.0.2 // indirect github.com/lib/pq v1.3.0 github.com/magiconair/properties v1.8.1 @@ -16,13 +19,14 @@ require ( github.com/mattn/go-sqlite3 v2.0.3+incompatible github.com/mgutz/ansi v0.0.0-20170206155736-9520e82c474b github.com/natefinch/lumberjack v2.0.0+incompatible + github.com/schollz/progressbar v1.0.0 // indirect github.com/sirupsen/logrus v1.4.2 github.com/stretchr/objx v0.2.0 // indirect - github.com/stretchr/testify v1.5.1 + github.com/stretchr/testify v1.6.1 + github.com/tdewolff/minify/v2 v2.12.4 // indirect go.uber.org/zap v1.14.1 golang.org/x/crypto v0.0.0-20200221231518-2aa609cf4a9d - golang.org/x/sys v0.0.0-20200219091948-cb0a6d8edb6c // indirect - golang.org/x/text v0.3.2 + golang.org/x/text v0.3.3 google.golang.org/appengine v1.6.5 // indirect gopkg.in/ini.v1 v1.51.0 gopkg.in/yaml.v2 v2.2.8 diff --git a/go.sum b/go.sum index 3a30432fc..dc96e2574 100644 --- a/go.sum +++ b/go.sum @@ -4,18 +4,25 @@ cloud.google.com/go v0.37.4/go.mod h1:NHPJ89PdicEuT9hdPXMROBD91xc5uRDxsMtSB16k7h gitea.com/xorm/sqlfiddle v0.0.0-20180821085327-62ce714f951a/go.mod h1:EXuID2Zs0pAQhH8yz+DNjUbjppKQzKFAn28TMYPB6IU= github.com/360EntSecGroup-Skylar/excelize v1.4.1 h1:l55mJb6rkkaUzOpSsgEeKYtS6/0gHwBYyfo5Jcjv/Ks= github.com/360EntSecGroup-Skylar/excelize v1.4.1/go.mod h1:vnax29X2usfl7HHkBrX5EvSCJcmH3dT9luvxzu8iGAE= +github.com/AlecAivazis/survey/v2 v2.3.6 h1:NvTuVHISgTHEHeBFqt6BHOe4Ny/NwGZr7w+F8S9ziyw= +github.com/AlecAivazis/survey/v2 v2.3.6/go.mod h1:4AuI9b7RjAR+G7v9+C4YSlX/YL3K3cWNXgWXOhllqvI= github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/GoAdminGroup/html v0.0.1 h1:SdWNWl4OKPsvDk2GDp5ZKD6ceWoN8n4Pj6cUYxavUd0= github.com/GoAdminGroup/html v0.0.1/go.mod h1:A1laTJaOx8sQ64p2dE8IqtstDeCNBHEazrEp7hR5VvM= github.com/NebulousLabs/fastrand v0.0.0-20181203155948-6fb6489aac4e h1:n+DcnTNkQnHlwpsrHoQtkrJIO7CBx029fw6oR4vIob4= github.com/NebulousLabs/fastrand v0.0.0-20181203155948-6fb6489aac4e/go.mod h1:Bdzq+51GR4/0DIhaICZEOm+OHvXGwwB2trKZ8B4Y6eQ= +github.com/Netflix/go-expect v0.0.0-20220104043353-73e0943537d2 h1:+vx7roKuyA63nhn5WAunQHLTznkw5W8b1Xc0dNjp83s= +github.com/Netflix/go-expect v0.0.0-20220104043353-73e0943537d2/go.mod h1:HBCaDeC1lPdgDeDbhX8XFpy1jqjK0IBG8W5K+xYqA0w= github.com/Shopify/sarama v1.19.0/go.mod h1:FVkBWblsNy7DGZRfXLU0O9RCGt5g3g3yEuWXgklEdEo= github.com/Shopify/toxiproxy v2.1.4+incompatible/go.mod h1:OXgGpZ6Cli1/URJOF1DMxUHB2q5Ap20/P/eIdh4G0pI= github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= github.com/apache/thrift v0.12.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb+bacwQ= github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q= +github.com/cheekybits/is v0.0.0-20150225183255-68e9c0620927/go.mod h1:h/aW8ynjgkuj+NQRlZcDbAbM1ORAbXjXX77sX7T289U= github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= +github.com/creack/pty v1.1.17 h1:QeVUsEDNrLBW4tMgZHvxy18sKtr6VI492kBhUfhDJNI= +github.com/creack/pty v1.1.17/go.mod h1:MOBLtS5ELjhRRrroQr9kyvTxUAFNvYEK993ew/Vr4O4= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -24,10 +31,16 @@ github.com/denisenkom/go-mssqldb v0.0.0-20191001013358-cfbb681360f0 h1:epsH3lb7K github.com/denisenkom/go-mssqldb v0.0.0-20191001013358-cfbb681360f0/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU= github.com/denisenkom/go-mssqldb v0.0.0-20200206145737-bbfc9a55622e h1:LzwWXEScfcTu7vUZNlDDWDARoSGEtvlDKK2BYHowNeE= github.com/denisenkom/go-mssqldb v0.0.0-20200206145737-bbfc9a55622e/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU= +github.com/djherbis/atime v1.1.0 h1:rgwVbP/5by8BvvjBNrbh64Qz33idKT3pSnMSJsxhi0g= +github.com/djherbis/atime v1.1.0/go.mod h1:28OF6Y8s3NQWwacXc5eZTsEsiMzp7LF8MbXE+XJPdBE= +github.com/dustin/go-humanize v1.0.0 h1:VSnTsYCnlFHaM2/igO1h6X3HA71jcobQuxemgkq4zYo= +github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/eapache/go-resiliency v1.1.0/go.mod h1:kFI+JgMyC7bLPUVY133qvEBtVayf5mFgVsvEsIPBvNs= github.com/eapache/go-xerial-snappy v0.0.0-20180814174437-776d5712da21/go.mod h1:+020luEh2TKB4/GOp8oxxtq0Daoen/Cii55CzbTV6DU= github.com/eapache/queue v1.1.0/go.mod h1:6eCeP0CKFpHLu8blIFXhExK/dRa7WDZfr6jVFPTqq+I= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= +github.com/fsnotify/fsnotify v1.5.4 h1:jRbGcIw6P2Meqdwuo0H1p6JVLbL5DHKAKlYndzMwVZI= +github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmVXmkdnm1bU= github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE= github.com/go-sql-driver/mysql v1.4.1 h1:g24URVg0OFbNUTx9qqY1IRZ9D9z3iPyi5zKhQZpNwpA= @@ -57,9 +70,17 @@ github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+ github.com/gorilla/context v1.1.1/go.mod h1:kBGZzfjB9CEq2AlWe17Uuf7NDRt0dE0s8S51q0aT7Yg= github.com/gorilla/mux v1.6.2/go.mod h1:1lud6UwP+6orDFRuTfBEV8e9/aOM/c4fVVCaMa2zaAs= github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8= +github.com/hinshun/vt10x v0.0.0-20220119200601-820417d04eec h1:qv2VnGeEQHchGaZ/u7lxST/RaJw+cv273q79D81Xbog= +github.com/hinshun/vt10x v0.0.0-20220119200601-820417d04eec/go.mod h1:Q48J4R4DvxnHolD5P8pOtXigYlRuPLGl6moFx3ulM68= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= +github.com/jawher/mow.cli v1.2.0 h1:e6ViPPy+82A/NFF/cfbq3Lr6q4JHKT9tyHwTCcUQgQw= +github.com/jawher/mow.cli v1.2.0/go.mod h1:y+pcA3jBAdo/GIZx/0rFjw/K2bVEODP9rfZOfaiq8Ko= github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU= +github.com/jteeuwen/go-bindata v3.0.7+incompatible h1:91Uy4d9SYVr1kyTJ15wJsog+esAZZl7JmEfTkwmhJts= +github.com/jteeuwen/go-bindata v3.0.7+incompatible/go.mod h1:JVvhzYOiGBnFSYRyV00iY8q7/0PThjIYav1p9h5dmKs= github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= +github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51 h1:Z9n2FFNUXsshfwJMBgNA0RU6/i7WVaAegv3PtuIHPMs= +github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51/go.mod h1:CzGEWj7cYgsdH8dAjBGEr58BoE7ScuLd+fwFZ44+/x8= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/konsorten/go-windows-terminal-sequences v1.0.1 h1:mweAR1A6xJ3oS2pRaGiHgQ4OO8tzTaLawm8vnODuwDk= github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= @@ -76,6 +97,9 @@ github.com/lib/pq v1.3.0 h1:/qkRGz8zljWiDcFvgpwUpwIAPu3r07TDvs3Rws+o/pU= github.com/lib/pq v1.3.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= github.com/magiconair/properties v1.8.1 h1:ZC2Vc7/ZFkGmsVC9KvOjumD+G5lXy2RtTKyzRKO2BQ4= github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/matryer/try v0.0.0-20161228173917-9ac251b645a2 h1:JAEbJn3j/FrhdWA9jW8B5ajsLIjeuEHLi8xE4fk997o= +github.com/matryer/try v0.0.0-20161228173917-9ac251b645a2/go.mod h1:0KeJpeMD6o+O4hW7qJOT7vyQPKrWmj26uf5wMc/IiIs= +github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= github.com/mattn/go-colorable v0.1.4 h1:snbPLB8fVfU9iwbbo30TPtbLRzwWu6aJS6Xh4eaaviA= github.com/mattn/go-colorable v0.1.4/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= github.com/mattn/go-isatty v0.0.8 h1:HLtExJ+uU2HOZ+wI0Tt5DtUDrx8yhUqDcp7fYERX4CE= @@ -112,9 +136,13 @@ github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R github.com/prometheus/procfs v0.0.0-20190117184657-bf6a532e95b1/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4= github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= +github.com/schollz/progressbar v1.0.0 h1:gbyFReLHDkZo8mxy/dLWMr+Mpb1MokGJ1FqCiqacjZM= +github.com/schollz/progressbar v1.0.0/go.mod h1:/l9I7PC3L3erOuz54ghIRKUEFcosiWfLvJv+Eq26UMs= github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= github.com/sirupsen/logrus v1.4.2 h1:SPIRibHv4MatM3XXNO2BJeFLZwZ2LvZgfQ5+UNI2im4= github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE= +github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= +github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1 h1:2vfRuCMp5sSVIDSqO8oNnWJq7mPa6KVP3iPIwFBuy8A= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= @@ -127,8 +155,16 @@ github.com/stretchr/testify v1.4.0 h1:2E4SXV/wtOkTonXsotYi4li6zVWxYlZuYNCXe9XRJy github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0= +github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.0 h1:fBdIW9lB4Iz0n9khmH8w27SJ3QEJ7+IgjPEwGSZiFdE= github.com/syndtr/goleveldb v1.0.0/go.mod h1:ZVVdQEZoIme9iO1Ch2Jdy24qqXrMMOU6lpPAyBWyWuQ= +github.com/tdewolff/minify/v2 v2.12.4 h1:kejsHQMM17n6/gwdw53qsi6lg0TGddZADVyQOz1KMdE= +github.com/tdewolff/minify/v2 v2.12.4/go.mod h1:h+SRvSIX3kwgwTFOpSckvSxgax3uy8kZTSF1Ojrr3bk= +github.com/tdewolff/parse/v2 v2.6.4 h1:KCkDvNUMof10e3QExio9OPZJT8SbdKojLBumw8YZycQ= +github.com/tdewolff/parse/v2 v2.6.4/go.mod h1:woz0cgbLwFdtbjJu8PIKxhW05KplTFQkOdX78o+Jgrs= +github.com/tdewolff/test v1.0.7 h1:8Vs0142DmPFW/bQeHRP3MV19m1gvndjUb1sn8yy74LM= +github.com/tdewolff/test v1.0.7/go.mod h1:6DAvZliBAAnD7rhVgwaM7DE5/d9NMOAJ09SqYqeK4QE= github.com/ziutek/mymysql v1.5.4/go.mod h1:LMSpPZ6DbqWFxNCHW77HeMg9I646SAhApZ/wKdgO/C0= go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= go.uber.org/atomic v1.6.0 h1:Ezj3JGmsOnG1MoRWQkPBsKLe9DwWD9QeXzTRzzldNVk= @@ -182,10 +218,18 @@ golang.org/x/sys v0.0.0-20190422165155-953cdadca894 h1:Cz4ceDQGXuKRnVBDTS23GTn/p golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200219091948-cb0a6d8edb6c h1:jceGD5YNJGgGMkJz79agzOln1K9TaZUjv5ird16qniQ= golang.org/x/sys v0.0.0-20200219091948-cb0a6d8edb6c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220422013727-9388b58f7150 h1:xHms4gcpe1YE7A3yIllJXP16CMAGuqwO2lX1mTyyRRc= +golang.org/x/sys v0.0.0-20220422013727-9388b58f7150/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/term v0.0.0-20210503060354-a79de5458b56 h1:b8jxX3zqjpqb2LklXPzKSGJhzyxCOZSz8ncv8Nv+y7w= +golang.org/x/term v0.0.0-20210503060354-a79de5458b56/go.mod h1:tfny5GFUkzUvx4ps4ajbZsCe5lw1metzhBm9T3x7oIY= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2 h1:tW2bmiBqwgJj/UpqtC8EpXEZVYOwU0yG4iWbprSVAcs= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= +golang.org/x/text v0.3.3 h1:cokOdA+Jmi5PJGXLlLllQSgYigAEfHXJAERHVMaCc2k= +golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= @@ -220,10 +264,13 @@ gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWD gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.5/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.7 h1:VUgggvou5XRW9mHwD/yXxIYSMtY0zoKQf/v226p2nyo= gopkg.in/yaml.v2 v2.2.7/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.8 h1:obN1ZagJSUGI0Ek/LBmuj4SNLPfIny3KsKFopxRdj10= gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= diff --git a/modules/auth/session.go b/modules/auth/session.go index 61aea179b..ecf9e34b9 100644 --- a/modules/auth/session.go +++ b/modules/auth/session.go @@ -178,6 +178,8 @@ func (driver *DBDriver) deleteOverdueSession() { raw = `strftime('%s', created_at) < strftime('%s', 'now') - ` + duration } else if db.DriverMssql == driverName { raw = `DATEDIFF(second, [created_at], GETDATE()) > ` + duration + } else if db.DriverOceanBase == driverName { + raw = `unix_timestamp(created_at) < unix_timestamp() - ` + duration } if raw != "" { diff --git a/modules/config/config.go b/modules/config/config.go index c2e4eeb07..dd9739f1f 100644 --- a/modules/config/config.go +++ b/modules/config/config.go @@ -73,6 +73,10 @@ func (d Database) GetDSN() string { if d.Driver == DriverSqlite { return d.File + d.ParamStr() } + if d.Driver == DriverOceanBase { + return d.User + ":" + d.Pwd + "@tcp(" + d.Host + ":" + d.Port + ")/" + + d.Name + d.ParamStr() + } return "" } @@ -81,8 +85,8 @@ func (d Database) ParamStr() string { if d.Params == nil { d.Params = make(map[string]string) } - if d.Driver == DriverMysql || d.Driver == DriverSqlite { - if d.Driver == DriverMysql { + if d.Driver == DriverMysql || d.Driver == DriverSqlite || d.Driver == DriverOceanBase { + if d.Driver == DriverMysql || d.Driver == DriverOceanBase { if _, ok := d.Params["charset"]; !ok { d.Params["charset"] = "utf8mb4" } @@ -191,6 +195,8 @@ const ( DriverPostgresql = "postgresql" // DriverMssql is a const value of mssql driver. DriverMssql = "mssql" + // DriverOceanBase is a const value of mysql driver. + DriverOceanBase = "oceanbase" ) // Store is the file store config. Path is the local store path. diff --git a/modules/db/connection.go b/modules/db/connection.go index 871e39357..fd77bb064 100644 --- a/modules/db/connection.go +++ b/modules/db/connection.go @@ -22,6 +22,8 @@ const ( DriverPostgresql = "postgresql" // DriverMssql is a const value of mssql driver. DriverMssql = "mssql" + // DriverOceanBase is a const value of oceanbase driver. + DriverOceanBase = "oceanbase" ) // Connection is a connection handler of database. @@ -84,6 +86,8 @@ func GetConnectionByDriver(driver string) Connection { return GetSqliteDB() case "postgresql": return GetPostgresqlDB() + case "oceanbase": + return GetOceanBaseDB() default: panic("driver not found!") } @@ -113,6 +117,9 @@ func GetAggregationExpression(driver, field, headField, delimiter string) string return fmt.Sprintf("group_concat(%s, '%s') as %s", field, delimiter, headField) case "mssql": return fmt.Sprintf("string_agg(%s, '%s') as [%s]", field, delimiter, headField) + case "oceanbase": + return fmt.Sprintf("group_concat(%s separator '%s') as %s", field, delimiter, headField) + default: panic("wrong driver") } diff --git a/modules/db/dialect/dialect.go b/modules/db/dialect/dialect.go index 003ec52b8..4d8b2c999 100644 --- a/modules/db/dialect/dialect.go +++ b/modules/db/dialect/dialect.go @@ -61,6 +61,10 @@ func GetDialectByDriver(driver string) Dialect { return sqlite{ commonDialect: commonDialect{delimiter: "`", delimiter2: "`"}, } + case "oceanbase": + return oceanbase{ + commonDialect: commonDialect{delimiter: "`", delimiter2: "`"}, + } default: return commonDialect{delimiter: "`", delimiter2: "`"} } diff --git a/modules/db/dialect/oceanbase.go b/modules/db/dialect/oceanbase.go new file mode 100644 index 000000000..542a561ba --- /dev/null +++ b/modules/db/dialect/oceanbase.go @@ -0,0 +1,17 @@ +package dialect + +type oceanbase struct { + commonDialect +} + +func (oceanbase) GetName() string { + return "oceanbase" +} + +func (oceanbase) ShowColumns(table string) string { + return "show columns in " + table +} + +func (oceanbase) ShowTables() string { + return "show tables" +} diff --git a/modules/db/drivers/oceanbase/oceanbase.go b/modules/db/drivers/oceanbase/oceanbase.go new file mode 100644 index 000000000..36aa64b15 --- /dev/null +++ b/modules/db/drivers/oceanbase/oceanbase.go @@ -0,0 +1,4 @@ +package oceanbase + +//oceanbase-ce can use mysql driver +import _ "github.com/go-sql-driver/mysql" // Import the mysql driver. diff --git a/modules/db/oceanbase.go b/modules/db/oceanbase.go new file mode 100644 index 000000000..2312b1b15 --- /dev/null +++ b/modules/db/oceanbase.go @@ -0,0 +1,165 @@ +package db + +import ( + "database/sql" + "github.com/GoAdminGroup/go-admin/modules/config" +) + +// OceanBase is a Connection of OceanBase. +type OceanBase struct { + Base +} + +// GetOceanBaseDB return the global OceanBase connection. +func GetOceanBaseDB() *OceanBase { + return &OceanBase{ + Base: Base{ + DbList: make(map[string]*sql.DB), + }, + } +} + +// Name implements the method Connection.Name. +func (db *OceanBase) Name() string { + return "OceanBase" +} + +// GetDelimiter implements the method Connection.GetDelimiter. +func (db *OceanBase) GetDelimiter() string { + return "`" +} + +// GetDelimiter2 implements the method Connection.GetDelimiter2. +func (db *OceanBase) GetDelimiter2() string { + return "`" +} + +// GetDelimiters implements the method Connection.GetDelimiters. +func (db *OceanBase) GetDelimiters() []string { + return []string{"`", "`"} +} + +// InitDB implements the method Connection.InitDB. +func (db *OceanBase) InitDB(cfgs map[string]config.Database) Connection { + db.Configs = cfgs + db.Once.Do(func() { + for conn, cfg := range cfgs { + + sqlDB, err := sql.Open("mysql", cfg.GetDSN()) + + if err != nil { + if sqlDB != nil { + _ = sqlDB.Close() + } + panic(err) + } + + // Largest set up the database connection reduce time wait + sqlDB.SetMaxIdleConns(cfg.MaxIdleConns) + sqlDB.SetMaxOpenConns(cfg.MaxOpenConns) + sqlDB.SetConnMaxLifetime(cfg.ConnMaxLifetime) + sqlDB.SetConnMaxIdleTime(cfg.ConnMaxIdleTime) + + db.DbList[conn] = sqlDB + + if err := sqlDB.Ping(); err != nil { + panic(err) + } + } + }) + return db +} + +// QueryWithConnection implements the method Connection.QueryWithConnection. +func (db *OceanBase) QueryWithConnection(con string, query string, args ...interface{}) ([]map[string]interface{}, error) { + return CommonQuery(db.DbList[con], query, args...) +} + +// ExecWithConnection implements the method Connection.ExecWithConnection. +func (db *OceanBase) ExecWithConnection(con string, query string, args ...interface{}) (sql.Result, error) { + return CommonExec(db.DbList[con], query, args...) +} + +// Query implements the method Connection.Query. +func (db *OceanBase) Query(query string, args ...interface{}) ([]map[string]interface{}, error) { + return CommonQuery(db.DbList["default"], query, args...) +} + +// Exec implements the method Connection.Exec. +func (db *OceanBase) Exec(query string, args ...interface{}) (sql.Result, error) { + return CommonExec(db.DbList["default"], query, args...) +} + +// QueryWithTx is query method within the transaction. +func (db *OceanBase) QueryWithTx(tx *sql.Tx, query string, args ...interface{}) ([]map[string]interface{}, error) { + return CommonQueryWithTx(tx, query, args...) +} + +// ExecWithTx is exec method within the transaction. +func (db *OceanBase) ExecWithTx(tx *sql.Tx, query string, args ...interface{}) (sql.Result, error) { + return CommonExecWithTx(tx, query, args...) +} + +func (db *OceanBase) QueryWith(tx *sql.Tx, conn, query string, args ...interface{}) ([]map[string]interface{}, error) { + if tx != nil { + return db.QueryWithTx(tx, query, args...) + } + return db.QueryWithConnection(conn, query, args...) +} + +func (db *OceanBase) ExecWith(tx *sql.Tx, conn, query string, args ...interface{}) (sql.Result, error) { + if tx != nil { + return db.ExecWithTx(tx, query, args...) + } + return db.ExecWithConnection(conn, query, args...) +} + +// BeginTxWithReadUncommitted starts a transaction with level LevelReadUncommitted. +func (db *OceanBase) BeginTxWithReadUncommitted() *sql.Tx { + return CommonBeginTxWithLevel(db.DbList["default"], sql.LevelReadUncommitted) +} + +// BeginTxWithReadCommitted starts a transaction with level LevelReadCommitted. +func (db *OceanBase) BeginTxWithReadCommitted() *sql.Tx { + return CommonBeginTxWithLevel(db.DbList["default"], sql.LevelReadCommitted) +} + +// BeginTxWithRepeatableRead starts a transaction with level LevelRepeatableRead. +func (db *OceanBase) BeginTxWithRepeatableRead() *sql.Tx { + return CommonBeginTxWithLevel(db.DbList["default"], sql.LevelRepeatableRead) +} + +// BeginTx starts a transaction with level LevelDefault. +func (db *OceanBase) BeginTx() *sql.Tx { + return CommonBeginTxWithLevel(db.DbList["default"], sql.LevelDefault) +} + +// BeginTxWithLevel starts a transaction with given transaction isolation level. +func (db *OceanBase) BeginTxWithLevel(level sql.IsolationLevel) *sql.Tx { + return CommonBeginTxWithLevel(db.DbList["default"], level) +} + +// BeginTxWithReadUncommittedAndConnection starts a transaction with level LevelReadUncommitted and connection. +func (db *OceanBase) BeginTxWithReadUncommittedAndConnection(conn string) *sql.Tx { + return CommonBeginTxWithLevel(db.DbList[conn], sql.LevelReadUncommitted) +} + +// BeginTxWithReadCommittedAndConnection starts a transaction with level LevelReadCommitted and connection. +func (db *OceanBase) BeginTxWithReadCommittedAndConnection(conn string) *sql.Tx { + return CommonBeginTxWithLevel(db.DbList[conn], sql.LevelReadCommitted) +} + +// BeginTxWithRepeatableReadAndConnection starts a transaction with level LevelRepeatableRead and connection. +func (db *OceanBase) BeginTxWithRepeatableReadAndConnection(conn string) *sql.Tx { + return CommonBeginTxWithLevel(db.DbList[conn], sql.LevelRepeatableRead) +} + +// BeginTxAndConnection starts a transaction with level LevelDefault and connection. +func (db *OceanBase) BeginTxAndConnection(conn string) *sql.Tx { + return CommonBeginTxWithLevel(db.DbList[conn], sql.LevelDefault) +} + +// BeginTxWithLevelAndConnection starts a transaction with given transaction isolation level and connection. +func (db *OceanBase) BeginTxWithLevelAndConnection(conn string, level sql.IsolationLevel) *sql.Tx { + return CommonBeginTxWithLevel(db.DbList[conn], level) +}