mirror of https://gitee.com/answerdev/answer.git
Merge branch 'github-dev' into release/1.0.5
# Conflicts: # go.mod
This commit is contained in:
commit
00df552422
|
@ -1,4 +1,4 @@
|
|||
version: "3"
|
||||
version: "3.9"
|
||||
|
||||
# uffizzi integration
|
||||
x-uffizzi:
|
||||
|
@ -10,8 +10,27 @@ services:
|
|||
|
||||
answer:
|
||||
image: "${ANSWER_IMAGE}"
|
||||
environment:
|
||||
- AUTO_INSTALL=true
|
||||
- DB_TYPE=mysql
|
||||
- DB_USERNAME=root
|
||||
- DB_PASSWORD=password
|
||||
- DB_HOST=127.0.0.1:3306
|
||||
- DB_NAME=answer
|
||||
- LANGUAGE=en_US
|
||||
- SITE_NAME=answer-test
|
||||
- SITE_URL=http://localhost
|
||||
- CONTACT_EMAIL=test@answer.com
|
||||
- ADMIN_NAME=admin123
|
||||
- ADMIN_PASSWORD=admin123
|
||||
- ADMIN_EMAIL=admin123@admin.com
|
||||
volumes:
|
||||
- answer-data:/data
|
||||
depends_on:
|
||||
mysql:
|
||||
condition: service_healthy
|
||||
links:
|
||||
- db
|
||||
deploy:
|
||||
resources:
|
||||
limits:
|
||||
|
@ -24,6 +43,11 @@ services:
|
|||
- MYSQL_ROOT_PASSWORD=password
|
||||
- MYSQL_USER=mysql
|
||||
- MYSQL_PASSWORD=mysql
|
||||
healthcheck:
|
||||
test: [ "CMD", "mysqladmin" ,"ping", "-uroot", "-ppassword" ]
|
||||
timeout: 20s
|
||||
retries: 10
|
||||
command: ['mysqld', '--character-set-server=utf8mb4', '--collation-server=utf8mb4_unicode_ci', '--skip-character-set-client-handshake']
|
||||
volumes:
|
||||
- sql_data:/var/lib/mysql
|
||||
deploy:
|
||||
|
|
15
go.mod
15
go.mod
|
@ -35,12 +35,13 @@ require (
|
|||
github.com/segmentfault/pacman/contrib/server/http v0.0.0-20221018072427-a15dd1434e05
|
||||
github.com/spf13/cobra v1.6.1
|
||||
github.com/stretchr/testify v1.8.1
|
||||
github.com/swaggo/files v1.0.0
|
||||
github.com/swaggo/files v0.0.0-20220728132757-551d4a08d97a
|
||||
github.com/swaggo/gin-swagger v1.5.3
|
||||
github.com/swaggo/swag v1.8.10
|
||||
github.com/swaggo/swag v1.8.7
|
||||
github.com/tidwall/gjson v1.14.4
|
||||
github.com/yuin/goldmark v1.4.13
|
||||
golang.org/x/crypto v0.1.0
|
||||
golang.org/x/net v0.2.0
|
||||
golang.org/x/net v0.1.0
|
||||
gopkg.in/gomail.v2 v2.0.0-20160411212932-81ebce5c23df
|
||||
gopkg.in/yaml.v3 v3.0.1
|
||||
modernc.org/sqlite v1.14.2
|
||||
|
@ -109,6 +110,8 @@ require (
|
|||
github.com/spf13/viper v1.13.0 // indirect
|
||||
github.com/subosito/gotenv v1.4.1 // indirect
|
||||
github.com/syndtr/goleveldb v1.0.0 // indirect
|
||||
github.com/tidwall/match v1.1.1 // indirect
|
||||
github.com/tidwall/pretty v1.2.0 // indirect
|
||||
github.com/ugorji/go/codec v1.2.7 // indirect
|
||||
github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f // indirect
|
||||
github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 // indirect
|
||||
|
@ -118,7 +121,7 @@ require (
|
|||
go.uber.org/zap v1.23.0 // indirect
|
||||
golang.org/x/image v0.1.0 // indirect
|
||||
golang.org/x/mod v0.6.0 // indirect
|
||||
golang.org/x/sys v0.2.0 // indirect
|
||||
golang.org/x/sys v0.1.0 // indirect
|
||||
golang.org/x/text v0.5.0 // indirect
|
||||
golang.org/x/tools v0.2.0 // indirect
|
||||
google.golang.org/protobuf v1.28.1 // indirect
|
||||
|
@ -138,6 +141,6 @@ require (
|
|||
)
|
||||
|
||||
// github action runner Sometimes it will time out.
|
||||
// replace gitee.com/travelliu/dm v1.8.11192 => github.com/aichy126/dm v1.8.11192
|
||||
replace gitee.com/travelliu/dm v1.8.11192 => github.com/aichy126/dm v1.8.11192
|
||||
|
||||
// replace modernc.org/z v1.2.19 => github.com/aichy126/modernc.org_z v1.2.19
|
||||
replace modernc.org/z v1.2.19 => github.com/aichy126/modernc.org_z v1.2.19
|
||||
|
|
6
go.sum
6
go.sum
|
@ -681,6 +681,12 @@ github.com/swaggo/swag v1.8.10/go.mod h1:ezQVUUhly8dludpVk+/PuwJWvLLanB13ygV5Pr9
|
|||
github.com/syndtr/gocapability v0.0.0-20200815063812-42c35b437635/go.mod h1:hkRG7XYTFWNJGYcbNJQlaLq0fg1yr4J4t/NcTQtrfww=
|
||||
github.com/syndtr/goleveldb v1.0.0 h1:fBdIW9lB4Iz0n9khmH8w27SJ3QEJ7+IgjPEwGSZiFdE=
|
||||
github.com/syndtr/goleveldb v1.0.0/go.mod h1:ZVVdQEZoIme9iO1Ch2Jdy24qqXrMMOU6lpPAyBWyWuQ=
|
||||
github.com/tidwall/gjson v1.14.4 h1:uo0p8EbA09J7RQaflQ1aBRffTR7xedD2bcIVSYxLnkM=
|
||||
github.com/tidwall/gjson v1.14.4/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk=
|
||||
github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA=
|
||||
github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM=
|
||||
github.com/tidwall/pretty v1.2.0 h1:RWIZEg2iJ8/g6fDDYzMpobmaoGh5OLl4AXtGUGPcqCs=
|
||||
github.com/tidwall/pretty v1.2.0/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU=
|
||||
github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U=
|
||||
github.com/ugorji/go v1.1.7/go.mod h1:kZn38zHttfInRq0xu/PH0az30d+z6vm202qpg1oXVMw=
|
||||
github.com/ugorji/go v1.2.7/go.mod h1:nF9osbDWLy6bDVv/Rtoh6QgnvNDpmCalQV5urGCCS6M=
|
||||
|
|
|
@ -41,7 +41,6 @@ func InstallAllInitialEnvironment(dataDirPath string) {
|
|||
FormatAllPath(dataDirPath)
|
||||
installUploadDir()
|
||||
installI18nBundle()
|
||||
installReservedUsernames()
|
||||
fmt.Println("install all initial environment done")
|
||||
}
|
||||
|
||||
|
@ -114,16 +113,3 @@ func installI18nBundle() {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
func installReservedUsernames() {
|
||||
reservedUsernamesJsonFilePath := filepath.Join(ConfigFileDir, DefaultReservedUsernamesConfigFileName)
|
||||
if !dir.CheckFileExist(reservedUsernamesJsonFilePath) {
|
||||
err := writer.WriteFile(reservedUsernamesJsonFilePath, string(configs.ReservedUsernames))
|
||||
if err != nil {
|
||||
fmt.Printf("[%s] write file fail: %s\n", DefaultReservedUsernamesConfigFileName, err)
|
||||
} else {
|
||||
fmt.Printf("[%s] write file success\n", DefaultReservedUsernamesConfigFileName)
|
||||
}
|
||||
return
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,125 @@
|
|||
package install
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"os"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
"github.com/tidwall/gjson"
|
||||
)
|
||||
|
||||
type Env struct {
|
||||
AutoInstall string `json:"auto_install"`
|
||||
DbType string `json:"db_type"`
|
||||
DbUsername string `json:"db_username"`
|
||||
DbPassword string `json:"db_password"`
|
||||
DbHost string `json:"db_host"`
|
||||
DbName string `json:"db_name"`
|
||||
DbFile string `json:"db_file"`
|
||||
Language string `json:"lang"`
|
||||
|
||||
SiteName string `json:"site_name"`
|
||||
SiteURL string `json:"site_url"`
|
||||
ContactEmail string `json:"contact_email"`
|
||||
AdminName string `json:"name"`
|
||||
AdminPassword string `json:"password"`
|
||||
AdminEmail string `json:"email"`
|
||||
}
|
||||
|
||||
func TryToInstallByEnv() (installByEnv bool, err error) {
|
||||
env := loadEnv()
|
||||
if len(env.AutoInstall) == 0 {
|
||||
return false, nil
|
||||
}
|
||||
fmt.Println("[auto-install] try to install by environment variable")
|
||||
return true, initByEnv(env)
|
||||
}
|
||||
|
||||
func loadEnv() (env *Env) {
|
||||
return &Env{
|
||||
AutoInstall: os.Getenv("AUTO_INSTALL"),
|
||||
DbType: os.Getenv("DB_TYPE"),
|
||||
DbUsername: os.Getenv("DB_USERNAME"),
|
||||
DbPassword: os.Getenv("DB_PASSWORD"),
|
||||
DbHost: os.Getenv("DB_HOST"),
|
||||
DbName: os.Getenv("DB_NAME"),
|
||||
DbFile: os.Getenv("DB_FILE"),
|
||||
Language: os.Getenv("LANGUAGE"),
|
||||
SiteName: os.Getenv("SITE_NAME"),
|
||||
SiteURL: os.Getenv("SITE_URL"),
|
||||
ContactEmail: os.Getenv("CONTACT_EMAIL"),
|
||||
AdminName: os.Getenv("ADMIN_NAME"),
|
||||
AdminPassword: os.Getenv("ADMIN_PASSWORD"),
|
||||
AdminEmail: os.Getenv("ADMIN_EMAIL"),
|
||||
}
|
||||
}
|
||||
|
||||
func initByEnv(env *Env) (err error) {
|
||||
gin.SetMode(gin.TestMode)
|
||||
if err = dbCheck(env); err != nil {
|
||||
return err
|
||||
}
|
||||
if err = initConfigAndDb(env); err != nil {
|
||||
return err
|
||||
}
|
||||
if err = initBaseInfo(env); err != nil {
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func dbCheck(env *Env) (err error) {
|
||||
req := &CheckDatabaseReq{
|
||||
DbType: env.DbType,
|
||||
DbUsername: env.DbUsername,
|
||||
DbPassword: env.DbPassword,
|
||||
DbHost: env.DbHost,
|
||||
DbName: env.DbName,
|
||||
DbFile: env.DbFile,
|
||||
}
|
||||
return requestAPI(req, "POST", "/installation/db/check", CheckDatabase)
|
||||
}
|
||||
|
||||
func initConfigAndDb(env *Env) (err error) {
|
||||
req := &CheckDatabaseReq{
|
||||
DbType: env.DbType,
|
||||
DbUsername: env.DbUsername,
|
||||
DbPassword: env.DbPassword,
|
||||
DbHost: env.DbHost,
|
||||
DbName: env.DbName,
|
||||
DbFile: env.DbFile,
|
||||
}
|
||||
return requestAPI(req, "POST", "/installation/init", InitEnvironment)
|
||||
}
|
||||
|
||||
func initBaseInfo(env *Env) (err error) {
|
||||
req := &InitBaseInfoReq{
|
||||
Language: env.Language,
|
||||
SiteName: env.SiteName,
|
||||
SiteURL: env.SiteURL,
|
||||
ContactEmail: env.ContactEmail,
|
||||
AdminName: env.AdminName,
|
||||
AdminPassword: env.AdminPassword,
|
||||
AdminEmail: env.AdminEmail,
|
||||
}
|
||||
return requestAPI(req, "POST", "/installation/base-info", InitBaseInfo)
|
||||
}
|
||||
|
||||
func requestAPI(req interface{}, method, url string, handlerFunc gin.HandlerFunc) error {
|
||||
w := httptest.NewRecorder()
|
||||
c, _ := gin.CreateTestContext(w)
|
||||
body, _ := json.Marshal(req)
|
||||
c.Request, _ = http.NewRequest(method, url, bytes.NewBuffer(body))
|
||||
if method == "POST" {
|
||||
c.Request.Header.Set("Content-Type", "application/json")
|
||||
}
|
||||
handlerFunc(c)
|
||||
if w.Code != http.StatusOK {
|
||||
return fmt.Errorf(gjson.Get(w.Body.String(), "msg").String())
|
||||
}
|
||||
return nil
|
||||
}
|
|
@ -21,6 +21,11 @@ func Run(configPath string) {
|
|||
panic(err)
|
||||
}
|
||||
|
||||
// try to install by env
|
||||
if installByEnv, err := TryToInstallByEnv(); installByEnv && err != nil {
|
||||
fmt.Printf("[auto-install] try to init by env fail: %v\n", err)
|
||||
}
|
||||
|
||||
installServer := NewInstallHTTPServer()
|
||||
if len(port) == 0 {
|
||||
port = "80"
|
||||
|
|
Loading…
Reference in New Issue