Commit 0551c6f8 by Li Feifei

merge test

parents 42bd65c5 58443297
Pipeline #15954 failed with stages
in 18 seconds
package api
import (
"ppt_server/app/model"
"ppt_server/app/service"
"ppt_server/library/response"
"ppt_server/packed/file"
"github.com/gogf/gf/net/ghttp"
)
var File = fileApi{}
type fileApi struct{}
func (f *fileApi) Index(r *ghttp.Request) {
response.Success(r)
}
/**
* @Author lifeifei
* @Date 9:44 上午 2021/7/22
* @Summary 课件上传接口
* @Tags 客户端通过接口上传课件
* @Produce json
* @Router POST /file/upload
* @Param room_num formData string true "房间名称"
* @Param name formData string true "课件名称"
* @Param nickname formData string true "用户昵称"
* @Param type formData string true "文件类型"
* @Param url formData int true "课件地址"
* @Param uuid formData string true "用户唯一标识"
* @Return {"code":0,"data":null,"msg":"成功"}
**/
func (f *fileApi) Upload(r *ghttp.Request) {
var req model.FileUploadRequest
if err := r.Parse(&req); err != nil {
response.Fail(r, err)
}
// 检测课件格式
parserFile, err := file.Upload(&req, service.File.Done, service.File.Ok)
if err != nil {
response.Fail(r, err)
}
go service.File.Upload(parserFile)
response.Success(r)
}
package internal
import (
"github.com/gogf/gf/database/gdb"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/frame/gmvc"
)
type xyuRoomColumns struct {
Id string
RoomNum string
}
type XyuRoomDao struct {
gmvc.M
DB gdb.DB
Table string
Columns xyuRoomColumns
}
var (
XyuRoom = XyuRoomDao{
M: g.DB("default").Model("xyu_room").Safe(),
DB: g.DB("default"),
Table: "xyu_room",
Columns: xyuRoomColumns{
Id: "id",
RoomNum: "room_num",
},
}
)
package internal
import (
"github.com/gogf/gf/database/gdb"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/frame/gmvc"
)
type xyuRoomFilesColumns struct {
Id string
RoomId string
Name string
}
type XyuRoomFilesDao struct {
gmvc.M
DB gdb.DB
Table string
Columns xyuRoomFilesColumns
}
var (
XyuRoomFiles = XyuRoomFilesDao{
M: g.DB("default").Model("xyu_room_files").Safe(),
DB: g.DB("default"),
Table: "xyu_room_files",
Columns: xyuRoomFilesColumns{
Id: "id",
RoomId: "room_id",
Name: "name",
},
}
)
package dao
import "ppt_server/app/dao/internal"
type xyuRoomDao struct {
internal.XyuRoomDao
}
var XyuRoom = xyuRoomDao{internal.XyuRoom}
package dao
import "ppt_server/app/dao/internal"
type xyuRoomFilesDao struct {
internal.XyuRoomFilesDao
}
var XyuRoomFile = xyuRoomFilesDao{
internal.XyuRoomFiles,
}
package model
import (
"ppt_server/app/model/internal"
)
type (
XyuRoom internal.XyuRoom
XyuRoomFiles internal.XyuRoomFiles
// 客户端上传课件请求参数
FileUploadRequest struct {
RoomNum string `p:"room_num" v:"required#房间号不能为空"`
Name string `p:"name" v:"required#课件名称不能为空"`
NickName string `p:"nickname" v:"required#用户昵称不能为空"`
Type int `p:"type"`
Url string `p:"url" v:"required#上传课件地址不能为空"`
Uuid string `p:"uuid" v:"required#上传者UUID不能为空"`
}
// web365解析文件返回信息
UploadFileInfo struct {
FileName string `json:"FileName"`
FileSize int64 `json:"FileSize"`
PageCount int `jons:"PageCount"`
SlideCount int `json:"SlideCount"`
SheetCount int `json:"SheetCount"`
}
//OssPacked
Packed struct {
FileName string `json:"fileName"`
Hash string `json:"json"`
ImagesName []string `json:"imagesName"`
OssImagesPath string `json:"ossImagesPath"`
ImageInfos [][]interface{} `json:"imageInfos"`
}
// 服务端通知返回信息
NotifyResponse struct {
Code int64 `json:"code"`
Msg string `json:"msg"`
}
)
package internal
type XyuRoom struct {
Id int `orm:"id,primary" json:"id"`
RoomNum string `orm:"room_num" json:"room_num"`
}
package internal
type XyuRoomFiles struct {
Id int `orm:"id,primary" json:"id"`
RoomId int `orm:"room_id" json:"room_id"`
Name string `orm:"name" json:"name"`
}
package service
import (
"ppt_server/app/dao"
"ppt_server/app/model"
"ppt_server/packed/file"
"github.com/gogf/gf/frame/g"
)
var File = &fileService{
Done: make(chan error),
Ok: make(chan bool),
}
type fileService struct {
Done chan error
Ok chan bool
}
// 上传课件
func (f *fileService) Upload(file *file.ObtainFile) {
// 检查房间是否存在
var room model.XyuRoom
err := dao.XyuRoom.Where(dao.XyuRoom.Columns.RoomNum, file.R.RoomNum).Scan(&room)
// 上传操作
go file.Worker(err)
// 回调通知
select {
case <-f.Done:
// 上传失败
file.Fail()
return
case <-f.Ok:
// 上传成功
count, err := dao.XyuRoomFile.Where(dao.XyuRoomFile.Columns.RoomId, room.Id).
Where(dao.XyuRoomFile.Columns.Name, file.R.Name).Count()
if err != nil {
g.Log().Async().Errorf("Mysql Err: %s\n", err)
return
}
// 数据库已经存在不需要通知
if count == 1 {
return
}
file.Success(room.Id)
return
}
}
package boot
import (
"fmt"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/net/ghttp"
"os"
)
func init() {
link := fmt.Sprintf("mysql:%s:%s@tcp(%s:3306)/xyu",
os.Getenv("read_user"),
os.Getenv("read_pass"),
os.Getenv("read_sql"))
_ = g.Config().Set("database.link", link)
g.Server().SetNameToUriType(ghttp.URI_TYPE_CAMEL)
g.Log().SetAsync(true)
}
-----BEGIN RSA PRIVATE KEY-----
MIIEogIBAAKCAQEAo+8g8CvasfIwe4uToDzY8ir2rZoaBBV8EqM2gu+EwpmYnfBD
FYagyWvNDYNRYBKJgZuT/BU4f/dF0bFTFp0KwxcYDkhYE1TBNsnPqTNZGp0K2C9m
v2ATLyf+2DuVhW4etlQVnsqQBxPEoWCPmf4Mrta4xy83ZqS7BRBmi8avGyzhYjjB
hYLVuDAyOb+pDSGe9rpgcp0pyzpJ/4u8xLRO08CAUbyhN5l9ubrIBmV1F4PMhy1H
mmq26cJdMXcumzUZRebWtKK4xxZFteG8GNZIA0Oz8sk1RKjMgAVko7Uu6eR4rSlG
+R6pI79Npps3REIm1m8A3kMDCEmdDnl5q+ef3wIDAQABAoIBAHN4Mkk5epewsfmz
vM43TdB19r8dNon94CD4maLstySjL96/p2D4LTTzG8IS5zS2meiS/0+mWt+3+pPT
RWU+RKBaGfWle3RSVK4UxJK3umGGkGbqLINMVvb2QwloHs+XW0auP3RT1dNGV1Ac
RcoAKkrUr96NIYbJLXpJrRFzZ0/JzaKeHNB0OB8xQeWTVdM6liBgKhE8EMKqzA7E
Z3vZaB5Z4ezcYM+eKjKCkXkkhwc4AxibKdFdfBmdB6oFvMGoZjLbET/8CeOp6xKH
ovNEPohKpz0ewz932ZrpcikvnucXXhzhaxwmUmLF74WvVU+T5uIMjkj8jyylrUxw
kMzgufECgYEA9ew+hKtS8wWfnDqfURpDezjMueQF5/2kUVKuwsNhERLuXCe4XLFb
USAvHWrCiEqO0RA4Y+CybTS9kekMyC3lRHc+3otZ9ienp9BAcqA1T8UO2HEfFrfG
knUH9Xw7vjKwKBHPBARlnURqoiX5B9pjRs/Kya+19XVcAB7RNfbcvBsCgYEAqqbQ
b/3RYkM+fhy7xTITP6ommjRcnfI2RV/gGlt4jYM6/2GJ1PH3zOv+nhZfoffw/NYp
3A7zKfUe37frp5eYyoeZB1nB6Xo+aNsF0nSsc0x/Jms83gT5mfT3v9zUpOhe9FvH
iKgS0SYJVe9D5yuefLP1WNuYCy6/BLqE7nvyX40CgYBiD+s6EesItyRXMtUWjQd9
mj+gnHlycaTVPMgtJ6WMHmVn3/rXE23bYp8G9uxNVpWube5efVoIy/APv8N2Cz8R
1w79xMmBq3xiIVuhmZrIjUaHLkx8TZnkCsC6tehIxoOR5tAKxQoT9RUkRUoRRJcz
xGYTmHpRP5QJBEDeaOrKIwKBgBQ+zBWtOAz/S0es4v3nDe+MoR3EPoSiepvKXwzh
czDes74edTqlJi/Sg5d/sgLGJnnocnjf8Ss2IF6MNFHio0bLxXTgyieH0CWiblNk
ch0PozoMmOECGBaSwF2rtjKGOtWkmcx1nB3h9FOUmiqvuxKyStYq3yPcfN7zvdeJ
Ltz1AoGAI2P5xabnyBT2RU0pHth+YLg6SX0KNAPDuASTEUVcEFxftPmv90QRQhMU
2Ks6BpL+hwGxL6qu6heeq4PU9MVsFWCEZh9/igHDf0hHM60+euo/g8FHUkNn4/1q
2dd8CJM1uD/LSY0Cu7I3o2TOILHX9METraw6EWDq4iHnPy/tySI=
-----END RSA PRIVATE KEY-----
-----BEGIN CERTIFICATE-----
MIIGxTCCBa2gAwIBAgIQBlYKeyjVKIgKNuFr3A2gfzANBgkqhkiG9w0BAQsFADBf
MQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3
d3cuZGlnaWNlcnQuY29tMR4wHAYDVQQDExVHZW9UcnVzdCBDTiBSU0EgQ0EgRzEw
HhcNMTkwOTE2MDAwMDAwWhcNMjEwOTE1MTIwMDAwWjB4MQswCQYDVQQGEwJDTjES
MBAGA1UECAwJ5YyX5Lqs5biCMS0wKwYDVQQKDCTljJfkuqzkuK3lhazmlZnogrLn
p5HmioDmnInpmZDlhazlj7gxCzAJBgNVBAsTAklUMRkwFwYDVQQDDBAqLm9mZmNu
Y2xvdWQuY29tMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAo+8g8Cva
sfIwe4uToDzY8ir2rZoaBBV8EqM2gu+EwpmYnfBDFYagyWvNDYNRYBKJgZuT/BU4
f/dF0bFTFp0KwxcYDkhYE1TBNsnPqTNZGp0K2C9mv2ATLyf+2DuVhW4etlQVnsqQ
BxPEoWCPmf4Mrta4xy83ZqS7BRBmi8avGyzhYjjBhYLVuDAyOb+pDSGe9rpgcp0p
yzpJ/4u8xLRO08CAUbyhN5l9ubrIBmV1F4PMhy1Hmmq26cJdMXcumzUZRebWtKK4
xxZFteG8GNZIA0Oz8sk1RKjMgAVko7Uu6eR4rSlG+R6pI79Npps3REIm1m8A3kMD
CEmdDnl5q+ef3wIDAQABo4IDYjCCA14wHwYDVR0jBBgwFoAUkZ9eMRWuEJ+tYMH3
wcyqSDQvDCYwHQYDVR0OBBYEFBdhbm8eOCcYqUMMraPc3XpinOcDMCsGA1UdEQQk
MCKCECoub2ZmY25jbG91ZC5jb22CDm9mZmNuY2xvdWQuY29tMA4GA1UdDwEB/wQE
AwIFoDAdBgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwdQYDVR0fBG4wbDA0
oDKgMIYuaHR0cDovL2NybDMuZGlnaWNlcnQuY29tL0dlb1RydXN0Q05SU0FDQUcx
LmNybDA0oDKgMIYuaHR0cDovL2NybDQuZGlnaWNlcnQuY29tL0dlb1RydXN0Q05S
U0FDQUcxLmNybDBMBgNVHSAERTBDMDcGCWCGSAGG/WwBATAqMCgGCCsGAQUFBwIB
FhxodHRwczovL3d3dy5kaWdpY2VydC5jb20vQ1BTMAgGBmeBDAECAjBvBggrBgEF
BQcBAQRjMGEwIQYIKwYBBQUHMAGGFWh0dHA6Ly9vY3NwLmRjb2NzcC5jbjA8Bggr
BgEFBQcwAoYwaHR0cDovL2NybC5kaWdpY2VydC1jbi5jb20vR2VvVHJ1c3RDTlJT
QUNBRzEuY3J0MAkGA1UdEwQCMAAwggF9BgorBgEEAdZ5AgQCBIIBbQSCAWkBZwB2
ALvZ37wfinG1k5Qjl6qSe0c4V5UKq1LoGpCWZDaOHtGFAAABbTkJDU8AAAQDAEcw
RQIhAKxPVhYZl6lmgwkrHtPR6Tj+w07w8OEzzIi5tCux/F+NAiBzfajUaCWyHBkq
FmzUoZ2WRxhwDLJsGMfY/GVcLOf+XgB2AId1v+dZfPiMQ5lfvfNu/1aNR1Y2/0q1
YMG06v9eoIMPAAABbTkJDbUAAAQDAEcwRQIhAJ+oKOIjCEdBwBsdj9CYaJ1PBLoS
BfEAGv/rOy7t6rNoAiBdK24FvESSzbrN5hfPRCyZKTDQ0CCqsMn/5ztQ/z5iNAB1
AESUZS6w7s6vxEAH2Kj+KMDa5oK+2MsxtT/TM5a1toGoAAABbTkJDLoAAAQDAEYw
RAIgXX/xR8XI24dq8iZxhZBmLOLuo4ZbjOvdNz9wPV35eQQCICQu0+sZQ9aQXp9I
jRAnxxVtibIkystgYpgTn/VqMN/MMA0GCSqGSIb3DQEBCwUAA4IBAQBt0ddC3sUW
hRmTThB9ohImhH+pkwkDNRMF8YbOiDFuxFVBcvpKLjE+4BS0Tznkl7kMY/uCCmoo
PZeIdvpSIqVq6GmixWjcixOSXZ1gqiRHomqFOIYPi3emJbDV+J6c1rUzQvr8LFNb
Fen0xrT1ZNVK4W1GVM0givqjlvz0MI+8ds35HwuofzO8OUiJmcKziOTnlqHn/qNC
nFHlyCU33NYZw2YsZXZorJiPqoYAGSMcvunwKA7g0cZNMq9TXzOm9xDYrJ+wcEcU
uy0B6LfHkftgHlJ+7cOzQu4Gx8HI/eoJuTayifkjQQIAd4WgVmFLjDFkU0fZA5vL
S+8iHnMiCHok
-----END CERTIFICATE-----
-----BEGIN CERTIFICATE-----
MIIFGjCCBAKgAwIBAgIQCgRw0Ja8ihLIkKbfgm7sSzANBgkqhkiG9w0BAQsFADBh
MQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3
d3cuZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBD
QTAeFw0xOTA2MjAxMjI3NThaFw0yOTA2MjAxMjI3NThaMF8xCzAJBgNVBAYTAlVT
MRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5j
b20xHjAcBgNVBAMTFUdlb1RydXN0IENOIFJTQSBDQSBHMTCCASIwDQYJKoZIhvcN
AQEBBQADggEPADCCAQoCggEBALFJ+j1KeZVG4jzgQob23lQ8PJUNhY31ufZihuUx
hYc6HSU4Lw0fxfA43a9DpJl74M3E6F1ZRBOfJ+dWnaiyYD0PxRIQd4wJisti4Uad
vz61IYY/oQ/Elxk/X7GFDquYuxCSyBdHtTVMXCxFSvQ2C/7jWZFDfGGKKNoQSiJy
wDe8iiHbUOakLMmXmOTZyWJnFdR/TH5YNTiMKCNUPHAleG4IigGxDyL/gbwrdDNi
bDA4lUNhD0xNvPjQ8BNKqm5HWDvirUuHdC+4hpi0GJO34O3iiRV16YmWTuVFNboU
LDZ0+PQtctJnatpuZKPGyKX6jCpPvzzPw/EhNDlpEdrYHZMCAwEAAaOCAc4wggHK
MB0GA1UdDgQWBBSRn14xFa4Qn61gwffBzKpINC8MJjAfBgNVHSMEGDAWgBQD3lA1
VtFMu2bwo+IbG8OXsj3RVTAOBgNVHQ8BAf8EBAMCAYYwHQYDVR0lBBYwFAYIKwYB
BQUHAwEGCCsGAQUFBwMCMA8GA1UdEwEB/wQFMAMBAf8wMQYIKwYBBQUHAQEEJTAj
MCEGCCsGAQUFBzABhhVodHRwOi8vb2NzcC5kY29jc3AuY24wRAYDVR0fBD0wOzA5
oDegNYYzaHR0cDovL2NybC5kaWdpY2VydC1jbi5jb20vRGlnaUNlcnRHbG9iYWxS
b290Q0EuY3JsMIHOBgNVHSAEgcYwgcMwgcAGBFUdIAAwgbcwKAYIKwYBBQUHAgEW
HGh0dHBzOi8vd3d3LmRpZ2ljZXJ0LmNvbS9DUFMwgYoGCCsGAQUFBwICMH4MfEFu
eSB1c2Ugb2YgdGhpcyBDZXJ0aWZpY2F0ZSBjb25zdGl0dXRlcyBhY2NlcHRhbmNl
IG9mIHRoZSBSZWx5aW5nIFBhcnR5IEFncmVlbWVudCBsb2NhdGVkIGF0IGh0dHBz
Oi8vd3d3LmRpZ2ljZXJ0LmNvbS9ycGEtdWEwDQYJKoZIhvcNAQELBQADggEBABfg
eXrxIrtlixBv+KMDeqKxtNJbZiLDzJBkGCd4HI63X5eS6BElJBn6mI9eYVrr7qOL
Tp7WiO02Sf1Yrpaz/ePSjZ684o89UAGpxOfbgVSMvo/a07n/220jUWLxzaJhQNLu
lACXwwWsxYf8twP8glkoIHnUUNTlhsyyl1ZzvVC4bDpI4hC6QkJGync1MNqYSMj8
tZbhQNw3HdSmcTO0Nc/J/pK2VZc6fFbKBgspmzdHc6jMKG2t4lisXEysS3wPcg0a
Nfr1Odl5+myh3MnMK08f6pTXvduLz+QZiIh8IYL+Z6QWgTZ9e2jnV8juumX1I8Ge
7cZdtNnTCB8hFfwGLUA=
-----END CERTIFICATE-----
appname = ppt_server
httpport = 80
runmode = dev
autorender = false
copyrequestbody = true
EnableDocs = true
sqlconn =
EnableHTTPS=true
EnableHttpTLS = true
HttpsPort = 443
HTTPSCertFile="conf/2817229__offcncloud.com.pem"
HTTPSKeyFile="conf/2817229__offcncloud.com.key"
# HTTP Server
[server]
Address = ":80"
ServerAgent = "gf-app"
LogPath = "/tmp/log/gf-app/server"
DumpRouterMap = true
# Logger.
[logger]
Path = "/tmp/log/gf-app"
Level = "all"
StdoutPrint = true
HeaderPrint = true
# 回调通知
[notify]
url = "http://offcn-live-svc"
[oss]
url = "https://xiaoyu-live.oss-cn-beijing-internal.aliyuncs.com"
point = "oss-cn-beijing-internal.aliyuncs.com"
bucket = "xiaoyu-live"
# 下载zip包存储目录
[temp]
path = "/data/files/"
# Database.
[database]
debug = false
# Database logger.
[database.logger]
Path = "/tmp/log/gf-app/sql"
Level = "all"
Stdout = true
package controllers
import (
"github.com/astaxie/beego"
"ppt_server/models"
"ppt_server/upload"
)
type Response struct {
Code int `json:"code"`
Msg string `json:"msg"`
}
type UploadController struct {
beego.Controller
}
func (this *UploadController) newResponse(code int, msg string) {
response := &Response{
Code: code,
}
if msg != "" {
response.Msg = msg
}
this.Data["json"] = response
this.ServeJSON()
}
func (this *UploadController) Get() {
this.newResponse(200, "成功")
}
func (this *UploadController) Post() {
u := models.XyuSmallTempFiles{}
if err := this.ParseForm(&u); err != nil {
//handle error
this.newResponse(100, "参数绑定失败")
return
}
if u.RoomNum == "" || u.Uuid == "" || u.Url == "" {
this.newResponse(100, "参数不正确")
return
}
go upload.Upload(&u)
this.newResponse(200, "成功")
return
//fmt.Println(u)
}
\ No newline at end of file
module ppt_server
go 1.12
go 1.16
require (
github.com/aliyun/aliyun-oss-go-sdk v2.0.6+incompatible
github.com/astaxie/beego v1.12.1
github.com/beego/bee v1.12.3
github.com/go-sql-driver/mysql v1.5.0
github.com/shiena/ansicolor v0.0.0-20151119151921-a422bbe96644 // indirect
github.com/streadway/amqp v1.0.0
github.com/stretchr/objx v0.1.1 // indirect
golang.org/x/time v0.0.0-20191024005414-555d28b269f0 // indirect
github.com/aliyun/aliyun-oss-go-sdk v2.1.9+incompatible // indirect
github.com/gogf/gf v1.16.4 // indirect
github.com/xxjwxc/gowp v0.0.0-20210520113007-57eb4693b12d // indirect
golang.org/x/time v0.0.0-20210611083556-38a9dc6acbc6 // indirect
)
cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
cloud.google.com/go v0.38.0/go.mod h1:990N+gfupTy94rShfmMCWGDn0LpTmnzTp2qbd1dvSRU=
cloud.google.com/go v0.44.1/go.mod h1:iSa0KzasP4Uvy3f1mN/7PiObzGgflwredwwASm/v6AU=
cloud.google.com/go v0.44.2/go.mod h1:60680Gw3Yr4ikxnPRS/oxxkBccT6SA1yMk63TGekxKY=
cloud.google.com/go v0.45.1/go.mod h1:RpBamKRgapWJb87xiFSdk4g1CME7QZg3uwTez+TSTjc=
cloud.google.com/go v0.46.3/go.mod h1:a6bKKbmY7er1mI7TEI4lsAkts/mkhTSZK8w33B4RAg0=
cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o=
cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE=
cloud.google.com/go/firestore v1.1.0/go.mod h1:ulACoGHTpvq5r8rxGJ4ddJZBZqakUQqClKRT5SZwBmk=
cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I=
cloud.google.com/go/storage v1.0.0/go.mod h1:IhtSnM/ZTZV8YYJWCY8RULGVqBDmpoyjwiyrjsg+URw=
dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU=
github.com/BurntSushi/toml v0.3.0/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
github.com/BurntSushi/toml v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
github.com/Knetic/govaluate v3.0.0+incompatible/go.mod h1:r7JcOSlj0wfOMncg0iLm8Leh48TZaKVeNIfJntJ2wa0=
github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU=
github.com/OwnLocal/goes v1.0.0/go.mod h1:8rIFjBGTue3lCU0wplczcUgt9Gxgrkkrw7etMIcn8TM=
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/aliyun/aliyun-oss-go-sdk v2.0.6+incompatible h1:ZDgadcjGIrbHMBLSqQVHkMOdNd/jF6bsSRJd/Ysxlos=
github.com/aliyun/aliyun-oss-go-sdk v2.0.6+incompatible/go.mod h1:T/Aws4fEfogEE9v+HPhhw+CntffsBHJ8nXQCwKr0/g8=
github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o=
github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY=
github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
github.com/astaxie/beego v1.12.1 h1:dfpuoxpzLVgclveAXe4PyNKqkzgm5zF4tgF2B3kkM2I=
github.com/astaxie/beego v1.12.1/go.mod h1:kPBWpSANNbSdIqOc8SUL9h+1oyBMZhROeYsXQDbidWQ=
github.com/beego/bee v1.12.3 h1:9gCJRAhSWtUasJsX4p3BXH9QQf7MS09PdYP3xE6iD5Q=
github.com/beego/bee v1.12.3/go.mod h1:WNn8+mpl0sbRgP3JKh6wJG3pSCpEQ8hoDMZFBb0n/Ps=
github.com/beego/goyaml2 v0.0.0-20130207012346-5545475820dd/go.mod h1:1b+Y/CofkYwXMUU0OhQqGvsY2Bvgr4j6jfT699wyZKQ=
github.com/beego/x2j v0.0.0-20131220205130-a0352aadc542/go.mod h1:kSeGC/p1AbBiEp5kat81+DSQrZenVBZXklMLaELspWU=
github.com/aliyun/aliyun-oss-go-sdk v2.1.9+incompatible h1:mO8fA9l5cQ7r0D2v3WribTT1GGbNVtnVviKM51jH6lI=
github.com/aliyun/aliyun-oss-go-sdk v2.1.9+incompatible/go.mod h1:T/Aws4fEfogEE9v+HPhhw+CntffsBHJ8nXQCwKr0/g8=
github.com/ant0ine/go-json-rest v3.3.2+incompatible/go.mod h1:q6aCt0GfU6LhpBsnZ/2U+mwe+0XB5WStbmwyoPfc+sk=
github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8=
github.com/atotto/clipboard v0.1.2/go.mod h1:ZY9tmq7sm5xIbd9bOK4onWV4S6X0u6GY7Vn0Yu86PYI=
github.com/axgle/mahonia v0.0.0-20180208002826-3358181d7394/go.mod h1:Q8n74mJTIgjX4RBBcHnJ05h//6/k6foqmgE45jTQtxg=
github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q=
github.com/beorn7/perks v1.0.0/go.mod h1:KWe93zE9D1o94FZ5RNwFwVgaQK1VOXiVxmqh+CedLV8=
github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs=
github.com/bketelsen/crypt v0.0.3-0.20200106085610-5cbc8cc4026c/go.mod h1:MKsuJmJgSg28kpZDP6UIiPt0e0Oz0kqKNGyRaWEPv84=
github.com/bradfitz/gomemcache v0.0.0-20180710155616-bc664df96737/go.mod h1:PmM6Mmwb0LSuEubjR8N7PtNe1KxZLtOUHtbeikc5h60=
github.com/casbin/casbin v1.7.0/go.mod h1:c67qKN6Oum3UF5Q1+BByfFxkwKvhwW57ITjqwtzR1KE=
github.com/bitly/go-simplejson v0.5.0/go.mod h1:cXHtHw4XUPsvGaxgjIAn8PhEWG9NfngEKAMDJEczWVA=
github.com/bmizerany/assert v0.0.0-20160611221934-b7ed37b82869/go.mod h1:Ekp36dRnpXw/yCqJaO+ZrUyxD+3VXMFFr56k5XYrpB4=
github.com/btcsuite/winsvc v1.0.0/go.mod h1:jsenWakMcC0zFBFurPLEAyrnc/teJEM1O46fmI40EZs=
github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc=
github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
github.com/clbanning/mxj v1.8.5-0.20200714211355-ff02cfb8ea28 h1:LdXxtjzvZYhhUaonAaAKArG3pyC67kGL3YY+6hGG8G4=
github.com/clbanning/mxj v1.8.5-0.20200714211355-ff02cfb8ea28/go.mod h1:BVjHeAH+rl9rs6f+QIpeRl0tfu10SXn1pUSa5PVGJng=
github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
github.com/cloudflare/golz4 v0.0.0-20150217214814-ef862a3cdc58/go.mod h1:EOBUe0h4xcZ5GoxqC5SDxFQ8gwyZPKQoEzownBlhI80=
github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk=
github.com/coreos/etcd v3.3.13+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE=
github.com/coreos/go-semver v0.3.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk=
github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE=
github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk=
github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4=
github.com/coreos/pkg v0.0.0-20180928190104-399ea9e2e55f/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA=
github.com/cosiner/argv v0.1.0/go.mod h1:EusR6TucWKX+zFgtdUsKT2Cvg45K5rtpCcWz4hK06d8=
github.com/couchbase/go-couchbase v0.0.0-20181122212707-3e9b6e1258bb/go.mod h1:TWI8EKQMs5u5jLKW/tsb9VwauIrMIxQG1r5fMsswK5U=
github.com/couchbase/gomemcached v0.0.0-20181122193126-5125a94a666c/go.mod h1:srVSlQLB8iXBVXHgnqemxUXqN6FCvClgCMPCsjBDR7c=
github.com/couchbase/goutils v0.0.0-20180530154633-e865a1461c8a/go.mod h1:BQwMFlJzDjFDG3DJUdU0KORxn88UlsOULuxLExMh3Hs=
github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE=
github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E=
github.com/cupcake/rdb v0.0.0-20161107195141-43ba34106c76/go.mod h1:vYwsqCOLxGiisLwp9rITslkFNpZD5rz43tf41QFkTWY=
github.com/cpuguy83/go-md2man/v2 v2.0.0/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/denisenkom/go-mssqldb v0.0.0-20191124224453-732737034ffd/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU=
github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ=
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f/go.mod h1:cuUVRXasLTGF7a8hSLbxyZXjz+1KgoB3wDUb6vlszIc=
github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no=
github.com/edsrzf/mmap-go v0.0.0-20170320065105-0bce6a688712/go.mod h1:YO35OhQPt3KJa3ryjFM5Bs14WD66h8eGKpfaBNrHW5M=
github.com/elazarl/go-bindata-assetfs v1.0.0/go.mod h1:v+YaWX3bdea5J/mo8dSETolEo7R71Vk1u8bnjau5yw4=
github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4=
github.com/flosch/pongo2 v0.0.0-20190707114632-bbf5a6c351f4/go.mod h1:T9YF2M40nIgbVgp3rreNmTged+9HrbNTIQf1PsaIiTA=
github.com/flosch/pongo2 v0.0.0-20200529170236-5abacdfa4915/go.mod h1:fB4mx6dzqFinCxIf3a7Mf5yLk+18Bia9mPAnuejcvDA=
github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0=
github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g=
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4=
github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ=
github.com/gadelkareem/delve v1.4.2-0.20200619175259-dcd01330766f/go.mod h1:yRnaIw9CedrRtnrIhNVh1JLOz0cjEUWOEM5FaWEMOV0=
github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
github.com/go-check/check v0.0.0-20180628173108-788fd7840127/go.mod h1:9ES+weclKsC9YodN5RgxqK/VD9HM9JsCSh7rNhMZE98=
github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU=
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-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk=
github.com/go-redis/redis v6.14.2+incompatible/go.mod h1:NAIEuMOZ/fxfXJIrKDQDz8wamY7mA7PouImQ2Jvg6kA=
github.com/go-sql-driver/mysql v1.4.1 h1:g24URVg0OFbNUTx9qqY1IRZ9D9z3iPyi5zKhQZpNwpA=
github.com/go-redis/redis/v8 v8.4.11/go.mod h1:d5yY/TlkQyYBSBHnXUmnf1OrHbyQere5JV4dLKwvXmo=
github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w=
github.com/go-sql-driver/mysql v1.5.0 h1:ozyZYNQW3x3HtqT1jira07DN2PArx2v7/mN66gGcHOs=
github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
github.com/gogf/gf v1.16.4 h1:1Y8/P1UMp9BmrtUn0wAg3g6ElRAO0R9QHCdUNt9Z5L4=
github.com/gogf/gf v1.16.4/go.mod h1:EjnxZXddTwfFoLPofDE3NokFWx+immofINtSyFCj280=
github.com/gogf/mysql v1.6.1-0.20210603073548-16164ae25579 h1:pP/uEy52biKDytlgK/ug8kiYPAiYu6KajKVUHfGrtyw=
github.com/gogf/mysql v1.6.1-0.20210603073548-16164ae25579/go.mod h1:52e6mXyNnHAsFrXrSnj5JPRSKsZKpHylVtA3j4AtMz8=
github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4=
github.com/golang-sql/civil v0.0.0-20190719163853-cb61b32ac6fe/go.mod h1:8vg3r2VgvsThLBIFL93Qb5yWzgyZWhEmBwUJWevAkK0=
github.com/golang/freetype v0.0.0-20170609003504-e2365dfdc4a0/go.mod h1:E/TSTwGwJL78qG/PmXZO1EjYhfJinVAhrmmHX6Z8B9k=
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
github.com/golang/groupcache v0.0.0-20190129154638-5b532d6fd5ef/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
github.com/golang/mock v1.2.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
github.com/golang/mock v1.3.1/go.mod h1:sBzyDLLjw3U8JLTeZvSv8jJB+tU5PVekmnlKIyFUx0Y=
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
github.com/golang/protobuf v1.3.1/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8=
github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA=
github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs=
github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w=
github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0=
github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI=
github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
github.com/gomodule/redigo v1.8.3/go.mod h1:P9dn9mFrCBvWhGE1wpxx6fgq7BAeLBk+UUUzlpkBYO0=
github.com/gomodule/redigo v2.0.0+incompatible h1:K/R+8tc58AaqLkqG2Ol3Qk+DR/TlNuhuh457pBFPtt0=
github.com/gomodule/redigo v2.0.0+incompatible/go.mod h1:B4C85qUVwatsJoIUNIfCRsp7qO0iAmpGFZ4EELWSbC4=
github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
github.com/google/btree v1.0.0/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
github.com/google/go-dap v0.2.0/go.mod h1:5q8aYQFnHOAZEMP+6vmq25HKYAEwE+LF5yh7JKrrhSQ=
github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs=
github.com/google/pprof v0.0.0-20181206194817-3ea8567a2e57/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc=
github.com/google/pprof v0.0.0-20190515194954-54271f7e092f/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc=
github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI=
github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg=
github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk=
github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY=
github.com/gorilla/websocket v1.4.2/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE=
github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/gookit/color v1.2.5/go.mod h1:AhIE+pS6D4Ql0SQWbBeXPHw7gY0/sjHoA4s/n1KB7xg=
github.com/gorilla/websocket v1.4.0/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ=
github.com/gorilla/websocket v1.4.1 h1:q7AeDBpnBk8AogcD4DSag/Ukw/KV+YhzLj2bP5HvKCM=
github.com/gorilla/websocket v1.4.1/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE=
github.com/grokify/html-strip-tags-go v0.0.0-20190921062105-daaa06bf1aaf h1:wIOAyJMMen0ELGiFzlmqxdcV1yGbkyHBAB6PolcNbLA=
github.com/grokify/html-strip-tags-go v0.0.0-20190921062105-daaa06bf1aaf/go.mod h1:2Su6romC5/1VXOQMaWL2yb618ARB8iVo6/DR99A6d78=
github.com/grpc-ecosystem/go-grpc-middleware v1.0.0/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs=
github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk=
github.com/grpc-ecosystem/grpc-gateway v1.9.0/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY=
github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBtguAZLlVdkD9Q=
github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8=
github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
github.com/hashicorp/go-msgpack v0.5.3/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM=
github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk=
github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU=
github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU=
github.com/hashicorp/go-syslog v1.0.0/go.mod h1:qPfqrKkXGihmCqbJM2mZgkZGvKG1dFdvsLplgctolz4=
github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go.net v0.0.1/go.mod h1:hjKkEWcCURg++eb33jQU7oqQcI9XDCnUzHA0oac0k90=
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
github.com/hashicorp/golang-lru v0.5.4/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4=
github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ=
github.com/hashicorp/logutils v1.0.0/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64=
github.com/hashicorp/mdns v1.0.0/go.mod h1:tL+uN++7HEJ6SQLQ2/p+z2pH24WQKWjBPkE0mNTz8vQ=
github.com/hashicorp/memberlist v0.1.3/go.mod h1:ajVTdAv/9Im8oMAAj5G31PhhMCZJV2pPBoIllUwCN7I=
github.com/hashicorp/serf v0.8.2/go.mod h1:6hOLApaqBFA1NXqRQAsxw9QxuDEvNxSQRwA/JwenrHc=
github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU=
github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
github.com/jander/golog v0.0.0-20150917071935-954a5be801fc/go.mod h1:uWhWXOR4dpfk9J8fegnMY7sP2GFXxe3PFI9Ps+TRXJs=
github.com/jinzhu/gorm v1.9.12/go.mod h1:vhTjlKSJUTWNtcbQtrMBFCxy7eXTzeCAzfL5fBZT/Qs=
github.com/jinzhu/inflection v1.0.0/go.mod h1:h+uFLlag+Qp1Va5pdKtLDYj+kHp5pxUVkryuEj+Srlc=
github.com/jinzhu/now v1.0.1/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8=
github.com/jinzhu/now v1.1.1/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/z8=
github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo=
github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU=
github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU=
github.com/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU=
github.com/juju/errors v0.0.0-20181118221551-089d3ea4e4d5/go.mod h1:W54LbzXuIE0boCoNJfwqpmkKJ1O4TCTZMetAt6jGk7Q=
github.com/juju/errors v0.0.0-20190930114154-d42613fe1ab9/go.mod h1:W54LbzXuIE0boCoNJfwqpmkKJ1O4TCTZMetAt6jGk7Q=
github.com/juju/loggo v0.0.0-20180524022052-584905176618/go.mod h1:vgyd7OREkbtVEN/8IXZe5Ooef3LQePvuBm9UWj6ZL8U=
github.com/juju/testing v0.0.0-20180920084828-472a3e8b2073/go.mod h1:63prj8cnj0tU0S9OHjGJn+b1h0ZghCndfnbQolrYTwA=
github.com/jroimartin/gocui v0.4.0/go.mod h1:7i7bbj99OgFHzo7kB2zPb8pXLqMBSQegY7azfqXMkyY=
github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w=
github.com/kardianos/service v1.0.0/go.mod h1:8CzDhVuCuugtsHyZoTvsOBuvonN/UDBvl0kH+BUxvbo=
github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q=
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
github.com/konsorten/go-windows-terminal-sequences v1.0.3/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc=
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
github.com/lib/pq v1.0.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
github.com/lib/pq v1.7.0/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
github.com/mattn/go-colorable v0.0.0-20170327083344-ded68f7a9561/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
github.com/mattn/go-sqlite3 v1.10.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc=
github.com/mattn/goveralls v0.0.2/go.mod h1:8d1ZMHsd7fW6IRPKQh46F2WRpyib5/X4FOpevwGNQEw=
github.com/lib/pq v1.1.1/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
github.com/mailru/easyjson v0.7.1/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs=
github.com/mattn/go-runewidth v0.0.9/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI=
github.com/mattn/go-runewidth v0.0.10 h1:CoZ3S2P7pvtP45xOtBw+/mDL2z0RKI576gSkzRRpdGg=
github.com/mattn/go-runewidth v0.0.10/go.mod h1:RAqKPSqVFrSLVXbA8x7dzmKdmGzieGRCM46jaSJTDAk=
github.com/mattn/go-sqlite3 v2.0.1+incompatible/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc=
github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0=
github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc=
github.com/mitchellh/go-homedir v1.0.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
github.com/mitchellh/go-testing-interface v1.0.0/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI=
github.com/mitchellh/gox v0.4.0/go.mod h1:Sd9lOJ0+aimLBi73mGofS1ycjY8lL3uZM3JPS42BGNg=
github.com/mitchellh/iochan v1.0.0/go.mod h1:JwYml1nuB7xOzsp52dPpHFffvOCDupsG0QubkSMEySY=
github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0=
github.com/muesli/cache2go v0.0.0-20200423001931-a100c5aac93f/go.mod h1:414R+qZrt4f9S2TO/s6YVQMNAXR2KdwqQ7pW+O4oYzU=
github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U=
github.com/nicksnyder/go-i18n/v2 v2.0.3/go.mod h1:oDab7q8XCYMRlcrBnaY/7B1eOectbvj6B1UPBT+p5jo=
github.com/nsf/termbox-go v0.0.0-20200418040025-38ba6e5628f1/go.mod h1:IuKpRQcYE1Tfu+oAQqaLisqDeXgjyyltCfsaoYN18NQ=
github.com/nsqio/go-nsq v1.0.8/go.mod h1:vKq36oyeVXgsS5Q8YEO7WghqidAVXQlcFxzQbQTuDEY=
github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A=
github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U=
github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc=
github.com/olekukonko/tablewriter v0.0.5 h1:P2Ga83D34wi1o9J6Wh1mRuqd4mF/x/lgBS7N7AbDhec=
github.com/olekukonko/tablewriter v0.0.5/go.mod h1:hPp6KlRPjbx+hW8ykQs1w3UBbZlj6HuIJcUGPhkA7kY=
github.com/olivere/elastic v6.2.31+incompatible/go.mod h1:J+q1zQJTgAz9woqsbVRqGeB5G1iqDKVBWLNSYW8yfJ8=
github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk=
github.com/onsi/ginkgo v1.14.2/go.mod h1:iSB4RoI2tjJc9BBv4NKIKWKya62Rps+oPG/Lv9klQyY=
github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY=
github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo=
github.com/onsi/gomega v1.10.4/go.mod h1:g/HbgYopi++010VEqkFgJHKC09uJiW9UkXvMUuKHUCQ=
github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic=
github.com/peterh/liner v0.0.0-20170317030525-88609521dc4b/go.mod h1:xIteQHvHuaLYG9IFj6mSxM0fCKrs34IrEQUhOYuGPHc=
github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI=
github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw=
github.com/prometheus/client_golang v0.9.3/go.mod h1:/TN21ttK/J9q6uSwhBd54HahCDft0ttaMvbicHlPoso=
github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
......@@ -178,184 +147,139 @@ github.com/prometheus/common v0.4.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y8
github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk=
github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA=
github.com/prometheus/tsdb v0.7.1/go.mod h1:qhTCs0VvXwvX/y3TZrWD7rabWM+ijKTux40TwIPHuXU=
github.com/rivo/uniseg v0.1.0 h1:+2KBaVoUmb9XzDsrx/Ct0W/EYOSFf/nWTauy++DprtY=
github.com/rivo/uniseg v0.1.0/go.mod h1:J6wj4VEh+S6ZtnVlnTBMWIodfgj8LQOQFoIToxlJtxc=
github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg=
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g=
github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts=
github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc=
github.com/shiena/ansicolor v0.0.0-20151119151921-a422bbe96644 h1:X+yvsM2yrEktyI+b2qND5gpH8YhURn0k8OCaeRnkINo=
github.com/shiena/ansicolor v0.0.0-20151119151921-a422bbe96644/go.mod h1:nkxAfR/5quYxwPZhyDxgasBMnRtBZd0FCEpawpjMUFg=
github.com/siddontang/go v0.0.0-20180604090527-bdc77568d726/go.mod h1:3yhqj7WBBfRhbBlzyOC3gUxftwsU0u8gqevxwIHQpMw=
github.com/siddontang/ledisdb v0.0.0-20181029004158-becf5f38d373/go.mod h1:mF1DpOSOUiJRMR+FDqaqu3EBqrybQtrDDszLUZ6oxPg=
github.com/siddontang/rdb v0.0.0-20150307021120-fc89ed2e418d/go.mod h1:AMEsy7v5z92TR1JKMkLLoaOQk++LVnOKL3ScbJ8GNGA=
github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
github.com/shurcooL/sanitized_anchor_name v1.0.0/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc=
github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo=
github.com/sirupsen/logrus v1.6.0/go.mod h1:7uNnSEd1DgxDLC74fIahvMZmmYsHGZGEOFrfsX/uA88=
github.com/smartwalle/pongo2render v1.0.1/go.mod h1:MGnTzND7nEMz7g194kjlnw8lx/V5JJlb1hr5kDXEO0I=
github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc=
github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA=
github.com/soheilhy/cmux v0.1.4/go.mod h1:IM3LyeVVIOuxMH7sFAkER9+bJ4dT7Ms6E4xg4kGIyLM=
github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ=
github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE=
github.com/spf13/cobra v0.0.0-20170417170307-b6cb39589372/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ=
github.com/spf13/cobra v1.0.0/go.mod h1:/6GTrnGXV9HjY+aR4k0oJ5tcvakLuG6EuKReYlHNrgE=
github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo=
github.com/spf13/pflag v0.0.0-20170417173400-9e4c21054fa1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
github.com/spf13/viper v1.7.0/go.mod h1:8WkrPz2fc9jxqZNCJI/76HCieCp4Q8HaLFoCha5qpdg=
github.com/ssdb/gossdb v0.0.0-20180723034631-88f6b59b84ec/go.mod h1:QBvMkMya+gXctz3kmljlUCu/yB3GZ6oee+dUozsezQE=
github.com/streadway/amqp v1.0.0 h1:kuuDrUJFZL1QYL9hUNuCxNObNzB0bV/ZG5jV3RWAQgo=
github.com/streadway/amqp v1.0.0/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw=
github.com/spf13/viper v1.4.0/go.mod h1:PTJ7Z/lr49W6bUbkmS1V3by4uWynFiR9p7+dSq/yZzE=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw=
github.com/syndtr/goleveldb v0.0.0-20181127023241-353a9fca669c/go.mod h1:Z4AUp2Km+PwemOoO/VB5AOx9XSsIItzFjoJlOSiYmn0=
github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/syndtr/goleveldb v1.0.0/go.mod h1:ZVVdQEZoIme9iO1Ch2Jdy24qqXrMMOU6lpPAyBWyWuQ=
github.com/tmc/grpc-websocket-proxy v0.0.0-20190109142713-0ad062ec5ee5/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U=
github.com/wendal/errors v0.0.0-20130201093226-f66c77a7882b/go.mod h1:Q12BUT7DqIlHRmgv3RskH+UCM/4eqVMgI0EMmlSpAXc=
github.com/ugorji/go v1.1.4/go.mod h1:uQMGLiO92mf5W77hV/PUCpI3pbzQx3CRekS0kk+RGrc=
github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2/go.mod h1:UETIi67q53MR2AWcXfiuqkDkRtnGDLqkBTpCHuJHxtU=
github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q=
github.com/xxjwxc/gowp v0.0.0-20200603130651-4d7368b0e285/go.mod h1:yJ/fY5BorWARfDDsxBU/MyQTHc5MVyNcqBQQYD6MN0k=
github.com/xxjwxc/gowp v0.0.0-20210520113007-57eb4693b12d h1:ABCF9ZzxafV48FUus2qPE+Pq8K7e0f6YnvVV5fTBIyw=
github.com/xxjwxc/gowp v0.0.0-20210520113007-57eb4693b12d/go.mod h1:oaLsbo1ZWr4jYanHCB6zQetBkmQHNNH8N9E7xbmrLWc=
github.com/xxjwxc/public v0.0.0-20200603115833-341beff27850/go.mod h1:fp3M+FEQrCgWD1fZ/PLwZkCTglf086OEhC9LcydAUnc=
github.com/xxjwxc/public v0.0.0-20210518123934-6cc0965f0bc5 h1:PYu1xvS3JoXfLl3Yz5H0vdxdlvsMItQoFOZccJMIG54=
github.com/xxjwxc/public v0.0.0-20210518123934-6cc0965f0bc5/go.mod h1:za2pkqdDH64CbdyuZz6dqI+IhjCgstXeoWD3IAWbiAc=
go.etcd.io/bbolt v1.3.2/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU=
go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU=
go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8=
go.starlark.net v0.0.0-20190702223751-32f345186213/go.mod h1:c1/X6cHgvdXj6pUlmWKMkuqRnW4K8x2vwt6JAaaircg=
go.opentelemetry.io/otel v0.16.0/go.mod h1:e4GKElweB8W2gWUqbghw0B8t5MCTccc9212eNHnOHwA=
go.opentelemetry.io/otel v0.19.0 h1:Lenfy7QHRXPZVsw/12CWpxX6d/JkrX8wrx2vO8G80Ng=
go.opentelemetry.io/otel v0.19.0/go.mod h1:j9bF567N9EfomkSidSfmMwIwIBuP37AMAIzVW85OxSg=
go.opentelemetry.io/otel/metric v0.19.0 h1:dtZ1Ju44gkJkYvo+3qGqVXmf88tc+a42edOywypengg=
go.opentelemetry.io/otel/metric v0.19.0/go.mod h1:8f9fglJPRnXuskQmKpnad31lcLJ2VmNNqIsx/uIwBSc=
go.opentelemetry.io/otel/oteltest v0.19.0/go.mod h1:tI4yxwh8U21v7JD6R3BcA/2+RBoTKFexE/PJ/nSO7IA=
go.opentelemetry.io/otel/trace v0.19.0 h1:1ucYlenXIDA1OlHVLDZKX0ObXV5RLaq06DtUKz5e5zc=
go.opentelemetry.io/otel/trace v0.19.0/go.mod h1:4IXiNextNOpPnRlI4ryK69mn5iC84bjBWZQA5DXz/qg=
go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE=
go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0=
go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q=
golang.org/x/arch v0.0.0-20190927153633-4e8777c89be4/go.mod h1:flIaEI6LNU6xOCD5PaJvn9wGP0agmIOqjrtsKGRguv4=
golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
golang.org/x/crypto v0.0.0-20181029021203-45a5f77698d3/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550 h1:ObdrDkeb4kJdCP557AjRjq69pTHfNouLtWZG7j9rPN8=
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8=
golang.org/x/exp v0.0.0-20190829153037-c13cbed26979/go.mod h1:86+5VVa7VpoJ4kLfm080zCjGlMRFzhUhsZKEZO7MGek=
golang.org/x/exp v0.0.0-20191030013958-a1ab85dbe136/go.mod h1:JXzH8nQsPlswgeRAPE3MuO9GYsAcnJvJ4vnMwN/5qkY=
golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js=
golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
golang.org/x/crypto v0.0.0-20190506204251-e1dfcc566284/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
golang.org/x/crypto v0.0.0-20191205180655-e7c4368fe9dd/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
golang.org/x/image v0.0.0-20200430140353-33d19683fad8/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU=
golang.org/x/lint v0.0.0-20190301231843-5614ed5bae6f/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
golang.org/x/lint v0.0.0-20190409202823-959b441ac422/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
golang.org/x/lint v0.0.0-20190909230951-414d861bb4ac/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
golang.org/x/mobile v0.0.0-20190312151609-d3739f865fa6/go.mod h1:z+o9i4GpDbdi3rU15maQ/Ox0txvL9dWGYEHz965HBQE=
golang.org/x/mobile v0.0.0-20190719004257-d2bd2a29d028/go.mod h1:E/iHnbuqvinMTCcRqshq8CkpyQDoeVncDDYHnLhea+o=
golang.org/x/mod v0.0.0-20190513183733-4bf6d317e70e/go.mod h1:mXi4GBBbnImb6dmsKGUJ2LatrhH/nqhxcFungHvyanc=
golang.org/x/mod v0.1.0/go.mod h1:0QHyrYULN0/3qlju5TqG8bIK38QM8yzMo5ekMj3DlcY=
golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg=
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20181023162649-9b4f9f5ad519/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20181114220301-adae6a3d119a/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20181201002055-351d144fa1fc/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20181220203305-927f97764cc3/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
golang.org/x/net v0.0.0-20190501004415-9ce7a6920f09/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
golang.org/x/net v0.0.0-20190503192946-f4e77d36d62c/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
golang.org/x/net v0.0.0-20190603091049-60506f45cf65/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks=
golang.org/x/net v0.0.0-20190620200207-3b0461eec859 h1:R/3boaszxrf1GEUWTVDzSKVwLmSJpwZ1yqXm8j0v2QI=
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
golang.org/x/net v0.0.0-20190522155817-f3200d17e092/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks=
golang.org/x/net v0.0.0-20200506145744-7e3656a0809f/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
golang.org/x/net v0.0.0-20201031054903-ff519b6c9102 h1:42cLlJJdEh+ySyeUUbEQ5bsTiq8voBeTuweGVkY6Puw=
golang.org/x/net v0.0.0-20201031054903-ff519b6c9102/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
golang.org/x/net v0.0.0-20201202161906-c7110b5ffcbb h1:eBmm0M9fYhWpKZLjQUUKka/LtIxf46G4fxeEz5KJr9U=
golang.org/x/net v0.0.0-20201202161906-c7110b5ffcbb/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20181026203630-95b1ffbd15a5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20181107165924-66b7b1311ac8/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20190204203706-41f3e6584952/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190502145724-3ef323f4f1fd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190606165138-5da285871e9c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190624142023-c5567b49c5d0/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190626221950-04f50cda93cb/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg=
golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20200519105757-fe76b779f299/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f h1:+Nyd8tzPX9R7BWHguqsrbFdRx3WQ/1ib8I44HXV5yTA=
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
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/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.4 h1:0YWbFKbhXG/wIiuHDSKpS0Iy7FSA+u45VtBMfQcFTTc=
golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/time v0.0.0-20191024005414-555d28b269f0 h1:/5xXl8Y5W96D+TtHSlonuFqGHIWVuyCkGJLwGh9JJFs=
golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/time v0.0.0-20210611083556-38a9dc6acbc6 h1:Vv0JUPWTyeqUq42B2WJ1FeIDjjvGKoA2Ss+Ts0lAVbs=
golang.org/x/time v0.0.0-20210611083556-38a9dc6acbc6/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/tools v0.0.0-20180221164845-07fd8470d635/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20181221001348-537d06c36207/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY=
golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
golang.org/x/tools v0.0.0-20190312170243-e65039ee4138/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
golang.org/x/tools v0.0.0-20190328211700-ab21143f2384/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
golang.org/x/tools v0.0.0-20190425150028-36563e24a262/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
golang.org/x/tools v0.0.0-20190506145303-2d16b83fe98c/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
golang.org/x/tools v0.0.0-20190606124116-d0a3d012864b/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
golang.org/x/tools v0.0.0-20190621195816-6e04913cbbac/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
golang.org/x/tools v0.0.0-20190628153133-6cdbf07be9d0/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
golang.org/x/tools v0.0.0-20190816200558-6889da9d5479/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
golang.org/x/tools v0.0.0-20190911174233-4f2ddba30aff/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
golang.org/x/tools v0.0.0-20191012152004-8de300cfc20a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
golang.org/x/tools v0.0.0-20191112195655-aa38f8e97acc/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
golang.org/x/tools v0.0.0-20191127201027-ecd32218bd7f/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
golang.org/x/tools v0.0.0-20200117065230-39095c1d176c/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28=
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
google.golang.org/api v0.4.0/go.mod h1:8k5glujaEP+g9n7WNsDg8QP6cUVNI86fCNMcbazEtwE=
google.golang.org/api v0.7.0/go.mod h1:WtwebWUNSVBH/HAw79HIFXZNqEvBhG+Ra+ax0hx3E3M=
google.golang.org/api v0.8.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg=
google.golang.org/api v0.9.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg=
google.golang.org/api v0.13.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI=
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
google.golang.org/appengine v1.6.1/go.mod h1:i06prIuMbXzDqacNJfV5OdTW448YApPu5ww/cMBSeb0=
google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
google.golang.org/genproto v0.0.0-20190307195333-5fe7a883aa19/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE=
google.golang.org/genproto v0.0.0-20190418145605-e7d98fc518a7/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE=
google.golang.org/genproto v0.0.0-20190425155659-357c62f0e4bb/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE=
google.golang.org/genproto v0.0.0-20190502173448-54afdca5d873/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE=
google.golang.org/genproto v0.0.0-20190801165951-fa694d86fc64/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
google.golang.org/genproto v0.0.0-20190911173649-1774047e7e51/go.mod h1:IbNlFCBrqXvoKpeg0TB2l7cyZUmoaFKYIwrEpbDKLA8=
google.golang.org/genproto v0.0.0-20191108220845-16a3f7862a1a/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc=
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38=
google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM=
google.golang.org/grpc v1.21.0/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM=
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE=
google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo=
google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI=
gopkg.in/ini.v1 v1.51.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k=
gopkg.in/mgo.v2 v2.0.0-20180705113604-9856a29383ce/go.mod h1:yeKp02qBN3iKW1OzL3MGk2IdtZzaj7SFntXj72NppTA=
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/eapache/queue.v1 v1.1.0 h1:EldqoJEGtXYiVCMRo2C9mePO2UUGnYn2+qLmlQSqPdc=
gopkg.in/eapache/queue.v1 v1.1.0/go.mod h1:wNtmx1/O7kZSR9zNT1TTOJ7GLpm3Vn7srzlfylFbQwU=
gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
gopkg.in/go-with/wxpay.v1 v1.3.0/go.mod h1:12lWy92n19pAUSSE3BrOiEZbWRkl+9tneOd/aU/LU6g=
gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24xpD6X8LsfU/+k=
gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo=
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw=
gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74=
gopkg.in/yaml.v2 v2.2.1 h1:mUhvW9EsL+naU5Q3cakzfE91YhliOondGd6ZrsDBHQE=
gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU=
gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
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=
honnef.co/go/tools v0.0.0-20190418001031-e561f6794a2a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
honnef.co/go/tools v0.0.1-2019.2.3/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg=
rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8=
rsc.io/pdf v0.1.1/go.mod h1:n8OzWcQ6Sp37PL01nO98y4iUCRdTGarVfzxY20ICaU4=
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=
gorm.io/driver/mysql v1.0.1/go.mod h1:KtqSthtg55lFp3S5kUXqlGaelnWpKitn4k1xZTnoiPw=
gorm.io/gorm v1.9.19/go.mod h1:0HFTzE/SqkGTzK6TlDPPQbAYCluiVvhzoA1+aVyzenw=
gorm.io/gorm v1.20.2/go.mod h1:0HFTzE/SqkGTzK6TlDPPQbAYCluiVvhzoA1+aVyzenw=
honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
\ No newline at end of file
/**
* @Authore: lifeifei
* @Date: 2021/7/22 2:08 下午
*/
package interfaces
// 分组路由
type Router interface {
Init()
}
package http
import (
"fmt"
"io"
"os"
"strings"
"time"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/net/ghttp"
"github.com/gogf/gf/util/gconv"
)
func Get(url string) ([]byte, error) {
return handle(g.Client().Timeout(30 * time.Second).Get(url))
}
func handle(response *ghttp.ClientResponse, err error) ([]byte, error) {
if err != nil {
return nil, err
}
defer response.Close()
return response.ReadAll(), nil
}
type WriteCounter struct {
Total uint64
Length uint64
}
func (wc *WriteCounter) Write(p []byte) (int, error) {
n := len(p)
wc.Total += uint64(n)
wc.PrintProgress()
return n, nil
}
func (wc WriteCounter) PrintProgress() {
// Clear the line by using a character return to go back to the start and remove
// the remaining characters by filling it with spaces
fmt.Printf("\r%s", strings.Repeat(" ", 35))
// Return again and print current status of download
// We use the humanize package to print the bytes in a meaningful way (e.g. 10 MB)
fmt.Printf("\rDownloading... %s complete", fmt.Sprintf("%.2f", gconv.Float64(wc.Total)/gconv.Float64(wc.Length) * 100) + "%")
}
// 下载文件
func Download(file string, path string) error {
g.Log().Async().Infof("Download File: %s", path)
resp, err := g.Client().Get(file)
if err != nil {
return err
}
defer resp.Body.Close()
// 创建一个文件用于保存
out, err := os.Create(path)
if err != nil {
return err
}
defer out.Close()
// 然后将响应流和文件流对接起来
counter := &WriteCounter{Length: gconv.Uint64(resp.Header.Get("Content-Length"))}
_, err = io.Copy(out, io.TeeReader(resp.Body, counter))
if err != nil && err == io.EOF {
return nil
}
if err != nil {
return err
}
fmt.Print("\n")
return nil
}
/**
* @Authore: lifeifei
* @Date: 2021/7/21 4:26 下午
*/
package http
import (
"net/http"
"net/http/cookiejar"
"time"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/net/ghttp"
)
// 保持会话请求
type SessionHttpClient struct {
c *ghttp.Client
}
func NewSessionHttpClient() *SessionHttpClient {
jar, _ := cookiejar.New(nil)
c := g.Client()
c.Jar = jar
c.CheckRedirect = func(req *http.Request, via []*http.Request) error {
return http.ErrUseLastResponse
}
return &SessionHttpClient{c}
}
func (client *SessionHttpClient) Post(link string, data ...interface{}) ([]byte, error) {
return handle(client.c.Timeout(10*time.Second).Post(link, data))
}
func (client *SessionHttpClient) Get(url string) ([]byte, error) {
return handle(client.c.Timeout(10 * time.Second).Get(url))
}
/**
* @Authore: lifeifei
* @Date: 2021/7/23 2:48 下午
*/
package oss
import (
"io"
"os"
"sync"
"github.com/aliyun/aliyun-oss-go-sdk/oss"
"github.com/gogf/gf/frame/g"
)
var (
client *oss.Client
bucket *oss.Bucket
once sync.Once
)
func init() {
once.Do(func() {
client, _ = oss.New(g.Cfg().GetString("oss.point"),
os.Getenv("s_access_id"), os.Getenv("s_access_secret"))
bucket, _ = client.Bucket(g.Cfg().GetString("oss.bucket"))
})
}
//OSS上传
func Upload(path string, reader io.Reader) error {
return bucket.PutObject(path, reader)
}
/**
* @Authore: lifeifei
* @Date: 2021/7/21 3:08 下午
*/
package response
import (
"net/http"
"github.com/gogf/gf/errors/gerror"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/net/ghttp"
"github.com/gogf/gf/util/gvalid"
)
func Success(r *ghttp.Request, data ...interface{}) {
res := g.Map{
"code": 0,
"msg": "成功",
"data": nil,
}
if len(data) > 0 {
res["data"] = data[0]
}
_ = r.Response.WriteJsonExit(res)
}
func Fail(r *ghttp.Request, err error) {
switch e := err.(type) {
case gvalid.Error:
_ = r.Response.WriteJsonExit(g.Map{
"code": http.StatusBadRequest,
"msg": e.FirstString(),
})
case *gerror.Error:
_ = r.Response.WriteJsonExit(g.Map{
"code": e.Code(),
"msg": e.Error(),
})
default:
_ = r.Response.WriteJsonExit(g.Map{
"code": http.StatusInternalServerError,
"msg": e.Error(),
})
}
}
package main
import (
"archive/zip"
"crypto/md5"
"crypto/sha1"
"encoding/hex"
"encoding/json"
"errors"
"fmt"
"github.com/aliyun/aliyun-oss-go-sdk/oss"
"github.com/astaxie/beego"
"github.com/astaxie/beego/orm"
_ "ppt_server/boot"
_ "ppt_server/router"
"io"
"io/ioutil"
"mime"
"net/http"
"net/http/cookiejar"
"os"
"path"
"ppt_server/models"
_ "ppt_server/routers"
"regexp"
Qurl "net/url"
"strconv"
"strings"
"time"
)
var (
WEBURL string = "http://offcn-live-svc"
client *http.Client
token string
"github.com/gogf/gf/frame/g"
)
const docUrl string = "http://doc.offcncloud.com/"
func main() {
if beego.BConfig.RunMode == "dev" {
beego.BConfig.WebConfig.DirectoryIndex = true
beego.BConfig.WebConfig.StaticDir["/swagger"] = "swagger"
}
beego.Run()
}
//func main() {
//tick := time.NewTicker(30 * time.Minute)
//upload()
//for {
// select {
// case <-tick.C:
// upload()
// }
//}
//}
func ptoken() {
qclient, qtoken, err := webToken()
client = qclient
token = qtoken
if err != nil {
fmt.Println(err)
return
}
}
func upload() {
o := orm.NewOrm()
var files []*models.XyuSmallTempFiles
_, _ = o.QueryTable("xyu_small_temp_files").Filter("status", 1).All(&files)
if len(files) > 0 {
ptoken()
for _, v := range files {
go Down(v)
}
}
}
func Down(v *models.XyuSmallTempFiles) {
o := orm.NewOrm()
url, _ := Qurl.QueryUnescape(v.Url)
filename := path.Base(url)
filePath := "/data/files/" + filename
// 文件以及存在就不需要下载
if _, err := os.Stat(filePath); err != nil {
// Get the data
resp, err := http.Get(url)
if err != nil {
fmt.Println(err)
return
}
defer resp.Body.Close()
// 创建一个文件用于保存
out, err := os.Create(filePath)
if err != nil {
fmt.Println(err)
return
}
defer out.Close()
// 然后将响应流和文件流对接起来
_, err = io.Copy(out, resp.Body)
if err != nil {
fmt.Println(err)
return
}
}
var room models.XyuRoom
err := o.QueryTable("xyu_room").Filter("room_num", v.RoomNum).One(&room)
if err != nil {
fmt.Println(err)
return
}
bucket, err := newOssClient()
if err != nil {
fmt.Println(err)
return
}
file, err := os.Open(filePath)
if err != nil {
fmt.Println(err)
return
}
defer file.Close()
room_file := make(map[string]interface{})
t := time.Now()
now := fmt.Sprintf("%02d-%02d-%02d %02d:%02d:%02d",
t.Year(), t.Month(), t.Day(), t.Hour(), t.Minute(), t.Second())
room_file["room_id"] = room.Id
room_file["id"] = t.Unix()
room_file["is_courseware"] = "1"
room_file["private"] = "1"
room_file["nickname"] = "助教"
room_file["name"] = filename
room_file["time"] = now
if v.Type == 1 {
room_file["is_material"] = 1
} else if v.Type == 2 {
room_file["is_courseware"] = 1
} else if v.Type == 3 {
room_file["is_titlebook"] = 1
}
contentHash, _ := fileContentHash(file)
fileHash := []byte(filename)
fileHashName := fmt.Sprintf("%x", sha1.Sum(fileHash))
room_file["file_name_hash"] = fileHashName
room_file["hash"] = contentHash
//获取文件后缀
ext := path.Ext(filename)
var doc_type string
doc_type = "0"
if strings.Contains(ext, "ppt") || strings.Contains(ext, "pptx") {
doc_type = "4"
} else if strings.Contains(ext, "doc") || strings.Contains(ext, "docx") {
doc_type = "2"
} else if strings.Contains(ext, "xls") || strings.Contains(ext, "xlsx") {
doc_type = "3"
} else if strings.Contains(ext, "pdf") {
doc_type = "1"
}
room_file["doc_type"] = doc_type
_ = mime.AddExtensionType(".pptx", "application/vnd.openxmlformats-officedocument.presentationml.presentation")
room_file["type"] = mime.TypeByExtension(ext)
fd, err := os.Open(filePath)
if err != nil {
fmt.Println(err)
return
}
defer fd.Close()
objectPath := "documents/" + v.RoomNum + "/" + contentHash + "/" + fileHashName + "/"
objectName := objectPath + contentHash + ext
fmt.Println("objectName == ", objectName)
room_file["path"] = objectPath
err = bucket.PutObject(objectName, fd)
if err != nil {
fmt.Println(err)
return
}
furl := "https://xiaoyu-live.oss-cn-beijing.aliyuncs.com/" + objectName
maps, err := getFileInfo(furl)
if err != nil {
fmt.Println(err)
return
}
room_file["files_size"] = strconv.Itoa(int(maps["FileSize"].(float64)))
room_file["link"] = furl
wordFloat64 := getWords(maps)
downUrl := fmt.Sprintf("http://doc.offcncloud.com/?info=1&words=%v&ssl=1&furl=%s",
wordFloat64, furl)
go func() {
err := uploadPacked(bucket, filename, contentHash, objectPath,
wordFloat64)
if err != nil {
fmt.Println(err)
return
}
}()
ch := make(chan bool)
go func() {
err := downloadFile(downUrl, func(length, downLen int64) {
})
if err == nil {
ch <- true
}
}()
<-ch
var uploadImageCount float64
reader, err := zip.OpenReader( "/data/files/" + contentHash + ".zip")
if err != nil {
fmt.Println(err)
return
}
ch1 := make(chan bool)
for _, file := range reader.File {
go func(file *zip.File) {
err := pdfThumbnail(objectPath, file, bucket)
if err != nil {
fmt.Println(objectPath + file.Name + "上传失败")
// 上传缩略图失败,重试3次
for i := 0; i < 3; i++ {
err = pdfThumbnail(objectPath, file, bucket)
if err == nil {
ch1 <- true
return
}
}
ch1 <- false
return
} else {
ch1 <- true
return
}
}(file)
}
for i := 0; i < int(wordFloat64); i++ {
t := <-ch1
if t {
uploadImageCount++
}
}
defer reader.Close()
fmt.Println(uploadImageCount, wordFloat64)
if uploadImageCount != wordFloat64 {
fmt.Println("上传失败")
return
}
//调用服务端接口写入数据库
var roomFile models.XyuRoomFiles
err = o.QueryTable("xyu_room_files").Filter("room_id", room.Id).Filter("name", filename).One(&roomFile)
if err == orm.ErrNoRows {
err = createFileDataBase(room_file)
if err != nil {
fmt.Println(err)
return
}
}
elapsed := time.Since(t)
fmt.Println("filename == ", filename, " 上传成功, 上传耗时 == ", elapsed)
// 删除压缩包和删除文件
defer os.Remove(filePath)
defer os.Remove("/data/files/" + contentHash+".zip")
return
}
func webToken() (*http.Client, string, error) {
jar, err := cookiejar.New(nil)
if err != nil {
return &http.Client{}, "", err
}
client := &http.Client{
CheckRedirect: func(req *http.Request, via []*http.Request) error {
return http.ErrUseLastResponse
},
Jar: jar,
}
payload := strings.NewReader("name=offcn&password=123123")
req, err := http.NewRequest("POST", WEBURL+"/web/login", payload)
if err != nil {
return &http.Client{}, "", err
}
req.Header.Add("content-type", "multipart/form-data")
req.Header.Add("Content-Type", "application/x-www-form-urlencoded")
res, err := client.Do(req)
if err != nil {
return &http.Client{}, "", err
}
bodys, err := ioutil.ReadAll(res.Body)
if err != nil {
return &http.Client{}, "", err
}
defer res.Body.Close()
response := string(bodys)
map2 := make(map[string]interface{})
err = json.Unmarshal([]byte(response), &map2)
if err != nil {
return &http.Client{}, "", err
}
if int(map2["code"].(float64)) == 200 {
//登录成功获取token
t_res, err := client.Get(WEBURL + "/web/admin")
if err != nil {
return &http.Client{}, "", err
}
defer t_res.Body.Close()
body, err := ioutil.ReadAll(t_res.Body)
if err != nil {
return &http.Client{}, "", err
}
re := regexp.MustCompile(`<meta name="csrf-token" content="([^"]+)">`)
token := re.FindAllStringSubmatch(string(body), -1)[0][1]
return client, token, nil
} else {
return &http.Client{}, "", errors.New("登录失败")
}
}
func createFileDataBase(room_file map[string]interface{}) error {
vv := Qurl.Values{}
for k, v := range room_file {
vv.Add(k, fmt.Sprintf("%v", v))
}
vv.Add("_token", token)
body := vv.Encode()
payload := strings.NewReader(body)
req, err := http.NewRequest("POST",WEBURL + "/web/room_files_add", payload)
if err != nil {
fmt.Println("123")
return err
}
req.Header.Add("content-type", "multipart/form-data")
req.Header.Add("Content-Type", "application/x-www-form-urlencoded")
res, err := client.Do(req)
if err != nil {
return err
}
defer res.Body.Close()
post_body, err := ioutil.ReadAll(res.Body)
if err != nil {
fmt.Println("456")
return err
}
map2 := make(map[string]interface{})
err = json.Unmarshal(post_body, &map2)
if err != nil {
fmt.Println("678")
return err
}
if int(map2["code"].(float64)) != 200 {
return errors.New("上传失败")
}
return nil
}
func pdfThumbnail(objectPath string, file *zip.File, bucket *oss.Bucket) error {
fc, err := file.Open()
if err != nil {
return err
}
defer fc.Close()
objectPathName := objectPath + "images/"
var fileSuffix string
fileSuffix = path.Ext(file.Name) //获取文件后缀
var filenameOnly string
filenameOnly = strings.TrimRight(file.Name, fileSuffix)
filenameOnly = strings.Replace(filenameOnly, "p", "", -1)
fileName := fmt.Sprintf("%05s", filenameOnly) + fileSuffix
return bucket.PutObject(objectPathName+fileName, fc)
}
func uploadPacked(bucket *oss.Bucket, filename, contentHash,
objectPath string, word float64) error {
type packed struct {
FileName string `json:"fileName"`
Hash string `json:"hash"`
ImagesName []string `json:"imagesName"`
OssImagesPath string `json:"ossImagesPath"`
}
p := packed{
FileName: filename,
Hash: contentHash,
OssImagesPath: objectPath + "images/",
}
for i := 1; i <= int(word); i++ {
p.ImagesName = append(p.ImagesName, fmt.Sprintf("%05d", i)+".png")
}
data, err := json.Marshal(p)
if err != nil {
return err
}
err = bucket.PutObject(objectPath+"packed.json",
strings.NewReader(string(data)))
if err != nil {
return err
}
return nil
}
func getWords(maps map[string]interface{}) float64 {
if word, ok := maps["SlideCount"]; ok {
return word.(float64)
}
if word, ok := maps["PageCount"]; ok {
return word.(float64)
}
if word, ok := maps["SheetCount"]; ok {
return word.(float64)
}
return float64(0)
}
func getFileInfo(ossFile string) (map[string]interface{}, error) {
url := docUrl + "?info=0&ssl=1&furl=" + ossFile
resp, err := http.Get(url)
if err != nil {
return nil, err
}
defer resp.Body.Close()
b, err := ioutil.ReadAll(resp.Body)
if err != nil {
return nil, err
}
var maps map[string]interface{}
err = json.Unmarshal(b, &maps)
if err != nil {
return nil, err
}
return maps, nil
}
func newOssClient() (*oss.Bucket, error) {
client, err := oss.New("oss-cn-beijing.aliyuncs.com",
"LTAI1fMvVUPBXl2E", "cTAMLufmPFznfE0peur8oMmy2c5kvk")
if err != nil {
return nil, err
}
bucket, err := client.Bucket("xiaoyu-live")
if err != nil {
return nil, err
}
return bucket, nil
}
func fileContentHash(file io.Reader) (string, []byte) {
b, err := ioutil.ReadAll(file)
if err != nil {
fmt.Println(err)
}
hash := md5.New()
io.WriteString(hash, string(b))
result := hash.Sum(nil)
return fmt.Sprintf("%s", hex.EncodeToString(result)), b
}
func downloadFile(url string, fb func(length, downLen int64)) error {
var (
fsize int64
buf = make([]byte, 32*1024)
written int64
)
//创建一个http client
client := new(http.Client)
//get方法获取资源
resp, err := client.Get(url)
fmt.Println(url)
if err != nil {
return err
}
//读取服务器返回的文件大小
fsize, err = strconv.ParseInt(resp.Header.Get("Content-Length"), 10, 32)
if err != nil {
fmt.Println(err)
}
//创建文件
var filenameWithSuffix string
filenameWithSuffix = path.Base(url) //获取文件名带后缀
var fileSuffix string
fileSuffix = path.Ext(filenameWithSuffix) //获取文件后缀
var filenameOnly string
filenameOnly = strings.Replace(filenameWithSuffix, fileSuffix, ".zip", -1) //获取文件名
file, err := os.Create("/data/files/" + filenameOnly)
if err != nil {
return err
}
defer file.Close()
if resp.Body == nil {
return errors.New("body is null")
}
defer resp.Body.Close()
//下面是 io.copyBuffer() 的简化版本
for {
//读取bytes
nr, er := resp.Body.Read(buf)
if nr > 0 {
//写入bytes
nw, ew := file.Write(buf[0:nr])
//数据长度大于0
if nw > 0 {
written += int64(nw)
}
//写入出错
if ew != nil {
err = ew
break
}
//读取是数据长度不等于写入的数据长度
if nr != nw {
err = io.ErrShortWrite
break
}
}
if er != nil {
if er != io.EOF {
err = er
}
break
}
//没有错误了快使用 callback
fb(fsize, written)
}
return err
s := g.Server()
s.Run()
}
package middleware
import (
"bytes"
"io/ioutil"
"ppt_server/library/response"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/net/ghttp"
)
// Recover异常恢复
func Recover(r *ghttp.Request) {
r.Middleware.Next()
if err := r.GetError(); err != nil {
r.Response.ClearBuffer()
response.Fail(r, err)
}
}
// CorS跨域
func Cors(r *ghttp.Request) {
r.Response.CORSDefault()
r.Middleware.Next()
}
// BodyDump打印请求体
func BodyDump(r *ghttp.Request) {
reqBody, _ := ioutil.ReadAll(r.Request.Body)
r.Request.Body = ioutil.NopCloser(bytes.NewBuffer(reqBody))
if len(reqBody) > 0 {
g.Log().Async().Infof("path: %s, method: %s params: %s",
r.Request.URL.RequestURI(), r.Method, string(reqBody))
}
r.Middleware.Next()
}
package models
import (
"fmt"
"log"
"ppt_server/utils"
"sync"
"github.com/astaxie/beego/orm"
_ "github.com/go-sql-driver/mysql"
)
var (
user string = utils.ConfigObject.DBuser
pass string = utils.ConfigObject.DBpass
host string = utils.ConfigObject.DBHost
port string = utils.ConfigObject.DBPort
dbname string = utils.ConfigObject.DBname
charset string = utils.ConfigObject.DBcharset
driver string = utils.ConfigObject.Driver
maxFreeConn int = utils.ConfigObject.MaxFreeLink
maxConn int = utils.ConfigObject.MaxLink
prefix string = utils.ConfigObject.DBprefix
)
type XyuRoom struct {
Id int `json:"id"`
RoomNum string `json:"room_num"`
StartTime string `json:"start_time"`
EndTime string `json:"end_time"`
Status int `json:"status"`
TeacherPassword string `json:"teacher_password"`
AssistantPassword string `json:"assistant_password"`
StudentPassword string `json:"student_password"`
HostPassword string `json:"host_password"`
SupervisePassword string `json:"supervise_password"`
IsRecording int
RoomType int `json:"room_type"`
ActualPush int
}
type XyuSmallRoom struct {
Id int
RoomId int
MaxPush int
RoomMode int
AllowMic int
}
type XyuSmallRoomWindow struct {
Id int
RoomNum string `json:"room_num"`
WId int `json:"wndindex"`
EId string `json:"e_id"`
PId string `json:"pid"`
Role string `json:"role"`
UserId string `json:"user_id"`
SetType int `json:"set_type"`
CreateTime string `json:"create_time"`
Status int
}
type XyuRoomUsers struct {
Id int `json:"id"`
Role string `json:"role"`
RoomNum string `json:"room_num"`
Token string `json:"token"`
}
type XyuSmallRoomPeople struct {
Id int
RoomNum string `pk;json:"room_num";`
Teacher int
Assistant int
Student int
Host int
Supervise int
}
type XyuSmallRoomRecord struct {
Id int
RoomNum string
Sessid string
Peerid string
RecordName string
TimeStamp string
}
type XyuSmallTempFiles struct {
Id int
RoomNum string `form:"room_num"`
Name string `form:"name"`
Nickanem string `form:"nickname"`
Type int `form:"type"`
Url string `form:"url"`
Time string `form:"time"'`
Uuid string `form:"uuid"`
Status int
}
type XyuRoomFiles struct {
Id int
RoomId int
Name string
}
var once sync.Once
func init() {
once.Do(func() {
init_mysql()
})
}
func init_mysql() {
dbConfStr := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s?charset=%s",
user, pass, host, port, dbname, charset)
log.Println("dbconf => ", dbConfStr)
_ = orm.RegisterDriver(driver, orm.DRMySQL)
err := orm.RegisterDataBase("default", driver, dbConfStr, maxFreeConn, maxConn)
if err != nil {
log.Println("db connect error => ", err)
return
}
orm.RegisterModel(new(XyuRoom), new(XyuRoomUsers), new(XyuSmallRoom), new(XyuSmallRoomWindow),
new(XyuSmallRoomPeople), new(XyuSmallRoomRecord), new(XyuSmallTempFiles), new(XyuRoomFiles))
//orm.Debug = true
log.Println("MySQL connect success")
}
package file
import (
"encoding/json"
"os"
"ppt_server/app/model"
"ppt_server/library/http"
"github.com/gogf/gf/errors/gerror"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/text/gregex"
)
type notify struct {
name string
password string
url string
client *http.SessionHttpClient
}
func newNotify() *notify {
return &notify{
url: g.Cfg().GetString("notify.url"),
name: os.Getenv("live_name"),
password: os.Getenv("live_pwd"),
client: http.NewSessionHttpClient(),
}
}
//回调验权
func (n *notify) verify(url string, data g.Map) error {
res, err := n.client.Post(url, data)
if err != nil {
return err
}
var notifyResponse model.NotifyResponse
if err = json.Unmarshal(res, &notifyResponse); err != nil {
return err
}
if notifyResponse.Code != 200 {
return gerror.New(notifyResponse.Msg)
}
return nil
}
// 登录
func (n *notify) auth(data g.Map) error {
if err := n.verify(n.url+"/web/login", g.Map{
"name": n.name,
"password": n.password,
}); err != nil {
return err
}
// 获取Token
bufferBytes, err := n.client.Get(n.url + "/web/admin")
if err != nil {
return err
}
buf, _ := gregex.Match(`<meta name="csrf-token" content="([^"]+)">`, bufferBytes)
data["_token"] = string(buf[1])
return nil
}
// 发送通知
func (n *notify) notice(path string, data g.Map) error {
if err := n.auth(data); err != nil {
return err
}
g.Log().Async().Infof("Notify Success!")
return n.verify(n.url+path, data)
}
package file
import (
"fmt"
"mime"
"net/http"
"path"
"strings"
"github.com/gogf/gf/encoding/gurl"
"github.com/gogf/gf/errors/gerror"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/text/gstr"
)
type parser struct {
path string
slicePath []string
url string //课件地址
ext string //课件后缀
name string //课件名称
}
func parseURL(ossFileLink string) (*parser, error) {
parseURLPath, err := gurl.ParseURL(ossFileLink, 32)
if err != nil {
return nil, err
}
slicePath := gstr.SplitAndTrim(parseURLPath["path"], "/", "/")
if len(slicePath) < 4 {
return nil, gerror.NewCode(http.StatusBadRequest, "上传URL格式不正确")
}
f := &parser{
ext: path.Ext(ossFileLink),
url: ossFileLink,
path: parseURLPath["path"],
slicePath: slicePath,
name: path.Base(ossFileLink),
}
return f, nil
}
//解析课件的URL
func (f *parser) splitFileInfoLink() string {
return fmt.Sprintf("%s?info=0&ssl=1&furl=%s/%s",
parserFileLink, g.Cfg().GetString("oss.url"), f.dataPath())
}
// 临时存储解析包地址
func (f *parser) splitTempZipLink() string {
return fmt.Sprintf("%s%s.zip", g.Cfg().GetString("temp.path"), f.slicePath[2])
}
// 获取文件名称
func (f *parser) filename() string {
return f.name
}
// 上传课件路径
func (f *parser) splitUploadPath() string {
return strings.Join(f.slicePath[0:len(f.slicePath)-1], "/") + "/"
}
// 文件名称hash
func (f *parser) nameHash() string {
return f.slicePath[3]
}
// 文件内容hash
func (f *parser) contentHash() string {
return f.slicePath[2]
}
// 数据库存储path
func (f *parser) dataPath() string {
return f.splitUploadPath() + gurl.Encode(f.slicePath[len(f.slicePath)-1:][0])
}
// 解析doctype
func (f *parser) docType() string {
switch f.ext {
case ".ppt", ".pptx":
return "4"
case ".doc", ".docx":
return "2"
case ".xls", ".xlsx":
return "3"
case ".pdf":
return "1"
default:
return "1"
}
}
// 获取文件mine
func (f *parser) mineType() string {
_ = mime.AddExtensionType(".pptx", "application/vnd.openxmlformats-officedocument.presentationml.presentation")
_ = mime.AddExtensionType(".ppt", "application/vnd.ms-powerpoint")
return mime.TypeByExtension(f.ext)
}
package file
import (
"archive/zip"
"bytes"
"encoding/json"
"fmt"
"image"
"image/jpeg"
"image/png"
"io/ioutil"
"os"
"path"
"regexp"
"strings"
"ppt_server/app/model"
"ppt_server/library/http"
"ppt_server/library/oss"
"github.com/gogf/gf/errors/gerror"
"github.com/gogf/gf/frame/g"
"github.com/gogf/gf/os/gtime"
"github.com/xxjwxc/gowp/workpool"
)
// 解析URL返回基本信息
type ObtainFile struct {
R *model.FileUploadRequest // 客户端请求参数
ok chan bool // 上传课件响应成功
err chan error // 上传课件失败Error
fileSize int64 // 课件大小
pageCount int // 课件图片数量
parser *parser // 课件对象
n *notify // 事件通知
packed *model.Packed // packed.json
}
const (
parserFileLink = "http://doc.offcncloud.com/"
ossIntranetLink = "xiaoyu-live.oss-cn-beijing-internal.aliyuncs.com"
uploadFileLinkHost = "desktop.offcncloud.com"
)
var reFileNameCompile, _ = regexp.Compile(`p([\d]+)[.].*`)
func Upload(r *model.FileUploadRequest, errChan chan error,
ok chan bool) (file *ObtainFile, err error) {
f, err := parseURL(r.Url)
if err != nil {
return nil, err
}
file = &ObtainFile{
ok: ok,
err: errChan,
parser: f,
R: r,
packed: &model.Packed{
FileName: f.filename(),
Hash: f.contentHash(),
OssImagesPath: f.splitUploadPath() + "images/",
},
n: newNotify(),
}
return file, nil
}
//从web365获取上传文件信息
func (f *ObtainFile) fileInfo() error {
fileBytes, err := http.Get(f.parser.splitFileInfoLink())
if err != nil {
return err
}
var fileInfo model.UploadFileInfo
if err = json.Unmarshal(fileBytes, &fileInfo); err != nil {
return err
}
if fileInfo.FileSize != 0 {
f.fileSize = fileInfo.FileSize
}
switch {
case fileInfo.SlideCount != 0:
f.pageCount = fileInfo.SlideCount
case fileInfo.PageCount != 0:
f.pageCount = fileInfo.PageCount
case fileInfo.SheetCount != 0:
f.pageCount = fileInfo.SheetCount
}
return nil
}
// 获取图片宽和高 并将图片上传到OSS
func (f *ObtainFile) taskJob(file *zip.File) ([]interface{}, error) {
fd, err := file.Open()
if err != nil {
return nil, err
}
defer fd.Close()
pictureBytes, _ := ioutil.ReadAll(fd)
// 获取图片信息reader
imageReader := ioutil.NopCloser(bytes.NewBuffer(pictureBytes))
// 上传图片reader
fileReader := ioutil.NopCloser(bytes.NewBuffer(pictureBytes))
var img image.Image
fileSuffix := path.Ext(file.Name) //获取文件后缀
switch fileSuffix {
case ".png":
img, err = png.Decode(imageReader)
case ".jpeg":
img, err = jpeg.Decode(imageReader)
default:
return nil, gerror.New("image ext is not found")
}
if err != nil {
return nil, err
}
replaceName := fmt.Sprintf("%05s", reFileNameCompile.ReplaceAllString(file.Name, "$1")) + fileSuffix
info := img.Bounds()
imageInfo := []interface{}{replaceName, info.Max.X, info.Max.Y}
return imageInfo, oss.Upload(f.parser.splitUploadPath()+"images/"+replaceName, fileReader)
}
func (f *ObtainFile) task(file *zip.File) error {
var (
err error
imageInfo []interface{}
)
for i := 0; i < 3; i++ {
if imageInfo, err = f.taskJob(file); err == nil {
f.packed.ImageInfos = append(f.packed.ImageInfos, imageInfo)
break
}
}
return err
}
func (f *ObtainFile) uploadPicture() error {
reader, err := zip.OpenReader(f.parser.splitTempZipLink())
if err != nil {
return err
}
defer reader.Close()
pool := workpool.New(100)
for _, file := range reader.File {
pool.DoWait(func() error {
return f.task(file)
})
}
return pool.Wait()
}
// 上传packed.json
func (f *ObtainFile) uploadPacked() error {
for i := 1; i <= f.pageCount; i++ {
f.packed.ImagesName = append(f.packed.ImagesName, fmt.Sprintf("%05d", i) +".png")
}
packedBytes, err := json.Marshal(f.packed)
if err != nil {
return err
}
return oss.Upload(f.parser.splitUploadPath()+"packed.json", bytes.NewReader(packedBytes))
}
// 拼接下载zip包地址
func (f *ObtainFile) splitDownloadLink() string {
return fmt.Sprintf("%s?info=1&words=%v&ssl=1&furl=%s/%s",
parserFileLink, f.pageCount, g.Cfg().GetString("oss.url"),
f.parser.dataPath())
}
func (f *ObtainFile) deferWorker(err error) {
// 清理ZIP包
_ = os.Remove(f.parser.splitTempZipLink())
// 通知
if err != nil {
g.Log().Async().Error(err)
f.err <- err
return
}
f.ok <- true
}
// 进行解析上传操作
func (f *ObtainFile) Worker(err error) {
defer func() {
f.deferWorker(err)
}()
if err != nil {
return
}
// 解析课件获取课件信息
if err = f.fileInfo(); err != nil {
return
}
g.Log().Async().Infof("[1] file: %s file info complete", f.parser.filename())
// 下载ZIP包
if err = http.Download(f.splitDownloadLink(), f.parser.splitTempZipLink()); err != nil {
return
}
g.Log().Async().Infof("[2] file: %s zip donwload complete", f.parser.filename())
// 解析ZIP包并上传图片到OSS
if err = f.uploadPicture(); err != nil {
return
}
g.Log().Async().Infof("[3] file: %s picture upload oss complete", f.parser.filename())
// 上传packed.json到oss
if err = f.uploadPacked(); err != nil {
return
}
g.Log().Async().Infof("[4] file: %s upload complete!", f.parser.filename())
}
// 上传失败通知
func (f *ObtainFile) Fail() {
if err := f.n.notice("/web/room_files_error", g.Map{
"code": 400,
"uuid": f.R.Uuid,
"room_num": f.R.RoomNum,
"path": f.parser.dataPath(),
}); err != nil {
g.Log().Async().Error(err)
}
}
// 上传成功通知
func (f *ObtainFile) Success(roomID int) {
if err := f.n.notice("/web/room_files_add", g.Map{
"name": f.R.Name,
"file_name_hash": f.parser.nameHash(),
"hash": f.parser.contentHash(),
"path": f.parser.dataPath(),
"doc_type": f.parser.docType(),
"type": f.parser.mineType(),
"files_size": f.fileSize,
"page_count": f.pageCount,
"link": strings.Replace(f.parser.url, ossIntranetLink, uploadFileLinkHost, -1),
"private": "1",
"time": gtime.Datetime(),
"nickname": f.R.NickName,
"uuid": f.R.Uuid,
"room_id": roomID,
"is_courseware" : 1,
}); err != nil {
g.Log().Async().Error(err)
}
}
/**
* @Authore: lifeifei
* @Date: 2021/7/22 10:26 上午
*/
package api
import (
"ppt_server/app/api"
"ppt_server/interfaces"
"github.com/gogf/gf/net/ghttp"
)
type _file struct {
router *ghttp.RouterGroup
}
func NewFileRouter(router *ghttp.RouterGroup) interfaces.Router {
return &_file{router}
}
func (f *_file) Init() {
group := f.router.Group(`/file`)
{
// 阿里云健康检测
group.GET(`/upload`, api.File.Index)
// 课件解析
group.POST(`/upload`, api.File.Upload)
}
}
package router
import (
"ppt_server/middleware"
apiRouter "ppt_server/router/api"
"github.com/gogf/gf/frame/g"
)
func init() {
g.Server().Use(
middleware.Recover,
middleware.Cors,
)
api := g.Server().Group("").Middleware(middleware.BodyDump)
{
//课件解析
apiRouter.NewFileRouter(api).Init()
}
}
// @APIVersion 1.0.0
// @Title beego Test API
// @Description beego has a very cool tools to autogenerate documents for your API
// @Contact astaxie@gmail.com
// @TermsOfServiceUrl http://beego.me/
// @License Apache 2.0
// @LicenseUrl http://www.apache.org/licenses/LICENSE-2.0.html
package routers
import (
"encoding/json"
"fmt"
"ppt_server/controllers"
"github.com/astaxie/beego/context"
"github.com/astaxie/beego"
"ppt_server/upload"
)
func init() {
beego.Router("/file/upload", &controllers.UploadController{})
beego.Post("/file/callback", func(ctx *context.Context) {
var mapFiles map[string]interface{}
var err error
fmt.Println("body === ", string(ctx.Input.RequestBody))
if err = json.Unmarshal(ctx.Input.RequestBody, &mapFiles); err != nil {
ctx.WriteString("Error " + err.Error())
return
}
if mapFiles["success"].(string) == "false" {
_ = upload.UpdateFileError("1", mapFiles["uuid"].(string), mapFiles["roomNum"].(string), mapFiles["path"].(string))
ctx.WriteString("Upload Fail")
return
}
if err = upload.CreateFileDataBase(mapFiles); err != nil {
_ = upload.UpdateFileError("2", mapFiles["uuid"].(string), mapFiles["roomNum"].(string), mapFiles["path"].(string))
ctx.WriteString("Error " + err.Error())
return
}
ctx.WriteString("Upload Ok")
})
}
/**
* @Authore: lifeifei
* @Date: 2021/1/25 10:47 上午
*/
package upload
import (
"encoding/json"
"fmt"
beeLogger "github.com/beego/bee/logger"
"github.com/streadway/amqp"
)
type RabbitMQ struct {
connection *amqp.Connection
channel *amqp.Channel
}
func (r *RabbitMQ) mqConnect() error {
var err error
RabbitUrl := fmt.Sprintf("amqp://%s:%s@%s:%d/",
"video",
"1fqH4WFR19uckgRyHzgISw",
"test-rmq.offcncloud.com/",
5672)
if r.connection, err = amqp.DialConfig(RabbitUrl, amqp.Config{Vhost: "v.ofc.office"}); err != nil {
beeLogger.Log.Errorf("RabbitMQ Server Connect Fail: %s", err)
return err
}
c, err := r.connection.Channel()
if err != nil {
beeLogger.Log.Errorf("Channel connet fail: %s", err)
return err
}
r.channel = c
beeLogger.Log.Success("RabbitMQ Server is running...")
return nil
}
func (r *RabbitMQ) mqClose() {
if r.channel != nil {
err := r.channel.Close()
if err != nil {
beeLogger.Log.Errorf("RabbitMQ Server Close Err: %s", err)
}
}
if r.connection != nil {
err := r.connection.Close()
if err != nil {
beeLogger.Log.Errorf("RabbitMQ Server Channel Close Err: %s", err)
}
}
}
func (r *RabbitMQ) Send(req map[string]interface{}) error {
defer r.mqClose()
if err := r.mqConnect(); err != nil {
return err
}
bytes, err := json.Marshal(req)
if err != nil {
return err
}
return r.channel.Publish("X.ofc.ppt2image", "RK.ofc.ppt2image", false, false, amqp.Publishing{
ContentType: "text/plain",
Body: bytes,
})
}
func Send(r map[string]interface{}) error {
mq := &RabbitMQ{}
return mq.Send(r)
}
/**
* @Authore: lifeifei
* @Date: 2021/1/25 10:11 上午
*/
package upload
import (
"github.com/astaxie/beego/orm"
beeLogger "github.com/beego/bee/logger"
"mime"
Qurl "net/url"
"path"
"ppt_server/models"
"strings"
"time"
)
type PPT struct {
request *models.XyuSmallTempFiles
}
func (p *PPT) Transform() (err error) {
maps := make(map[string]interface{})
o := orm.NewOrm()
var room models.XyuRoom
err = o.QueryTable("xyu_room").Filter("room_num", p.request.RoomNum).One(&room)
if err != nil {
beeLogger.Log.Errorf("获取房间信息失败:%s", err)
return
}
maps["url"] = p.request.Url
maps["room_id"] = room.Id
maps["id"] = time.Now().Unix()
maps["is_courseware"] = "1"
maps["private"] = "1"
maps["nickname"] = p.request.Nickanem
maps["name"] = p.request.Name
maps["time"] = time.Now().Format("2006-01-02 15:04:0")
maps["uuid"] = p.request.Uuid
switch p.request.Type {
case 1:
maps["is_material"] = 1
case 2:
maps["is_courseware"] = 1
case 3:
maps["is_titlebook"] = 1
}
objectName := p.request.Url[strings.Index(p.request.Url, "com/")+4:]
url, _ := Qurl.QueryUnescape(p.request.Url)
filename := path.Base(url)
ext := path.Ext(filename)
slice_path := strings.Split(objectName, "/")
maps["file_name_hash"] = slice_path[3]
maps["hash"] = slice_path[2]
var docType string
if strings.Contains(ext, "ppt") || strings.Contains(ext, "pptx") {
docType = "4"
} else if strings.Contains(ext, "doc") || strings.Contains(ext, "docx") {
docType = "2"
} else if strings.Contains(ext, "xls") || strings.Contains(ext, "xlsx") {
docType = "3"
} else if strings.Contains(ext, "pdf") {
docType = "1"
}
maps["doc_type"] = docType
_ = mime.AddExtensionType(".pptx", "application/vnd.openxmlformats-officedocument.presentationml.presentation")
maps["type"] = mime.TypeByExtension(ext)
maps["path"] = objectName
link := strings.Replace(p.request.Url, "xiaoyu-live.oss-cn-beijing-internal.aliyuncs.com", "desktop.offcncloud.com", -1)
maps["link"] = link
if err = Send(maps); err != nil {
beeLogger.Log.Errorf("Send Error: %s", err)
_ = UpdateFileError("6", maps["uuid"].(string), maps["roomNum"].(string), objectName)
return
}
return nil
}
package utils
const (
ROOM_FIELD = "room_num"
CREATEROOM = "auth-createroom"
JOINROOM = "auth-push"
LEAVEROOM = "auth-unpush"
LEAVEPOD = "auth-podexit"
LEAVEEDGEID = "auth-edgeexit"
RECORDCREATE = "record-create"
TIME_FORMAT = "2006-01-02 15:04:05"
TABLE_XYU_ROOM_USERS = "xyu_room_users"
TABLE_XYU_ROOM = "xyu_room"
TABLE_XYU_SMAIL_ROOM = "xyu_small_room"
TABLE_XYU_SMAIL_ROOM_WINDOW = "xyu_small_room_window"
TABLE_XYU_SMALL_PEOPLE = "xyu_small_room_people"
TABLE_XYU_SMALL_RECORD = "xyu_small_room_record"
TEACHER = "teacher"
ASSISTANT = "assistant"
STUDENT = "student"
HOST = "host"
SUPERVISE = "supervise"
)
package utils
import (
"encoding/json"
"fmt"
"io/ioutil"
"os"
"time"
)
type RabbitMqConf struct {
Username string
Password string
Host string
Port int
ConfFilePath string
Driver string
DBHost string
DBPort string
DBpass string
DBuser string
DBname string
DBcharset string
DBprefix string
ReconnectionTime time.Duration
MaxFreeLink int
MaxLink int
}
var ConfigObject *RabbitMqConf
func (r *RabbitMqConf) Reload() {
if confFileExists, _ := PathExists(r.ConfFilePath); !confFileExists {
fmt.Println("Config File ", r.ConfFilePath, " is not exist!!")
return
}
data, err := ioutil.ReadFile(r.ConfFilePath)
if err != nil {
panic(err)
}
//将json数据解析到struct中
err = json.Unmarshal(data, r)
if err != nil {
panic(err)
}
}
//判断一个文件是否存在
func PathExists(path string) (bool, error) {
_, err := os.Stat(path)
if err == nil {
return true, nil
}
if os.IsNotExist(err) {
return false, nil
}
return false, err
}
func init() {
ConfigObject = &RabbitMqConf{
Host: os.Getenv("rb_host"),
Username: os.Getenv("rb_user"),
Password: os.Getenv("rb_pass"),
DBHost: os.Getenv("write_sql"),
DBuser: os.Getenv("write_user"),
DBpass: os.Getenv("write_pass"),
DBPort: "3306",
DBname: "xyu",
Driver: "mysql",
DBcharset: "utf8",
Port: 5672,
ConfFilePath: "conf/rmq.conf",
ReconnectionTime: 10 * time.Second,
}
ConfigObject.Reload()
// ConfigObject = &RabbitMqConf{
// DBHost: "rm-2ze364spvypz122fw8o.mysql.rds.aliyuncs.com",
// DBuser: "video",
// DBpass: "vlty&AxMwT$lmLv6bN8dkDuBYlh%N5pe",
// DBPort: "3306",
// DBname: "xyu",
// Driver: "mysql",
// DBcharset: "utf8",
// Username: "admin",
// Password: "admin",
// Host: "192.168.10.156",
// Port: 5672,
// ConfFilePath: "conf/rmq.conf",
// ReconnectionTime: 1 * time.Second,
// }
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment