✨ 重新初始化项目
This commit is contained in:
parent
10546eb629
commit
d6e256ef9e
@ -6,7 +6,6 @@ import (
|
||||
"Lee-WineList/core"
|
||||
"Lee-WineList/model/param"
|
||||
"Lee-WineList/oauth2"
|
||||
"Lee-WineList/repository"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
@ -30,7 +29,6 @@ func (l loginApi) Login(ctx *gin.Context) {
|
||||
core.R(ctx).FailWithMessage(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// 获取用户基础账号信息
|
||||
userId, err := oauth2.OAuthServer.UserAuthorizationHandler(ctx.Writer, ctx.Request)
|
||||
if err != nil {
|
||||
@ -40,10 +38,13 @@ func (l loginApi) Login(ctx *gin.Context) {
|
||||
}
|
||||
// 重新组装登录参数
|
||||
ctx.Request.Form = url.Values{
|
||||
"username": {userId},
|
||||
"password": {p.Password},
|
||||
"scope": {"ALL"},
|
||||
"grant_type": {"password"},
|
||||
"username": {userId},
|
||||
"password": {p.Password},
|
||||
"scope": {"ALL"},
|
||||
"grant_type": {"password"},
|
||||
"invite_code": {p.InviteCode},
|
||||
"nickName": {p.NickName},
|
||||
"avatarUrl": {p.AvatarUrl},
|
||||
}
|
||||
|
||||
// 参数解析成功,进行登录
|
||||
@ -52,11 +53,7 @@ func (l loginApi) Login(ctx *gin.Context) {
|
||||
core.R(ctx).FailWithMessage("系统错误,登录失败")
|
||||
return
|
||||
}
|
||||
// 登录成功才更新登录时间
|
||||
if ctx.Writer.Status() == http.StatusOK {
|
||||
// 登录成功,更新登录时间和IP
|
||||
go repository.Login().UpdateLastLoginInfo(userId, ctx.ClientIP(), p.UserIdentity)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Refresh 刷新登录Token
|
||||
@ -107,3 +104,13 @@ func (loginApi) Logout(ctx *gin.Context) {
|
||||
|
||||
r.Ok()
|
||||
}
|
||||
|
||||
func (l loginApi) GetWeChatToken(c *gin.Context) {
|
||||
wechaetToken, err := http.Get("https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=wx3d38ce1103a82225&secret=3c41ca428b4d0f43cfaef6f567a1cc06")
|
||||
if err != nil {
|
||||
log.Errorf("获取微信Token失败: %v", err)
|
||||
core.R(c).FailWithMessage(err.Error())
|
||||
return
|
||||
}
|
||||
core.R(c).OkWithData(wechaetToken)
|
||||
}
|
||||
|
@ -32,6 +32,7 @@ func (u userApi) GetUser(ctx *gin.Context) {
|
||||
// 转换为VO
|
||||
var v vo.UserVO
|
||||
v.ParseOrdinary(ue)
|
||||
|
||||
core.R(ctx).OkWithData(v)
|
||||
}
|
||||
|
||||
@ -56,11 +57,11 @@ func (u userApi) BindingWeChat(ctx *gin.Context) {
|
||||
core.R(ctx).FailWithMessage("系统错误,请稍后再试")
|
||||
return
|
||||
}
|
||||
log.Debugf("用户[%v]的UnionId为[%v],OpenId为[%v]", loginUser.Id, unionId, openId)
|
||||
if repository.User().CheckUnionIdIsExist(unionId, openId) {
|
||||
core.R(ctx).FailWithMessage("该微信已绑定其他账号")
|
||||
return
|
||||
}
|
||||
//log.Debugf("用户[%v]的UnionId为[%v],OpenId为[%v]", loginUser.Id, unionId, openId)
|
||||
//if repository.User().CheckUnionIdIsExist(unionId, openId) {
|
||||
// core.R(ctx).FailWithMessage("该微信已绑定其他账号")
|
||||
// return
|
||||
//}
|
||||
// 解析成功,修改用户信息
|
||||
loginUser.WechatUnionId = &unionId
|
||||
loginUser.WechatOpenId = &openId
|
||||
@ -100,5 +101,6 @@ func (u userApi) UpdateUser(ctx *gin.Context) {
|
||||
core.R(ctx).FailWithMessage("修改用户信息失败: " + err.Error())
|
||||
return
|
||||
}
|
||||
// 操作成功,更新头像和昵称
|
||||
core.R(ctx).Ok()
|
||||
}
|
||||
|
50
api/app/wine.go
Normal file
50
api/app/wine.go
Normal file
@ -0,0 +1,50 @@
|
||||
package app
|
||||
|
||||
import (
|
||||
"Lee-WineList/core"
|
||||
"Lee-WineList/model/param"
|
||||
"Lee-WineList/repository"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
type wineApi struct {
|
||||
}
|
||||
|
||||
func WineApi() *wineApi {
|
||||
return &wineApi{}
|
||||
}
|
||||
|
||||
// GetList 获取酒品列表
|
||||
func (w *wineApi) GetList(ctx *gin.Context) {
|
||||
var p param.GetWineList
|
||||
|
||||
if err := ctx.ShouldBind(&p); err != nil {
|
||||
core.R(ctx).FailWithMessage(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
wines, err := repository.Wine().GetWineList(p)
|
||||
if err != nil {
|
||||
core.R(ctx).FailWithMessage(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
core.R(ctx).OkWithData(wines)
|
||||
}
|
||||
|
||||
// Add 添加酒单
|
||||
func (w *wineApi) Add(ctx *gin.Context) {
|
||||
var p param.AddWine
|
||||
|
||||
if err := ctx.ShouldBind(&p); err != nil {
|
||||
core.R(ctx).FailWithMessage(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
if err := repository.Wine().Add(p); err != nil {
|
||||
core.R(ctx).FailWithMessage(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
core.R(ctx).OkWithMessage("添加成功")
|
||||
}
|
29
api/base.go
29
api/base.go
@ -2,39 +2,14 @@ package api
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/common/constant"
|
||||
"Lee-WineList/core"
|
||||
"Lee-WineList/model/entity"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"github.com/gin-gonic/gin"
|
||||
"net/http"
|
||||
"strconv"
|
||||
)
|
||||
|
||||
// GetAdminUser 获取登录的管理员信息
|
||||
func GetAdminUser(ctx *gin.Context, u *entity.AdminUser) {
|
||||
userId := ctx.Request.Header.Get("userId")
|
||||
if userId == "" {
|
||||
ctx.Abort()
|
||||
core.R(ctx).FailWithMessageAndCode("未授权操作", http.StatusUnauthorized)
|
||||
return
|
||||
}
|
||||
u.Id = userId
|
||||
// 查询用户信息
|
||||
err := client.MySQL.Where("id = ?", u.Id).First(&u).Error
|
||||
if err != nil {
|
||||
log.Errorf("获取用户信息失败:%s", err.Error())
|
||||
core.R(ctx).FailWithMessageAndCode("用户状态异常", http.StatusBadRequest)
|
||||
ctx.Abort()
|
||||
return
|
||||
}
|
||||
// 校验
|
||||
if u.Status != constant.UserStatusActive {
|
||||
core.R(ctx).FailWithMessageAndCode("用户已被禁用", http.StatusBadRequest)
|
||||
ctx.Abort()
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
// GetUser 获取登录的普通用户信息,dontResponse表示只获取用户信息,不论对错, dontCheck表示不检查微信绑定
|
||||
func GetUser(ctx *gin.Context, u *entity.User, dontResponse, dontCheck bool) {
|
||||
userId := ctx.Request.Header.Get("userId")
|
||||
@ -45,7 +20,7 @@ func GetUser(ctx *gin.Context, u *entity.User, dontResponse, dontCheck bool) {
|
||||
}
|
||||
return
|
||||
}
|
||||
u.Id = userId
|
||||
u.Id, _ = strconv.Atoi(userId)
|
||||
|
||||
// 查询
|
||||
err := client.MySQL.Take(&u).Error
|
||||
|
@ -2,8 +2,10 @@ package client
|
||||
|
||||
import (
|
||||
"Lee-WineList/config"
|
||||
"git.echol.cn/loser/logger"
|
||||
|
||||
"git.echol.cn/loser/logger/log"
|
||||
|
||||
"git.echol.cn/loser/logger"
|
||||
"gorm.io/driver/mysql"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
26
client/redis.go
Normal file
26
client/redis.go
Normal file
@ -0,0 +1,26 @@
|
||||
package client
|
||||
|
||||
import (
|
||||
"Lee-WineList/config"
|
||||
"context"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"github.com/go-redis/redis/v8"
|
||||
)
|
||||
|
||||
var Redis *redis.Client
|
||||
|
||||
func InitRedisClient() {
|
||||
conf := config.Scd.Redis
|
||||
// 初始化连接
|
||||
conn := redis.NewClient(&redis.Options{
|
||||
Addr: conf.GetDSN(),
|
||||
Password: conf.Password,
|
||||
DB: conf.Db,
|
||||
})
|
||||
if err := conn.Ping(context.Background()).Err(); err != nil {
|
||||
log.Panicf("Redis连接初始化失败: %v", err)
|
||||
} else {
|
||||
log.Debug("Redis连接初始化成功")
|
||||
}
|
||||
Redis = conn
|
||||
}
|
@ -1,11 +1,8 @@
|
||||
package constant
|
||||
|
||||
const (
|
||||
RdsCaptchaPrefix = "captcha:img:" // 验证码缓存前缀
|
||||
RdsSmsCaptchaPrefix = "captcha:sms:" // 短信验证码缓存前缀
|
||||
OAuth2RedisKey = "oauth:token:" // Token缓存前缀
|
||||
OAuth2UserCacheKey = "oauth:user:" // 用户缓存前缀
|
||||
ApiAntiShakeKey = "api:antishake:" // 防抖锁
|
||||
ReportGenTaskKey = "report:gen:task" // 任务生成计划待办队列
|
||||
WeChatSessionKey = "wechat:session:" // 小程序用户SessionKey前缀
|
||||
OAuth2RedisKey = "oauth:token:" // Token缓存前缀
|
||||
OAuth2UserCacheKey = "oauth:user:" // 用户缓存前缀
|
||||
ApiAntiShakeKey = "api:antishake:" // 防抖锁
|
||||
WeChatSessionKey = "wechat:session:" // 小程序用户SessionKey前缀
|
||||
)
|
||||
|
88
common/constant/user.go
Normal file
88
common/constant/user.go
Normal file
@ -0,0 +1,88 @@
|
||||
package constant
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
)
|
||||
|
||||
// UserStatus 用户状态
|
||||
type UserStatus string
|
||||
|
||||
const (
|
||||
UserStatusActive UserStatus = "NORMAL" // 用户状态正常
|
||||
UserStatusDisabled UserStatus = "DISABLE" // 已禁用用户
|
||||
)
|
||||
|
||||
// 状态对应的描述
|
||||
var userStatusMap = map[UserStatus]string{
|
||||
UserStatusActive: "正常",
|
||||
UserStatusDisabled: "已禁用",
|
||||
}
|
||||
|
||||
// 处理为看得懂的状态
|
||||
func (s UserStatus) String() string {
|
||||
if str, ok := userStatusMap[s]; ok {
|
||||
return str
|
||||
}
|
||||
return string(s)
|
||||
}
|
||||
|
||||
// =====================================================================================================================
|
||||
|
||||
// UserSex 性别
|
||||
type UserSex int
|
||||
|
||||
const (
|
||||
UserSexNone UserSex = iota // 不知道是啥
|
||||
UserSexMale // 男
|
||||
UserSexFemale // 女
|
||||
UserSexOther // 其他性别
|
||||
)
|
||||
|
||||
// 状态对应的描述
|
||||
var userSexMap = map[UserSex]string{
|
||||
UserSexNone: "无性别",
|
||||
UserSexMale: "男",
|
||||
UserSexFemale: "女",
|
||||
UserSexOther: "其他",
|
||||
}
|
||||
|
||||
// FromString 中文取性别
|
||||
func (s UserSex) FromString(sex string) UserSex {
|
||||
result := UserSexNone
|
||||
for key, value := range userSexMap {
|
||||
if sex == value {
|
||||
result = key
|
||||
break
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
// 处理为看得懂的状态
|
||||
func (s UserSex) String() string {
|
||||
if str, ok := userSexMap[s]; ok {
|
||||
return str
|
||||
}
|
||||
//return strconv.Itoa(int(s))
|
||||
return fmt.Sprintf("UserSex(%d)", int(s))
|
||||
}
|
||||
|
||||
// MarshalJSON JSON序列化的时候转换为中文
|
||||
func (s UserSex) MarshalJSON() ([]byte, error) {
|
||||
return []byte(`"` + s.String() + `"`), nil
|
||||
}
|
||||
|
||||
// =====================================================================================================================
|
||||
|
||||
// UserIdentity 用户身份
|
||||
type UserIdentity string
|
||||
|
||||
const (
|
||||
UserIdentityAdmin UserIdentity = "admin" // 管理员
|
||||
UserIdentityUser UserIdentity = "user" // 普通用户
|
||||
)
|
||||
|
||||
// String implements the Stringer interface.
|
||||
func (t UserIdentity) String() string {
|
||||
return string(t)
|
||||
}
|
8
common/default_keys.go
Normal file
8
common/default_keys.go
Normal file
@ -0,0 +1,8 @@
|
||||
package common
|
||||
|
||||
const (
|
||||
SmsSendKey = "sms:send:" // 短信发送缓存前缀
|
||||
Oauth2RedisKey = "oauth:token:" // Token缓存前缀
|
||||
WeChatSessionKey = "wechat:session:" // 小程序用户SessionKey前缀
|
||||
ImMessageKey = "im:message:" // IM消息缓存前缀
|
||||
)
|
16
common/login_type.go
Normal file
16
common/login_type.go
Normal file
@ -0,0 +1,16 @@
|
||||
package common
|
||||
|
||||
// LoginType 自定义登录类型
|
||||
type LoginType string
|
||||
|
||||
// 登录类型
|
||||
const (
|
||||
Github LoginType = "github" // Github登录
|
||||
WeChatMiniApp LoginType = "wechat_mini_app" // 微信小程序登录
|
||||
Password LoginType = "password" // 密码登录
|
||||
)
|
||||
|
||||
// String 转换为字符串
|
||||
func (t LoginType) String() string {
|
||||
return string(t)
|
||||
}
|
@ -11,3 +11,9 @@ type BaseDbModel struct {
|
||||
UpdatedAt DateTime `json:"updatedAt"`
|
||||
DeletedAt gorm.DeletedAt `json:"-" gorm:"index:deleted"`
|
||||
}
|
||||
|
||||
type Model struct {
|
||||
CreatedAt DateTime `json:"createdAt"`
|
||||
UpdatedAt DateTime `json:"updatedAt"`
|
||||
DeletedAt gorm.DeletedAt `json:"-" gorm:"index:deleted"`
|
||||
}
|
||||
|
41
config.yaml
41
config.yaml
@ -5,31 +5,26 @@ api:
|
||||
prefix: /api/v1
|
||||
|
||||
mysql:
|
||||
host: 127.0.0.1
|
||||
port: 49154
|
||||
host: 1.117.68.37
|
||||
port: 3307
|
||||
user: root
|
||||
password: mysqlpw
|
||||
db: mini_app
|
||||
password: loser765911.
|
||||
db: lee_wine
|
||||
|
||||
#redis:
|
||||
# host: 127.0.0.1
|
||||
# port: 49153
|
||||
# password: redispw
|
||||
# db: 2
|
||||
|
||||
jwt:
|
||||
AccessSecret: "leex"
|
||||
AccessExpire: 604800
|
||||
RefreshAfter: 86400
|
||||
|
||||
tencent:
|
||||
mini-app:
|
||||
app-id: xxxx
|
||||
app-secret: xxxx
|
||||
redis:
|
||||
host: 101.35.50.11
|
||||
port: 6379
|
||||
password: loser7659
|
||||
db: 10
|
||||
|
||||
aliyun:
|
||||
oss:
|
||||
endpoint: oss-cn-shanghai.aliyuncs.com
|
||||
bucket: xxxx
|
||||
access-key: xxxx
|
||||
access-key-secret: xxxx
|
||||
Endpoint: oss-cn-shanghai.aliyuncs.com
|
||||
Bucket: workflow-zym
|
||||
access-key: LTAI5tRFgH2mtJbtX8tuyeYY
|
||||
access-key-secret: CW37ibDs9i8uvM08gKhkj12dEq2mOU
|
||||
|
||||
tencent:
|
||||
mini-app:
|
||||
app-id: wxcac07f5e3d0dedf0
|
||||
app-secret: 431d9dad0c96c2b7020da7d23c761196
|
@ -2,9 +2,16 @@ package config
|
||||
|
||||
// 阿里云配置
|
||||
type aliyunConfig struct {
|
||||
Sms aliSmsConfig `mapstructure:"sms" yaml:"sms"` // 短信配置
|
||||
Oss aliOssConfig `mapstructure:"oss" yaml:"oss"` // oss配置
|
||||
}
|
||||
|
||||
// SmsConfig 阿里云短信配置
|
||||
type aliSmsConfig struct {
|
||||
AccessKeyId string `mapstructure:"access-key" yaml:"access-key"`
|
||||
AccessKeySecret string `mapstructure:"access-key-secret" yaml:"access-key-secret"`
|
||||
}
|
||||
|
||||
// OSSConfig 阿里云OSS配置
|
||||
type aliOssConfig struct {
|
||||
Endpoint string `mapstructure:"endpoint" yaml:"endpoint"`
|
||||
|
@ -1,14 +1,13 @@
|
||||
package config
|
||||
|
||||
var Scd systemConfigData
|
||||
var Nacos nacosConfig
|
||||
|
||||
// 配置信息
|
||||
type systemConfigData struct {
|
||||
Admin appInfo `mapstructure:"admin" yaml:"admin"` // 系统配置-Admin
|
||||
Api appInfo `mapstructure:"api" yaml:"api"` // 系统配置-Api
|
||||
MySQL mysqlConfig `mapstructure:"mysql" yaml:"mysql"` // MySQL配置
|
||||
Redis redisConfig `mapstructure:"redis" yaml:"redis"` // Redis配置
|
||||
Aliyun aliyunConfig `mapstructure:"aliyun" yaml:"aliyun"` // 阿里云配置
|
||||
Tencent tencentConfig `mapstructure:"tencent" yaml:"tencent"` // 腾讯相关配置
|
||||
JWT JWT `mapstructure:"jwt" yaml:"jwt"`
|
||||
}
|
||||
|
15
config/redis.go
Normal file
15
config/redis.go
Normal file
@ -0,0 +1,15 @@
|
||||
package config
|
||||
|
||||
import "fmt"
|
||||
|
||||
// Redis配置
|
||||
type redisConfig struct {
|
||||
Host string `mapstructure:"host" yaml:"host"` // 主机
|
||||
Port int `mapstructure:"port" yaml:"port"` // 端口
|
||||
Password string `mapstructure:"password" yaml:"password"` // 密码
|
||||
Db int `mapstructure:"db" yaml:"db"` // 数据库名称
|
||||
}
|
||||
|
||||
func (r redisConfig) GetDSN() string {
|
||||
return fmt.Sprintf("%s:%v", r.Host, r.Port)
|
||||
}
|
@ -3,6 +3,8 @@ package config
|
||||
// 腾讯相关配置
|
||||
type tencentConfig struct {
|
||||
MiniApp wechatMiniAppConfig `mapstructure:"mini-app" yaml:"mini-app"`
|
||||
Payment wechatPayConfig `mapstructure:"payment" yaml:"payment"`
|
||||
CApi capiConfig `mapstructure:"capi" yaml:"capi"`
|
||||
}
|
||||
|
||||
// 微信小程序配置
|
||||
@ -10,3 +12,18 @@ type wechatMiniAppConfig struct {
|
||||
AppId string `mapstructure:"app-id" yaml:"app-id"`
|
||||
AppSecret string `mapstructure:"app-secret" yaml:"app-secret"`
|
||||
}
|
||||
|
||||
// 微信支付配置
|
||||
type wechatPayConfig struct {
|
||||
MchId string `mapstructure:"mchId" yaml:"mchId"` // 商户号
|
||||
SerialNo string `mapstructure:"serialNo" yaml:"serialNo"` // 商户API证书的证书序列号
|
||||
ApiV3Key string `mapstructure:"apiV3Key" yaml:"apiV3Key"` // 支付key
|
||||
PrivateKey string `mapstructure:"privateKey" yaml:"privateKey"` // 支付私钥绝对路径
|
||||
}
|
||||
|
||||
// api密钥配置
|
||||
type capiConfig struct {
|
||||
AppId string `mapstructure:"app-id" yaml:"app-id"` // APP ID
|
||||
SecretId string `mapstructure:"secret-id" yaml:"secret-id"` // Secret ID
|
||||
SecretKey string `mapstructure:"secret-key" yaml:"secret-key"` // Secret Key
|
||||
}
|
||||
|
@ -2,8 +2,9 @@ package core
|
||||
|
||||
import (
|
||||
"Lee-WineList/utils"
|
||||
"github.com/gin-gonic/gin"
|
||||
"net/http"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
// 返回数据包装
|
||||
|
42
go.mod
42
go.mod
@ -4,30 +4,43 @@ go 1.18
|
||||
|
||||
require (
|
||||
git.echol.cn/loser/logger v1.0.15
|
||||
github.com/aliyun/alibaba-cloud-sdk-go v1.62.288
|
||||
github.com/aliyun/alibaba-cloud-sdk-go v1.62.296
|
||||
github.com/aliyun/aliyun-oss-go-sdk v2.2.7+incompatible
|
||||
github.com/duke-git/lancet/v2 v2.1.19
|
||||
github.com/fsnotify/fsnotify v1.6.0
|
||||
github.com/gin-gonic/gin v1.9.0
|
||||
github.com/go-oauth2/oauth2/v4 v4.5.2
|
||||
github.com/go-oauth2/redis/v4 v4.1.1
|
||||
github.com/go-pay/gopay v1.5.92
|
||||
github.com/go-redis/redis/v8 v8.11.5
|
||||
github.com/golang-jwt/jwt v3.2.1+incompatible
|
||||
github.com/google/uuid v1.3.0
|
||||
github.com/medivhzhan/weapp/v3 v3.6.19
|
||||
github.com/robfig/cron/v3 v3.0.1
|
||||
github.com/spf13/viper v1.15.0
|
||||
github.com/stretchr/testify v1.8.1
|
||||
golang.org/x/crypto v0.8.0
|
||||
golang.org/x/sync v0.1.0
|
||||
gorm.io/driver/mysql v1.5.0
|
||||
gorm.io/driver/postgres v1.5.0
|
||||
gorm.io/gorm v1.25.0
|
||||
)
|
||||
|
||||
require (
|
||||
cloud.google.com/go v0.105.0 // indirect
|
||||
cloud.google.com/go/compute v1.14.0 // indirect
|
||||
cloud.google.com/go/compute/metadata v0.2.3 // indirect
|
||||
cloud.google.com/go/firestore v1.9.0 // indirect
|
||||
cloud.google.com/go/longrunning v0.3.0 // indirect
|
||||
git.echol.cn/loser/loki-client-go v1.0.1 // indirect
|
||||
github.com/armon/go-metrics v0.4.0 // indirect
|
||||
github.com/beorn7/perks v1.0.1 // indirect
|
||||
github.com/bytedance/sonic v1.8.0 // indirect
|
||||
github.com/caarlos0/env/v6 v6.9.2 // indirect
|
||||
github.com/cespare/xxhash/v2 v2.1.2 // indirect
|
||||
github.com/chenzhuoyu/base64x v0.0.0-20221115062448-fe3a3abad311 // indirect
|
||||
github.com/coreos/go-semver v0.3.0 // indirect
|
||||
github.com/coreos/go-systemd/v22 v22.3.2 // indirect
|
||||
github.com/davecgh/go-spew v1.1.1 // indirect
|
||||
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f // indirect
|
||||
github.com/fatih/color v1.15.0 // indirect
|
||||
github.com/gin-contrib/sse v0.1.0 // indirect
|
||||
@ -40,13 +53,20 @@ require (
|
||||
github.com/go-sql-driver/mysql v1.7.0 // indirect
|
||||
github.com/goccy/go-json v0.10.0 // indirect
|
||||
github.com/gogo/protobuf v1.3.2 // indirect
|
||||
github.com/golang-jwt/jwt v3.2.1+incompatible // indirect
|
||||
github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect
|
||||
github.com/golang/protobuf v1.5.2 // indirect
|
||||
github.com/golang/snappy v0.0.4 // indirect
|
||||
github.com/google/go-cmp v0.5.9 // indirect
|
||||
github.com/googleapis/enterprise-certificate-proxy v0.2.1 // indirect
|
||||
github.com/googleapis/gax-go/v2 v2.7.0 // indirect
|
||||
github.com/hashicorp/consul/api v1.18.0 // indirect
|
||||
github.com/hashicorp/go-cleanhttp v0.5.2 // indirect
|
||||
github.com/hashicorp/go-hclog v1.2.0 // indirect
|
||||
github.com/hashicorp/go-immutable-radix v1.3.1 // indirect
|
||||
github.com/hashicorp/go-rootcerts v1.0.2 // indirect
|
||||
github.com/hashicorp/golang-lru v0.5.4 // indirect
|
||||
github.com/hashicorp/hcl v1.0.0 // indirect
|
||||
github.com/jackc/pgpassfile v1.0.0 // indirect
|
||||
github.com/jackc/pgservicefile v0.0.0-20221227161230-091c0ba34f0a // indirect
|
||||
github.com/jackc/pgx/v5 v5.3.0 // indirect
|
||||
github.com/hashicorp/serf v0.10.1 // indirect
|
||||
github.com/jinzhu/inflection v1.0.0 // indirect
|
||||
github.com/jinzhu/now v1.1.5 // indirect
|
||||
github.com/jmespath/go-jmespath v0.4.0 // indirect
|
||||
@ -59,6 +79,7 @@ require (
|
||||
github.com/mattn/go-colorable v0.1.13 // indirect
|
||||
github.com/mattn/go-isatty v0.0.18 // indirect
|
||||
github.com/matttproud/golang_protobuf_extensions v1.0.1 // indirect
|
||||
github.com/mitchellh/go-homedir v1.1.0 // indirect
|
||||
github.com/mitchellh/mapstructure v1.5.0 // indirect
|
||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
|
||||
github.com/modern-go/reflect2 v1.0.2 // indirect
|
||||
@ -67,11 +88,13 @@ require (
|
||||
github.com/opentracing/opentracing-go v1.2.1-0.20220228012449-10b1cf09e00b // indirect
|
||||
github.com/pelletier/go-toml/v2 v2.0.6 // indirect
|
||||
github.com/pkg/errors v0.9.1 // indirect
|
||||
github.com/pmezard/go-difflib v1.0.0 // indirect
|
||||
github.com/prometheus/client_golang v1.12.2 // indirect
|
||||
github.com/prometheus/client_model v0.2.0 // indirect
|
||||
github.com/prometheus/common v0.34.0 // indirect
|
||||
github.com/prometheus/procfs v0.7.3 // indirect
|
||||
github.com/prometheus/prometheus v1.8.2-0.20201028100903-3245b3267b24 // indirect
|
||||
github.com/sagikazarmark/crypt v0.9.0 // indirect
|
||||
github.com/sirupsen/logrus v1.8.1 // indirect
|
||||
github.com/spf13/afero v1.9.3 // indirect
|
||||
github.com/spf13/cast v1.5.0 // indirect
|
||||
@ -88,6 +111,11 @@ require (
|
||||
github.com/tidwall/tinyqueue v0.0.0-20180302190814-1e39f5511563 // indirect
|
||||
github.com/twitchyliquid64/golang-asm v0.15.1 // indirect
|
||||
github.com/ugorji/go/codec v1.2.9 // indirect
|
||||
go.etcd.io/etcd/api/v3 v3.5.6 // indirect
|
||||
go.etcd.io/etcd/client/pkg/v3 v3.5.6 // indirect
|
||||
go.etcd.io/etcd/client/v2 v2.305.6 // indirect
|
||||
go.etcd.io/etcd/client/v3 v3.5.6 // indirect
|
||||
go.opencensus.io v0.24.0 // indirect
|
||||
go.uber.org/atomic v1.9.0 // indirect
|
||||
go.uber.org/multierr v1.8.0 // indirect
|
||||
go.uber.org/zap v1.21.0 // indirect
|
||||
@ -97,6 +125,8 @@ require (
|
||||
golang.org/x/sys v0.7.0 // indirect
|
||||
golang.org/x/text v0.9.0 // indirect
|
||||
golang.org/x/time v0.1.0 // indirect
|
||||
golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 // indirect
|
||||
google.golang.org/api v0.107.0 // indirect
|
||||
google.golang.org/appengine v1.6.7 // indirect
|
||||
google.golang.org/genproto v0.0.0-20221227171554-f9683d7f8bef // indirect
|
||||
google.golang.org/grpc v1.52.0 // indirect
|
||||
|
131
go.sum
131
go.sum
@ -19,6 +19,8 @@ cloud.google.com/go v0.65.0/go.mod h1:O5N8zS7uWy9vkA9vayVHs65eM1ubvY4h553ofrNHOb
|
||||
cloud.google.com/go v0.72.0/go.mod h1:M+5Vjvlc2wnp6tjzE102Dw08nGShTscUx2nZMufOKPI=
|
||||
cloud.google.com/go v0.74.0/go.mod h1:VV1xSbzvo+9QJOxLDaJfTjx5e+MePCpCWwvftOeQmWk=
|
||||
cloud.google.com/go v0.75.0/go.mod h1:VGuuCn7PG0dwsd5XPVm2Mm3wlh3EL55/79EKB6hlPTY=
|
||||
cloud.google.com/go v0.105.0 h1:DNtEKRBAAzeS4KyIory52wWHuClNaXJ5x1F7xa4q+5Y=
|
||||
cloud.google.com/go v0.105.0/go.mod h1:PrLgOJNe5nfE9UMxKxgXj4mD3voiP+YQ6gdt6KMFOKM=
|
||||
cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o=
|
||||
cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE=
|
||||
cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc=
|
||||
@ -26,8 +28,16 @@ cloud.google.com/go/bigquery v1.5.0/go.mod h1:snEHRnqQbz117VIFhE8bmtwIDY80NLUZUM
|
||||
cloud.google.com/go/bigquery v1.7.0/go.mod h1://okPTzCYNXSlb24MZs83e2Do+h+VXtc4gLoIoXIAPc=
|
||||
cloud.google.com/go/bigquery v1.8.0/go.mod h1:J5hqkt3O0uAFnINi6JXValWIb1v0goeZM77hZzJN/fQ=
|
||||
cloud.google.com/go/bigtable v1.2.0/go.mod h1:JcVAOl45lrTmQfLj7T6TxyMzIN/3FGGcFm+2xVAli2o=
|
||||
cloud.google.com/go/compute v1.14.0 h1:hfm2+FfxVmnRlh6LpB7cg1ZNU+5edAHmW679JePztk0=
|
||||
cloud.google.com/go/compute v1.14.0/go.mod h1:YfLtxrj9sU4Yxv+sXzZkyPjEyPBZfXHUvjxega5vAdo=
|
||||
cloud.google.com/go/compute/metadata v0.2.3 h1:mg4jlk7mCAj6xXp9UJ4fjI9VUI5rubuGBW5aJ7UnBMY=
|
||||
cloud.google.com/go/compute/metadata v0.2.3/go.mod h1:VAV5nSsACxMJvgaAuX6Pk2AawlZn8kiOGuCv6gTkwuA=
|
||||
cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE=
|
||||
cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk=
|
||||
cloud.google.com/go/firestore v1.9.0 h1:IBlRyxgGySXu5VuW0RgGFlTtLukSnNkpDiEOMkQkmpA=
|
||||
cloud.google.com/go/firestore v1.9.0/go.mod h1:HMkjKHNTtRyZNiMzu7YAsLr9K3X2udY2AMwDaMEQiiE=
|
||||
cloud.google.com/go/longrunning v0.3.0 h1:NjljC+FYPV3uh5/OwWT6pVU+doBqMg2x/rZlE+CamDs=
|
||||
cloud.google.com/go/longrunning v0.3.0/go.mod h1:qth9Y41RRSUE69rDcOn6DdK3HfQfsUI0YSmW3iIlLJc=
|
||||
cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I=
|
||||
cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw=
|
||||
cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA=
|
||||
@ -95,8 +105,8 @@ github.com/alecthomas/template v0.0.0-20190718012654-fb15b899a751/go.mod h1:LOuy
|
||||
github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0=
|
||||
github.com/alecthomas/units v0.0.0-20190717042225-c3de453c63f4/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0=
|
||||
github.com/alecthomas/units v0.0.0-20190924025748-f65c72e2690d/go.mod h1:rBZYJk541a8SKzHPHnH3zbiI+7dagKZ0cgpgrD7Fyho=
|
||||
github.com/aliyun/alibaba-cloud-sdk-go v1.62.288 h1:+iF4BDaniUhwnNhyk3ckkDTU5hWSHgmuEqiYa/PKI2o=
|
||||
github.com/aliyun/alibaba-cloud-sdk-go v1.62.288/go.mod h1:Api2AkmMgGaSUAhmk76oaFObkoeCPc/bKAqcyplPODs=
|
||||
github.com/aliyun/alibaba-cloud-sdk-go v1.62.296 h1:fSZXZMcNHX52w4MwvY/YTVy/7h5d/nHd0uUs6qOTkI0=
|
||||
github.com/aliyun/alibaba-cloud-sdk-go v1.62.296/go.mod h1:Api2AkmMgGaSUAhmk76oaFObkoeCPc/bKAqcyplPODs=
|
||||
github.com/aliyun/aliyun-oss-go-sdk v2.2.7+incompatible h1:KpbJFXwhVeuxNtBJ74MCGbIoaBok2uZvkD7QXp2+Wis=
|
||||
github.com/aliyun/aliyun-oss-go-sdk v2.2.7+incompatible/go.mod h1:T/Aws4fEfogEE9v+HPhhw+CntffsBHJ8nXQCwKr0/g8=
|
||||
github.com/andreyvit/diff v0.0.0-20170406064948-c7f18ee00883/go.mod h1:rCTlJbsFo29Kk6CurOXKm700vrz8f0KW0JNfpkRJY/8=
|
||||
@ -110,6 +120,8 @@ github.com/apache/thrift v0.13.0/go.mod h1:cp2SuWMxlEZw2r+iP2GNCdIi4C1qmUzdZFSVb
|
||||
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-metrics v0.3.3/go.mod h1:4O98XIr/9W0sxpJ8UaYkvjk10Iff7SnFrb4QAOwNTFc=
|
||||
github.com/armon/go-metrics v0.4.0 h1:yCQqn7dwca4ITXb+CbubHmedzaQYHhNhrEXLYUeEe8Q=
|
||||
github.com/armon/go-metrics v0.4.0/go.mod h1:E6amYzXo6aW1tqzoZGT755KkbgrJsSdpwZ+3JqfkOG4=
|
||||
github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
|
||||
github.com/armon/go-radix v1.0.0/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
|
||||
github.com/aryann/difflib v0.0.0-20170710044230-e206f873d14a/go.mod h1:DAHtR1m6lCRdSC2Tm3DSWRPvIPr6xNKyeHdqDQSQT+A=
|
||||
@ -159,11 +171,16 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk
|
||||
github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc=
|
||||
github.com/cncf/udpa/go v0.0.0-20200629203442-efcf912fb354/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk=
|
||||
github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk=
|
||||
github.com/cncf/xds/go v0.0.0-20210805033703-aa0b78936158/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs=
|
||||
github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8=
|
||||
github.com/codahale/hdrhistogram v0.0.0-20161010025455-3a0bb77429bd/go.mod h1:sE/e/2PUdi/liOCUjSTXgM1o87ZssimdTWN964YiIeI=
|
||||
github.com/containerd/containerd v1.3.4/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA=
|
||||
github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk=
|
||||
github.com/coreos/go-semver v0.3.0 h1:wkHLiw0WNATZnSG7epLsujiMCgPAc9xhjJ4tgnAxmfM=
|
||||
github.com/coreos/go-semver v0.3.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk=
|
||||
github.com/coreos/go-systemd v0.0.0-20180511133405-39ca1b05acc7/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4=
|
||||
github.com/coreos/go-systemd/v22 v22.3.2 h1:D9/bQk5vlXQFZ6Kwuu6zaiXJ9oTPe68++AzAJc1DzSI=
|
||||
github.com/coreos/go-systemd/v22 v22.3.2/go.mod h1:Y58oyj3AT4RCenI/lSvhwexgC+NSVTIJ3seZv2GcEnc=
|
||||
github.com/coreos/pkg v0.0.0-20160727233714-3ac0863d7acf/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA=
|
||||
github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU=
|
||||
github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7DoTY=
|
||||
@ -189,6 +206,7 @@ github.com/docopt/docopt-go v0.0.0-20180111231733-ee0de3bc6815/go.mod h1:WwZ+bS3
|
||||
github.com/duke-git/lancet/v2 v2.1.19 h1:dbRB1m6wOMV1I0ax/3S6ngop8SYM6I7sr+7D9IXjS2E=
|
||||
github.com/duke-git/lancet/v2 v2.1.19/go.mod h1:hNcc06mV7qr+crH/0nP+rlC3TB0Q9g5OrVnO8/TGD4c=
|
||||
github.com/dustin/go-humanize v0.0.0-20171111073723-bb3d318650d4/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk=
|
||||
github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk=
|
||||
github.com/eapache/go-resiliency v1.1.0/go.mod h1:kFI+JgMyC7bLPUVY133qvEBtVayf5mFgVsvEsIPBvNs=
|
||||
github.com/eapache/go-xerial-snappy v0.0.0-20180814174437-776d5712da21/go.mod h1:+020luEh2TKB4/GOp8oxxtq0Daoen/Cii55CzbTV6DU=
|
||||
github.com/eapache/queue v1.1.0/go.mod h1:6eCeP0CKFpHLu8blIFXhExK/dRa7WDZfr6jVFPTqq+I=
|
||||
@ -202,6 +220,8 @@ github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.m
|
||||
github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1mIlRU8Am5FuJP05cCM98=
|
||||
github.com/envoyproxy/go-control-plane v0.9.7/go.mod h1:cwu0lG7PUMfa9snN8LXBig5ynNVH9qI8YYLbd1fK2po=
|
||||
github.com/envoyproxy/go-control-plane v0.9.9-0.20201210154907-fd9021fe5dad/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk=
|
||||
github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk=
|
||||
github.com/envoyproxy/go-control-plane v0.9.10-0.20210907150352-cf90f659a021/go.mod h1:AFq3mo9L8Lqqiid3OhADV3RfLJnjiw63cSpi+fDTRC0=
|
||||
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
|
||||
github.com/evanphx/json-patch v4.9.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk=
|
||||
github.com/fasthttp-contrib/websocket v0.0.0-20160511215533-1f3b11f56072/go.mod h1:duJ4Jxv5lDcvg4QuQr0oowTf7dz4/CR8NtyCooz9HL8=
|
||||
@ -314,6 +334,8 @@ github.com/go-openapi/validate v0.18.0/go.mod h1:Uh4HdOzKt19xGIGm1qHf/ofbX1YQ4Y+
|
||||
github.com/go-openapi/validate v0.19.2/go.mod h1:1tRCw7m3jtI8eNWEEliiAqUIcBztB2KDnRCRMUi7GTA=
|
||||
github.com/go-openapi/validate v0.19.3/go.mod h1:90Vh6jjkTn+OT1Eefm0ZixWNFjhtOH7vS9k0lo6zwJo=
|
||||
github.com/go-openapi/validate v0.19.8/go.mod h1:8DJv2CVJQ6kGNpFW6eV9N3JviE1C85nY1c2z52x1Gk4=
|
||||
github.com/go-pay/gopay v1.5.92 h1:W1poLl2wdzIDyl96TqWwdxCyDYSSx9AWH0BmXwVR+W4=
|
||||
github.com/go-pay/gopay v1.5.92/go.mod h1:9Xqqi6R3WjUCknmWcy8Y+F/lt0Zi817kA+mlIi2PDMw=
|
||||
github.com/go-playground/assert/v2 v2.2.0 h1:JvknZsQTYeFEAhQwI4qEt9cyV5ONwRHC+lYKSsYSR8s=
|
||||
github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/oXslEjJA=
|
||||
github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY=
|
||||
@ -356,6 +378,7 @@ github.com/gobuffalo/packr/v2 v2.2.0/go.mod h1:CaAwI0GPIAv+5wKLtv8Afwl+Cm78K/I/V
|
||||
github.com/gobuffalo/syncx v0.0.0-20190224160051-33c29581e754/go.mod h1:HhnNqWY95UYwwW3uSASeV7vtgYkT2t16hJgV3AEPUpw=
|
||||
github.com/goccy/go-json v0.10.0 h1:mXKd9Qw4NuzShiRlOXKews24ufknHO7gx30lsDyokKA=
|
||||
github.com/goccy/go-json v0.10.0/go.mod h1:6MelG93GURQebXPDq3khkgXZkazVtN9CRI+MGFi0w8I=
|
||||
github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA=
|
||||
github.com/gofrs/uuid v3.3.0+incompatible/go.mod h1:b2aQJv3Z4Fp6yNu3cdSllBxTCLRxnplIgP/c0N/04lM=
|
||||
github.com/gogo/googleapis v1.1.0/go.mod h1:gf4bu3Q80BeJ6H1S1vYPm8/ELATdvryBaNFGgqEef3s=
|
||||
github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
|
||||
@ -374,6 +397,8 @@ github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4er
|
||||
github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
|
||||
github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
|
||||
github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
|
||||
github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da h1:oI5xCqsCo564l8iNU+DwB5epxmsaqB+rhGL0m5jtYqE=
|
||||
github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da/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=
|
||||
@ -404,6 +429,7 @@ github.com/golang/snappy v0.0.2/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEW
|
||||
github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM=
|
||||
github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
|
||||
github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
|
||||
github.com/google/btree v1.0.0 h1:0udJVsspx3VBr5FwtLhQQtuAsVc79tTq0ocGIPAU6qo=
|
||||
github.com/google/btree v1.0.0/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
|
||||
github.com/google/flatbuffers v1.11.0/go.mod h1:1AeVuKshWv4vARoZatz6mlQ0JxURH0Kv5+zNeJKJCa8=
|
||||
github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
|
||||
@ -414,9 +440,12 @@ github.com/google/go-cmp v0.4.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/
|
||||
github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
||||
github.com/google/go-cmp v0.5.1/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
||||
github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
|
||||
github.com/google/go-cmp v0.5.3/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/google/go-cmp v0.5.7/go.mod h1:n+brtR0CgQNWTVd5ZUFpTBC8YFBDLK/h/bpaJ8/DtOE=
|
||||
github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38=
|
||||
github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
|
||||
github.com/google/go-querystring v1.0.0 h1:Xkwi/a1rcvNg1PPYe5vI8GbeBY/jrVuDX5ASuANWTrk=
|
||||
github.com/google/go-querystring v1.0.0/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck=
|
||||
github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
||||
@ -441,8 +470,12 @@ github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+
|
||||
github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||
github.com/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I=
|
||||
github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||
github.com/googleapis/enterprise-certificate-proxy v0.2.1 h1:RY7tHKZcRlk788d5WSo/e83gOyyy742E8GSs771ySpg=
|
||||
github.com/googleapis/enterprise-certificate-proxy v0.2.1/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k=
|
||||
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/googleapis/gax-go/v2 v2.7.0 h1:IcsPKeInNvYi7eqSaDjiZqDDKu5rsmunY0Y1YupQSSQ=
|
||||
github.com/googleapis/gax-go/v2 v2.7.0/go.mod h1:TEop28CZZQ2y+c0VxMUmu1lV+fQx57QpBWsYpwqHJx8=
|
||||
github.com/googleapis/gnostic v0.4.1/go.mod h1:LRhVm6pbyptWbWbuZ38d1eyptfvIytN3ir6b65WBswg=
|
||||
github.com/googleapis/google-cloud-go-testing v0.0.0-20200911160855-bcd43fbb19e8/go.mod h1:dvDLG8qkwmyD9a/MJJN3XJcT3xFxOKAvTZGvuZmac9g=
|
||||
github.com/gophercloud/gophercloud v0.13.0/go.mod h1:VX0Ibx85B60B5XOrZr6kaNwrmPUzcmMpwxvQ1WQIIWM=
|
||||
@ -459,42 +492,68 @@ github.com/grpc-ecosystem/go-grpc-middleware v1.0.1-0.20190118093823-f849b5445de
|
||||
github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk=
|
||||
github.com/grpc-ecosystem/grpc-gateway v1.9.5/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY=
|
||||
github.com/grpc-ecosystem/grpc-gateway v1.15.0/go.mod h1:vO11I9oWA+KsxmfFQPhLnnIb1VDE24M+pdxZFiuZcA8=
|
||||
github.com/grpc-ecosystem/grpc-gateway v1.16.0/go.mod h1:BDjrQk3hbvj6Nolgz8mAMFbcEtjT1g+wF4CSlocrBnw=
|
||||
github.com/hashicorp/consul/api v1.3.0/go.mod h1:MmDNSzIMUjNpY/mQ398R4bk2FnqQLoPndWW5VkKPlCE=
|
||||
github.com/hashicorp/consul/api v1.7.0/go.mod h1:1NSuaUUkFaJzMasbfq/11wKYWSR67Xn6r2DXKhuDNFg=
|
||||
github.com/hashicorp/consul/api v1.18.0 h1:R7PPNzTCeN6VuQNDwwhZWJvzCtGSrNpJqfb22h3yH9g=
|
||||
github.com/hashicorp/consul/api v1.18.0/go.mod h1:owRRGJ9M5xReDC5nfT8FTJrNAPbT4NM6p/k+d03q2v4=
|
||||
github.com/hashicorp/consul/sdk v0.3.0/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8=
|
||||
github.com/hashicorp/consul/sdk v0.6.0/go.mod h1:fY08Y9z5SvJqevyZNy6WWPXiG3KwBPAvlcdx16zZ0fM=
|
||||
github.com/hashicorp/consul/sdk v0.13.0 h1:lce3nFlpv8humJL8rNrrGHYSKc3q+Kxfeg3Ii1m6ZWU=
|
||||
github.com/hashicorp/consul/sdk v0.13.0/go.mod h1:0hs/l5fOVhJy/VdcoaNqUSi2AUs95eF5WKtv+EYIQqE=
|
||||
github.com/hashicorp/errwrap v1.0.0 h1:hLrqtEDnRye3+sgx6z4qVLNuviH3MR5aQ0ykNJa/UYA=
|
||||
github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
|
||||
github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
|
||||
github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
|
||||
github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9neXJWAZQ=
|
||||
github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48=
|
||||
github.com/hashicorp/go-hclog v0.12.0/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ=
|
||||
github.com/hashicorp/go-hclog v0.12.2/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ=
|
||||
github.com/hashicorp/go-hclog v1.2.0 h1:La19f8d7WIlm4ogzNHB0JGqs5AUDAZ2UfCY4sJXcJdM=
|
||||
github.com/hashicorp/go-hclog v1.2.0/go.mod h1:whpDNt7SSdeAju8AWKIWsul05p54N/39EeqMAyrmvFQ=
|
||||
github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
|
||||
github.com/hashicorp/go-immutable-radix v1.2.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
|
||||
github.com/hashicorp/go-immutable-radix v1.3.1 h1:DKHmCUm2hRBK510BaiZlwvpD40f8bJFeZnpfm2KLowc=
|
||||
github.com/hashicorp/go-immutable-radix v1.3.1/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
|
||||
github.com/hashicorp/go-msgpack v0.5.3 h1:zKjpN5BK/P5lMYrLmBHdBULWbJ0XpYR+7NGzqkZzoD4=
|
||||
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-multierror v1.1.0 h1:B9UzwGQJehnUY1yNrnwREHc3fGbC2xefo8g4TbElacI=
|
||||
github.com/hashicorp/go-multierror v1.1.0/go.mod h1:spPvp8C1qA32ftKqdAHm4hHTbPw+vmowP0z+KUhOZdA=
|
||||
github.com/hashicorp/go-retryablehttp v0.5.3/go.mod h1:9B5zBasrRhHXnJnui7y6sL7es7NDiJgTc6Er0maI1Xs=
|
||||
github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU=
|
||||
github.com/hashicorp/go-rootcerts v1.0.2 h1:jzhAVGtqPKbwpyCPELlgNWhE1znq+qwJtW5Oi2viEzc=
|
||||
github.com/hashicorp/go-rootcerts v1.0.2/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8=
|
||||
github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU=
|
||||
github.com/hashicorp/go-sockaddr v1.0.2 h1:ztczhD1jLxIRjVejw8gFomI1BQZOe2WoVOu0SyteCQc=
|
||||
github.com/hashicorp/go-sockaddr v1.0.2/go.mod h1:rB4wwRAUzs07qva3c5SdrY/NEtAUjGlgmH/UkBUC97A=
|
||||
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-uuid v1.0.2 h1:cfejS+Tpcp13yd5nYHWDI6qVCny6wyX2Mt5SGur2IGE=
|
||||
github.com/hashicorp/go-uuid v1.0.2/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
|
||||
github.com/hashicorp/go-version v1.2.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA=
|
||||
github.com/hashicorp/go-version v1.2.1 h1:zEfKbn2+PDgroKdiOzqiE8rsmLqU2uwi5PB5pBJ3TkI=
|
||||
github.com/hashicorp/go-version v1.2.1/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA=
|
||||
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 h1:YDjusn29QI/Das2iO9M0BHnIbxPeyuCHsjMW+lJfyTc=
|
||||
github.com/hashicorp/golang-lru v0.5.4/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4=
|
||||
github.com/hashicorp/hcl v1.0.0 h1:0Anlzjpi4vEasTeNFn2mLJgTSwt0+6sfsiTG8qcWGx4=
|
||||
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/mdns v1.0.1/go.mod h1:4gW7WsVCke5TE7EPeYliwHlRUyBtfCwuFwuMg2DmyNY=
|
||||
github.com/hashicorp/mdns v1.0.4/go.mod h1:mtBihi+LeNXGtG8L9dX59gAEa12BDtBQSp4v/YAJqrc=
|
||||
github.com/hashicorp/memberlist v0.1.3/go.mod h1:ajVTdAv/9Im8oMAAj5G31PhhMCZJV2pPBoIllUwCN7I=
|
||||
github.com/hashicorp/memberlist v0.2.2/go.mod h1:MS2lj3INKhZjWNqd3N0m3J+Jxf3DAOnAH9VT3Sh9MUE=
|
||||
github.com/hashicorp/memberlist v0.5.0 h1:EtYPN8DpAURiapus508I4n9CzHs2W+8NZGbmmR/prTM=
|
||||
github.com/hashicorp/memberlist v0.5.0/go.mod h1:yvyXLpo0QaGE59Y7hDTsTzDD25JYBZ4mHgHUZ8lrOI0=
|
||||
github.com/hashicorp/serf v0.8.2/go.mod h1:6hOLApaqBFA1NXqRQAsxw9QxuDEvNxSQRwA/JwenrHc=
|
||||
github.com/hashicorp/serf v0.9.3/go.mod h1:UWDWwZeL5cuWDJdl0C6wrvrUwEqtQ4ZKBKKENpqIUyk=
|
||||
github.com/hashicorp/serf v0.10.1 h1:Z1H2J60yRKvfDYAOZLd2MU0ND4AH/WDz7xYHDWQsIPY=
|
||||
github.com/hashicorp/serf v0.10.1/go.mod h1:yL2t6BqATOLGc5HF7qbFkTfXoPIY0WZdWHfEvMqbG+4=
|
||||
github.com/hetznercloud/hcloud-go v1.22.0/go.mod h1:xng8lbDUg+xM1dgc0yGHX5EeqbwIq7UYlMWMTx3SQVg=
|
||||
github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU=
|
||||
github.com/hudl/fargo v1.3.0/go.mod h1:y3CKSmjA+wD2gak7sUSXTAoopbhU08POFhmITJgmKTg=
|
||||
@ -513,13 +572,6 @@ github.com/influxdata/promql/v2 v2.12.0/go.mod h1:fxOPu+DY0bqCTCECchSRtWfc+0X19y
|
||||
github.com/influxdata/roaring v0.4.13-0.20180809181101-fc520f41fab6/go.mod h1:bSgUQ7q5ZLSO+bKBGqJiCBGAl+9DxyW63zLTujjUlOE=
|
||||
github.com/influxdata/tdigest v0.0.0-20181121200506-bf2b5ad3c0a9/go.mod h1:Js0mqiSBE6Ffsg94weZZ2c+v/ciT8QRHFOap7EKDrR0=
|
||||
github.com/influxdata/usage-client v0.0.0-20160829180054-6d3895376368/go.mod h1:Wbbw6tYNvwa5dlB6304Sd+82Z3f7PmVZHVKU637d4po=
|
||||
github.com/jackc/pgpassfile v1.0.0 h1:/6Hmqy13Ss2zCq62VdNG8tM1wchn8zjSGOBJ6icpsIM=
|
||||
github.com/jackc/pgpassfile v1.0.0/go.mod h1:CEx0iS5ambNFdcRtxPj5JhEz+xB6uRky5eyVu/W2HEg=
|
||||
github.com/jackc/pgservicefile v0.0.0-20221227161230-091c0ba34f0a h1:bbPeKD0xmW/Y25WS6cokEszi5g+S0QxI/d45PkRi7Nk=
|
||||
github.com/jackc/pgservicefile v0.0.0-20221227161230-091c0ba34f0a/go.mod h1:5TJZWKEWniPve33vlWYSoGYefn3gLQRzjfDlhSJ9ZKM=
|
||||
github.com/jackc/pgx/v5 v5.3.0 h1:/NQi8KHMpKWHInxXesC8yD4DhkXPrVhmnwYkjp9AmBA=
|
||||
github.com/jackc/pgx/v5 v5.3.0/go.mod h1:t3JDKnCBlYIc0ewLF0Q7B8MXmoIaBOZj/ic7iHozM/8=
|
||||
github.com/jackc/puddle/v2 v2.2.0/go.mod h1:vriiEXHvEE654aYKXXjOvZM39qJ0q+azkZFrfEOc3H4=
|
||||
github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI=
|
||||
github.com/jinzhu/inflection v1.0.0 h1:K317FqzuhWc8YvSVlFMCCUb36O/S9MCKRDI7QkRKD/E=
|
||||
github.com/jinzhu/inflection v1.0.0/go.mod h1:h+uFLlag+Qp1Va5pdKtLDYj+kHp5pxUVkryuEj+Srlc=
|
||||
@ -579,7 +631,6 @@ github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORN
|
||||
github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
|
||||
github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
|
||||
github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0=
|
||||
github.com/kr/pretty v0.3.0/go.mod h1:640gp4NfQd8pI5XOwp5fnNeVWj67G7CFk/SaSQn7NBk=
|
||||
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
||||
github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA=
|
||||
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
|
||||
@ -631,9 +682,12 @@ github.com/medivhzhan/weapp/v3 v3.6.19/go.mod h1:DBlnuMNGIcDYSDaM8JnBIT14I+OqMaM
|
||||
github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
|
||||
github.com/miekg/dns v1.1.26/go.mod h1:bPDLeHnStXmXAq1m/Ch/hvfNHr14JKNPMBo3VZKjuso=
|
||||
github.com/miekg/dns v1.1.31/go.mod h1:KNUDUusw/aVsxyTYZM1oqvCicbwhgbNgztCETuNZ7xM=
|
||||
github.com/miekg/dns v1.1.41/go.mod h1:p6aan82bvRIyn+zDIv9xYNUpwa73JcSh9BKwknJysuI=
|
||||
github.com/miekg/dns v1.1.43 h1:JKfpVSCB84vrAmHzyrsxB5NAr5kLoMXZArPSw7Qlgyg=
|
||||
github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc=
|
||||
github.com/mitchellh/cli v1.1.0/go.mod h1:xcISNoH86gajksDmfB23e/pu+B+GeFRMYmoHXxx3xhI=
|
||||
github.com/mitchellh/go-homedir v1.0.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
|
||||
github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y=
|
||||
github.com/mitchellh/go-homedir v1.1.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/go-wordwrap v1.0.0/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo=
|
||||
@ -642,6 +696,7 @@ github.com/mitchellh/iochan v1.0.0/go.mod h1:JwYml1nuB7xOzsp52dPpHFffvOCDupsG0Qu
|
||||
github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
|
||||
github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
|
||||
github.com/mitchellh/mapstructure v1.2.2/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo=
|
||||
github.com/mitchellh/mapstructure v1.4.1/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo=
|
||||
github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY=
|
||||
github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo=
|
||||
github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
||||
@ -711,6 +766,7 @@ github.com/openzipkin/zipkin-go v0.2.1/go.mod h1:NaW6tEwdmWMaCDZzg8sh+IBNOxHMPnh
|
||||
github.com/openzipkin/zipkin-go v0.2.2/go.mod h1:NaW6tEwdmWMaCDZzg8sh+IBNOxHMPnhQw8ySjnjRyN4=
|
||||
github.com/pact-foundation/pact-go v1.0.4/go.mod h1:uExwJY4kCzNPcHRj+hCR/HBbOOIwwtUjcrb0b5/5kLM=
|
||||
github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc=
|
||||
github.com/pascaldekloe/goe v0.1.0 h1:cBOtyMzM9HTpWjXfbbunk26uA6nG3a8n06Wieeh0MwY=
|
||||
github.com/pascaldekloe/goe v0.1.0/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc=
|
||||
github.com/paulbellamy/ratecounter v0.2.0/go.mod h1:Hfx1hDpSGoqxkVVpBi/IlYD7kChlfo5C6hzIHwPqfFE=
|
||||
github.com/pborman/uuid v1.2.0/go.mod h1:X/NO0urCmaxf9VXbdlT7C2Yzkj2IKimNn4k+gtPdI/k=
|
||||
@ -743,6 +799,7 @@ github.com/prometheus/client_golang v1.4.0/go.mod h1:e9GMxYsXl05ICDXkRhurwBS4Q3O
|
||||
github.com/prometheus/client_golang v1.6.0/go.mod h1:ZLOG9ck3JLRdB5MgO8f+lLTe83AXG6ro35rLTxvnIl4=
|
||||
github.com/prometheus/client_golang v1.7.1/go.mod h1:PY5Wy2awLA44sXw4AOSfFBetzPP4j5+D6mVACh+pe2M=
|
||||
github.com/prometheus/client_golang v1.11.0/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0=
|
||||
github.com/prometheus/client_golang v1.11.1/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0=
|
||||
github.com/prometheus/client_golang v1.12.1/go.mod h1:3Z9XVyYiZYEO+YQWt3RD2R3jrbd179Rt297l4aS6nDY=
|
||||
github.com/prometheus/client_golang v1.12.2 h1:51L9cDoUHVrXx4zWYlcLQIZ+d+VXHgqnYKkIuq4g/34=
|
||||
github.com/prometheus/client_golang v1.12.2/go.mod h1:3Z9XVyYiZYEO+YQWt3RD2R3jrbd179Rt297l4aS6nDY=
|
||||
@ -778,21 +835,25 @@ github.com/prometheus/prometheus v1.8.2-0.20201028100903-3245b3267b24 h1:V/4Cj2G
|
||||
github.com/prometheus/prometheus v1.8.2-0.20201028100903-3245b3267b24/go.mod h1:MDRkz271loM/PrYN+wUNEaTMDGSP760MQzB0yEjdgSQ=
|
||||
github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4=
|
||||
github.com/retailnext/hllpp v1.0.1-0.20180308014038-101a6d2f8b52/go.mod h1:RDpi1RftBQPUCDRw6SmxeaREsAaRKnOclghuzp/WRzc=
|
||||
github.com/robfig/cron/v3 v3.0.1 h1:WdRxkvbJztn8LMz/QEvLN5sBU+xKpSqwwUO1Pjr4qDs=
|
||||
github.com/robfig/cron/v3 v3.0.1/go.mod h1:eQICP3HwyT7UooqI/z+Ov+PtYAWygg1TEWWzGIFLtro=
|
||||
github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg=
|
||||
github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ=
|
||||
github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
|
||||
github.com/rogpeppe/go-internal v1.2.2/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
|
||||
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
|
||||
github.com/rogpeppe/go-internal v1.6.1/go.mod h1:xXDCJY+GAPziupqXw64V24skbSoqbTEfhy4qGm1nDQc=
|
||||
github.com/rogpeppe/go-internal v1.8.0 h1:FCbCCtXNOY3UtUuHUYaghJg4y7Fd14rXifAYUAtL9R8=
|
||||
github.com/rs/cors v1.7.0/go.mod h1:gFx+x8UowdsKA9AchylcLynDq+nNFfI8FkUZdN/jGCU=
|
||||
github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
|
||||
github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts=
|
||||
github.com/ryanuber/columnize v2.1.0+incompatible/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts=
|
||||
github.com/sagikazarmark/crypt v0.9.0 h1:fipzMFW34hFUEc4D7fsLQFtE7yElkpgyS2zruedRdZk=
|
||||
github.com/sagikazarmark/crypt v0.9.0/go.mod h1:RnH7sEhxfdnPm1z+XMgSLjWTEIjyK4z2dw6+4vHTMuo=
|
||||
github.com/samuel/go-zookeeper v0.0.0-20190923202752-2cc03de413da/go.mod h1:gi+0XIa01GRL2eRQVjQkKGqKF3SF9vZR/HnPullcV2E=
|
||||
github.com/samuel/go-zookeeper v0.0.0-20200724154423-2164a8ac840e/go.mod h1:gi+0XIa01GRL2eRQVjQkKGqKF3SF9vZR/HnPullcV2E=
|
||||
github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0=
|
||||
github.com/sclevine/agouti v3.0.0+incompatible/go.mod h1:b4WX9W9L1sfQKXeJf1mUTLZKJ48R1S7H23Ji7oFO5Bw=
|
||||
github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529 h1:nn5Wsu0esKSJiIVhscUtVbo7ada43DJhG55ua/hjS5I=
|
||||
github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc=
|
||||
github.com/segmentio/kafka-go v0.1.0/go.mod h1:X6itGqS9L4jDletMsxZ7Dz+JFWxM6JHfPOCvTvk+EJo=
|
||||
github.com/segmentio/kafka-go v0.2.0/go.mod h1:X6itGqS9L4jDletMsxZ7Dz+JFWxM6JHfPOCvTvk+EJo=
|
||||
@ -840,6 +901,7 @@ github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+
|
||||
github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
|
||||
github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE=
|
||||
github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw=
|
||||
github.com/stretchr/objx v0.5.0 h1:1zr/of2m5FGMsad5YfcqgdqdWrIhu+EBEJRhR1U7z/c=
|
||||
github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo=
|
||||
github.com/stretchr/testify v1.2.0/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
|
||||
github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
|
||||
@ -922,9 +984,16 @@ github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9de
|
||||
github.com/yuin/goldmark v1.1.32/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
||||
github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
||||
github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
||||
github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
|
||||
go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU=
|
||||
go.etcd.io/etcd v0.0.0-20191023171146-3cf2f69b5738/go.mod h1:dnLIgRNXwCJa5e+c6mIZCrds/GIG4ncV9HhK5PX7jPg=
|
||||
go.etcd.io/etcd/api/v3 v3.5.6 h1:Cy2qx3npLcYqTKqGJzMypnMv2tiRyifZJ17BlWIWA7A=
|
||||
go.etcd.io/etcd/api/v3 v3.5.6/go.mod h1:KFtNaxGDw4Yx/BA4iPPwevUTAuqcsPxzyX8PHydchN8=
|
||||
go.etcd.io/etcd/client/pkg/v3 v3.5.6 h1:TXQWYceBKqLp4sa87rcPs11SXxUA/mHwH975v+BDvLU=
|
||||
go.etcd.io/etcd/client/pkg/v3 v3.5.6/go.mod h1:ggrwbk069qxpKPq8/FKkQ3Xq9y39kbFR4LnKszpRXeQ=
|
||||
go.etcd.io/etcd/client/v2 v2.305.6 h1:fIDR0p4KMjw01MJMfUIDWdQbjo06PD6CeYM5z4EHLi0=
|
||||
go.etcd.io/etcd/client/v2 v2.305.6/go.mod h1:BHha8XJGe8vCIBfWBpbBLVZ4QjOIlfoouvOwydu63E0=
|
||||
go.etcd.io/etcd/client/v3 v3.5.6 h1:coLs69PWCXE9G4FKquzNaSHrRyMCAXwF+IX1tAPVO8E=
|
||||
go.etcd.io/etcd/client/v3 v3.5.6/go.mod h1:f6GRinRMCsFVv9Ht42EyY7nfsVGwrNO0WEoS2pRKzQk=
|
||||
go.mongodb.org/mongo-driver v1.0.3/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM=
|
||||
go.mongodb.org/mongo-driver v1.1.1/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM=
|
||||
go.mongodb.org/mongo-driver v1.1.2/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM=
|
||||
@ -938,7 +1007,10 @@ go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
||||
go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
||||
go.opencensus.io v0.22.4/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw=
|
||||
go.opencensus.io v0.22.5/go.mod h1:5pWMHQbX5EPX2/62yrJeAkowc+lfs/XD7Uxpq3pI6kk=
|
||||
go.opencensus.io v0.24.0 h1:y73uSU6J157QMP2kn2r30vwW1A2W2WFwSCGnAVxeaD0=
|
||||
go.opencensus.io v0.24.0/go.mod h1:vNK8G9p7aAivkbmorf4v+7Hgx+Zs0yY+0fOtgBfjQKo=
|
||||
go.opentelemetry.io/otel v0.6.0/go.mod h1:jzBIgIzK43Iu1BpDAXwqOd6UPsSAk+ewVZ5ofSXw4Ek=
|
||||
go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI=
|
||||
go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE=
|
||||
go.uber.org/atomic v1.5.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ=
|
||||
go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
|
||||
@ -956,6 +1028,7 @@ go.uber.org/tools v0.0.0-20190618225709-2cfd321de3ee/go.mod h1:vJERXedbb3MVM5f9E
|
||||
go.uber.org/zap v1.9.1/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q=
|
||||
go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q=
|
||||
go.uber.org/zap v1.13.0/go.mod h1:zwrFLgMcdUuIBviXEYEH1YKNaOBnKXsx2IPda5bBwHM=
|
||||
go.uber.org/zap v1.17.0/go.mod h1:MXVU+bhUf/A7Xi2HNOnopQOrmycQ5Ih87HtOu4q5SSo=
|
||||
go.uber.org/zap v1.21.0 h1:WefMeulhovoZ2sYXz7st6K0sLj7bBhpiFaud4r4zST8=
|
||||
go.uber.org/zap v1.21.0/go.mod h1:wjWOCqI0f2ZZrJF/UufIOkiC8ii6tm1iqIsLo76RfJw=
|
||||
golang.org/x/arch v0.0.0-20210923205945-b76863e36670 h1:18EFjUmQOcUvxNYSkA6jO9VAiXCnxFY6NyDX0bHDmkU=
|
||||
@ -978,10 +1051,8 @@ golang.org/x/crypto v0.0.0-20191206172530-e9b2fee46413/go.mod h1:LzIPMQfyMNhhGPh
|
||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||
golang.org/x/crypto v0.0.0-20201002170205-7f63de1d35b0/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||
golang.org/x/crypto v0.0.0-20210421170649-83a5a9bb288b/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4=
|
||||
golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
||||
golang.org/x/crypto v0.0.0-20211108221036-ceb1ce70b4fa/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
||||
golang.org/x/crypto v0.0.0-20220214200702-86341886e292/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
|
||||
golang.org/x/crypto v0.6.0/go.mod h1:OFC/31mSvZgRz0V1QTNCzfAI1aIRzbiufJtkMIlEp58=
|
||||
golang.org/x/crypto v0.8.0 h1:pd9TJtTueMTVQXzk8E2XESSMQDj/U7OUu0PqJqPXQjQ=
|
||||
golang.org/x/crypto v0.8.0/go.mod h1:mRqEX+O9/h5TFCrQhkgjo2yKi0yYA+9ecGkdQoHrywE=
|
||||
golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
||||
@ -1011,6 +1082,7 @@ golang.org/x/lint v0.0.0-20191125180803-fdd1cda4f05f/go.mod h1:5qLYkcX4OjUUV8bRu
|
||||
golang.org/x/lint v0.0.0-20200130185559-910be7a94367/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY=
|
||||
golang.org/x/lint v0.0.0-20200302205851-738671d3881b/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY=
|
||||
golang.org/x/lint v0.0.0-20201208152925-83fdc39ff7b5/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY=
|
||||
golang.org/x/lint v0.0.0-20210508222113-6edffad5e616/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY=
|
||||
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=
|
||||
@ -1022,7 +1094,6 @@ golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.4.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.4.1/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
|
||||
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-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
@ -1066,16 +1137,17 @@ golang.org/x/net v0.0.0-20200822124328-c89045814202/go.mod h1:/O7V0waA8r7cgGh81R
|
||||
golang.org/x/net v0.0.0-20201006153459-a7d1128ccaa0/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||
golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||
golang.org/x/net v0.0.0-20201031054903-ff519b6c9102/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||
golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||
golang.org/x/net v0.0.0-20201209123823-ac852fbbde11/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||
golang.org/x/net v0.0.0-20201224014010-6772e930b67b/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
|
||||
golang.org/x/net v0.0.0-20210410081132-afb366fc7cd1/go.mod h1:9tjilg8BloeKEkVJvy7fQ90B1CfIiPueXVOjqfkSzI8=
|
||||
golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||
golang.org/x/net v0.0.0-20211216030914-fe4d6282115f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||
golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
|
||||
golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
|
||||
golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
|
||||
golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
|
||||
golang.org/x/net v0.9.0 h1:aWJ/m6xSmxWBx+V0XRHTlrYrPG56jKsLdTFmsSsCzOM=
|
||||
golang.org/x/net v0.9.0/go.mod h1:d48xBJpPfHeWQsugry2m+kC02ZBRGRgulfHnEXEuWns=
|
||||
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||
@ -1104,7 +1176,6 @@ golang.org/x/sync v0.0.0-20200930132711-30421366ff76/go.mod h1:RxMgew5VJxzue5/jJ
|
||||
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20201207232520-09787c993a3a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.1.0 h1:wsuoTGHzEhffawBOhz5CYhcrV4IdKZbEyZjBMuTp12o=
|
||||
golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
@ -1175,7 +1246,9 @@ golang.org/x/sys v0.0.0-20210104204734-6f8348627aad/go.mod h1:h1NjWce9XRLGQEsW7w
|
||||
golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210225134936-a50acf3fe073/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210303074136-134d130e1a04/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210403161142-5e06dd20ab57/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210423185535-09eb48e85fd7/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
@ -1184,26 +1257,24 @@ golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBc
|
||||
golang.org/x/sys v0.0.0-20211216021012-1d35b9e2eb4e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220114195835-da31bd327af9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220227234510-4e6760a101f9/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220908164124-27713097b956/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.7.0 h1:3jlCCIQZPdOYu1h8BkNvLz8Kgwtae2cagcG/VamtZRU=
|
||||
golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
||||
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
||||
golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k=
|
||||
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||
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/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
||||
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
|
||||
golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
|
||||
golang.org/x/text v0.9.0 h1:2sjJmO8cDvYveuX97RDLsxlyUxLl+GHoLxBiRdHllBE=
|
||||
golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
|
||||
golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||
@ -1285,12 +1356,14 @@ golang.org/x/tools v0.0.0-20210105154028-b0ab187a4818/go.mod h1:emZCQorbCU4vsT4f
|
||||
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||
golang.org/x/tools v0.0.0-20210108195828-e2f9c7f1fc8e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||
golang.org/x/tools v0.1.0/go.mod h1:xkSsbof2nBLbhDlRMhhhyNLN/zl3eTqcnHD5viDpcZ0=
|
||||
golang.org/x/tools v0.1.2/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
|
||||
golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
|
||||
golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
|
||||
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=
|
||||
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 h1:H2TDz8ibqkAF6YGhCdN3jS9O0/s90v0rJh3X/OLHEUk=
|
||||
golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8=
|
||||
gonum.org/v1/gonum v0.0.0-20180816165407-929014505bf4/go.mod h1:Y+Yx5eoAFn32cQvJDxZx5Dpnq+c3wtXuadVZAcxbbBo=
|
||||
gonum.org/v1/gonum v0.0.0-20181121035319-3f7ecaa7e8ca/go.mod h1:Y+Yx5eoAFn32cQvJDxZx5Dpnq+c3wtXuadVZAcxbbBo=
|
||||
gonum.org/v1/gonum v0.6.0/go.mod h1:9mxDZsDKxgMAuccQkewq682L+0eCu4dCN2yonUJTCLU=
|
||||
@ -1318,6 +1391,8 @@ google.golang.org/api v0.32.0/go.mod h1:/XrVsuzM0rZmrsbjJutiuftIzeuTQcEeaYcSk/mQ
|
||||
google.golang.org/api v0.35.0/go.mod h1:/XrVsuzM0rZmrsbjJutiuftIzeuTQcEeaYcSk/mQ1dg=
|
||||
google.golang.org/api v0.36.0/go.mod h1:+z5ficQTmoYpPn8LCUNVpK5I7hwkpjbcgqA7I34qYtE=
|
||||
google.golang.org/api v0.40.0/go.mod h1:fYKFpnQN0DsDSKRVRcQSDQNtqWPfM9i+zNPxepjRCQ8=
|
||||
google.golang.org/api v0.107.0 h1:I2SlFjD8ZWabaIFOfeEDg3pf0BHJDh6iYQ1ic3Yu/UU=
|
||||
google.golang.org/api v0.107.0/go.mod h1:2Ts0XTHNVWxypznxWOYUeI4g3WdP9Pk2Qk58+a/O9MY=
|
||||
google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
|
||||
google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
@ -1368,6 +1443,7 @@ google.golang.org/genproto v0.0.0-20201210142538-e3217bee35cc/go.mod h1:FWY/as6D
|
||||
google.golang.org/genproto v0.0.0-20201214200347-8c77b98c765d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
||||
google.golang.org/genproto v0.0.0-20210108203827-ffc7fda8c3d7/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
||||
google.golang.org/genproto v0.0.0-20210226172003-ab064af71705/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
|
||||
google.golang.org/genproto v0.0.0-20210602131652-f16073e35f0c/go.mod h1:UODoCrxHCcBojKKwX1terBiRUaqAsFqJiF615XL43r0=
|
||||
google.golang.org/genproto v0.0.0-20221227171554-f9683d7f8bef h1:uQ2vjV/sHTsWSqdKeLqmwitzgvjMl7o4IdtHwUDXSJY=
|
||||
google.golang.org/genproto v0.0.0-20221227171554-f9683d7f8bef/go.mod h1:RGgjbofJ8xD9Sq1VVhDM1Vok1vRONV+rg+CjzG4SZKM=
|
||||
google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs=
|
||||
@ -1389,9 +1465,13 @@ google.golang.org/grpc v1.30.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM
|
||||
google.golang.org/grpc v1.31.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
||||
google.golang.org/grpc v1.31.1/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
||||
google.golang.org/grpc v1.32.0/go.mod h1:N36X2cJ7JwdamYAgDz+s+rVMFjt3numwzf/HckM8pak=
|
||||
google.golang.org/grpc v1.33.1/go.mod h1:fr5YgcSWrqhRRxogOsw7RzIpsmvOZ6IcH4kBYTpR3n0=
|
||||
google.golang.org/grpc v1.33.2/go.mod h1:JMHMWHQWaTccqQQlmk3MJZS+GWXOdAesneDmEnv2fbc=
|
||||
google.golang.org/grpc v1.34.0/go.mod h1:WotjhfgOW/POjDeRt8vscBtXq+2VjORFy659qA51WJ8=
|
||||
google.golang.org/grpc v1.35.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU=
|
||||
google.golang.org/grpc v1.36.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU=
|
||||
google.golang.org/grpc v1.38.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM=
|
||||
google.golang.org/grpc v1.41.0/go.mod h1:U3l9uK9J0sini8mHphKoXyaqDA/8VyGnDee1zzIUK6k=
|
||||
google.golang.org/grpc v1.52.0 h1:kd48UiU7EHsV4rnLyOJRuP/Il/UHE7gdDAQ+SZI7nZk=
|
||||
google.golang.org/grpc v1.52.0/go.mod h1:pu6fVzoFb+NBYNAvQL08ic+lvB2IojljRYuun5vorUY=
|
||||
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
|
||||
@ -1413,7 +1493,6 @@ gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8
|
||||
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q=
|
||||
gopkg.in/cheggaaa/pb.v1 v1.0.25/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw=
|
||||
gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI=
|
||||
gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
|
||||
@ -1446,8 +1525,6 @@ gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
|
||||
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
|
||||
gorm.io/driver/mysql v1.5.0 h1:6hSAT5QcyIaty0jfnff0z0CLDjyRgZ8mlMHLqSt7uXM=
|
||||
gorm.io/driver/mysql v1.5.0/go.mod h1:FFla/fJuCvyTi7rJQd27qlNX2v3L6deTR1GgTjSOLPo=
|
||||
gorm.io/driver/postgres v1.5.0 h1:u2FXTy14l45qc3UeCJ7QaAXZmZfDDv0YrthvmRq1l0U=
|
||||
gorm.io/driver/postgres v1.5.0/go.mod h1:FUZXzO+5Uqg5zzwzv4KK49R8lvGIyscBOqYrtI1Ce9A=
|
||||
gorm.io/gorm v1.24.7-0.20230306060331-85eaf9eeda11/go.mod h1:L4uxeKpfBml98NYqVqwAdmV1a2nBtAec/cf3fpucW/k=
|
||||
gorm.io/gorm v1.25.0 h1:+KtYtb2roDz14EQe4bla8CbQlmb9dN3VejSai3lprfU=
|
||||
gorm.io/gorm v1.25.0/go.mod h1:L4uxeKpfBml98NYqVqwAdmV1a2nBtAec/cf3fpucW/k=
|
||||
|
@ -6,5 +6,4 @@ import "Lee-WineList/client"
|
||||
func initClient() {
|
||||
client.InitMySQLClient()
|
||||
client.InitRedisClient()
|
||||
//client.InitPostgreSQLClient()
|
||||
}
|
||||
|
@ -9,9 +9,9 @@ import (
|
||||
// 初始化数据库表
|
||||
func databaseTable() {
|
||||
dbs := []any{
|
||||
entity.User{},
|
||||
entity.AdminUser{},
|
||||
entity.OAuth2Client{},
|
||||
new(entity.User), // 普通用户
|
||||
new(entity.OAuth2Client), // OAuth2客户端
|
||||
|
||||
}
|
||||
|
||||
if err := client.MySQL.AutoMigrate(dbs...); err != nil {
|
||||
|
@ -2,7 +2,7 @@ package initialize
|
||||
|
||||
// InitSystem 初始化系统
|
||||
func InitSystem() {
|
||||
initLocaConfig() // 初始化本地配置
|
||||
initLocaConfig() // 初始化配置
|
||||
initClient() // 初始化连接池等信息
|
||||
databaseTable() // 初始化数据库表信息
|
||||
}
|
||||
|
59
main.go
Normal file
59
main.go
Normal file
@ -0,0 +1,59 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"Lee-WineList/config"
|
||||
"Lee-WineList/core"
|
||||
"Lee-WineList/initialize"
|
||||
appRoute "Lee-WineList/router"
|
||||
"fmt"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"github.com/gin-gonic/gin"
|
||||
"golang.org/x/sync/errgroup"
|
||||
"net/http"
|
||||
"time"
|
||||
)
|
||||
|
||||
var g errgroup.Group
|
||||
|
||||
// 系统初始化
|
||||
func init() {
|
||||
initialize.InitSystem() // 初始化系统配置
|
||||
//oauth2.InitOAuth2Server() // 初始化OAuth2服务
|
||||
}
|
||||
|
||||
// 启动入口
|
||||
func main() {
|
||||
// 强制日志颜色化
|
||||
gin.ForceConsoleColor()
|
||||
// 定义启动入口
|
||||
|
||||
app := &http.Server{
|
||||
Addr: fmt.Sprintf(":%d", config.Scd.Api.Port),
|
||||
Handler: api(),
|
||||
ReadTimeout: 5 * time.Second,
|
||||
WriteTimeout: 1 * time.Minute,
|
||||
}
|
||||
// 启动项目
|
||||
g.Go(func() error {
|
||||
return app.ListenAndServe()
|
||||
})
|
||||
if err := g.Wait(); err != nil {
|
||||
log.Panicf("启动失败,错误信息:%s", err.Error())
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// 生成接口服务
|
||||
func api() http.Handler {
|
||||
app := gin.New()
|
||||
app.Use(gin.Recovery())
|
||||
// 开启自定义请求方式不允许处理函数
|
||||
app.HandleMethodNotAllowed = true
|
||||
// 处理请求方式不对
|
||||
app.NoMethod(core.NoMethodHandler())
|
||||
// 404返回数据
|
||||
app.NoRoute(core.NoRouteHandler())
|
||||
// 初始化路由
|
||||
appRoute.InitRoute(app.Group(config.Scd.Api.Prefix))
|
||||
return app
|
||||
}
|
21
middleware/cors.go
Normal file
21
middleware/cors.go
Normal file
@ -0,0 +1,21 @@
|
||||
package middleware
|
||||
|
||||
import (
|
||||
"github.com/gin-gonic/gin"
|
||||
"net/http"
|
||||
)
|
||||
|
||||
func Cors() gin.HandlerFunc {
|
||||
return func(c *gin.Context) {
|
||||
c.Writer.Header().Set("Access-Control-Allow-Origin", "*")
|
||||
c.Writer.Header().Set("Access-Control-Allow-Credentials", "true")
|
||||
c.Writer.Header().Set("Access-Control-Allow-Headers", "Content-Type, Content-Length, Accept-Encoding, X-CSRF-Token, Authorization, accept, origin, Cache-Control, X-Requested-With")
|
||||
c.Writer.Header().Set("Access-Control-Allow-Methods", "POST, OPTIONS, GET, PUT,DELETE")
|
||||
c.Header("Access-Control-Allow-Credentials", "true")
|
||||
if c.Request.Method == "OPTIONS" {
|
||||
c.AbortWithStatus(http.StatusNoContent)
|
||||
return
|
||||
}
|
||||
c.Next()
|
||||
}
|
||||
}
|
5
model/cache/user.go
vendored
5
model/cache/user.go
vendored
@ -4,9 +4,8 @@ import "encoding/json"
|
||||
|
||||
// UserInfo 登录用的用户信息结构体
|
||||
type UserInfo struct {
|
||||
UserType string `json:"userType"` // 用户类型
|
||||
RoleCodes string `json:"roleCodes"` // 角色代码
|
||||
UserId string `json:"userId"` // 用户Id
|
||||
UserType string `json:"userType"` // 用户类型
|
||||
UserId int `json:"userId"` // 用户Id
|
||||
}
|
||||
|
||||
// String 实现Stringer接口
|
||||
|
@ -1,8 +0,0 @@
|
||||
package entity
|
||||
|
||||
import "Lee-WineList/common/types"
|
||||
|
||||
type Category struct {
|
||||
types.BaseDbModel
|
||||
Name string `gorm:"column:name;type:varchar(255);comment:分类名;NOT NULL" json:"name"`
|
||||
}
|
14
model/entity/material.go
Normal file
14
model/entity/material.go
Normal file
@ -0,0 +1,14 @@
|
||||
package entity
|
||||
|
||||
import "Lee-WineList/common/types"
|
||||
|
||||
type Material struct {
|
||||
types.BaseDbModel
|
||||
Name string `gorm:"column:name;type:varchar(255);comment:材料名;NOT NULL" json:"name"`
|
||||
ML string `gorm:"column:ml;type:int(11) unsigned;comment:毫升;NOT NULL" json:"ml"`
|
||||
WindId int `gorm:"column:wine_id;type:int(11) unsigned;comment:酒ID;NOT NULL" json:"wine_id"`
|
||||
}
|
||||
|
||||
func (Material) TableName() string {
|
||||
return "materials"
|
||||
}
|
@ -1,17 +1,20 @@
|
||||
package entity
|
||||
|
||||
import (
|
||||
"Lee-WineList/common/constant"
|
||||
"Lee-WineList/common/types"
|
||||
)
|
||||
|
||||
// User 普通用户表
|
||||
type User struct {
|
||||
types.BaseDbModel
|
||||
Phone string `json:"phone" gorm:"index:deleted,unique;type:varchar(255) not null comment '手机号'"`
|
||||
UnionId string `json:"union_id" gorm:"type:varchar(255) comment '微信UnionId'"`
|
||||
OpenId string `json:"open_id" gorm:"type:varchar(255) comment '微信OpenId'"`
|
||||
Nickname string `json:"nickname" gorm:"type:varchar(255) comment '昵称'"`
|
||||
Avatar string `json:"avatar" gorm:"type:varchar(255) comment '头像'"`
|
||||
Phone string `json:"phone" gorm:"index:deleted,unique;type:varchar(255) not null comment '手机号'"`
|
||||
WechatUnionId *string `json:"wechat_union_id" gorm:"type:varchar(255) comment '微信UnionId'"`
|
||||
WechatOpenId *string `json:"wechat_open_id" gorm:"type:varchar(255) comment '微信OpenId'"`
|
||||
Nickname string `json:"nickname" gorm:"type:varchar(255) comment '昵称'"`
|
||||
Avatar string `json:"avatar" gorm:"type:varchar(255) comment '头像'"`
|
||||
Sex constant.UserSex `json:"sex" gorm:"type:int; default 0; not null comment 性别"` // 1男2女
|
||||
Status constant.UserStatus `json:"status" gorm:"type:enum('NORMAL','DISABLE'); default:'NORMAL'; not null; comment:'状态 NORMAL-正常;DISABLE-禁用'"`
|
||||
}
|
||||
|
||||
func (User) TableName() string {
|
||||
|
@ -4,12 +4,19 @@ import "Lee-WineList/common/types"
|
||||
|
||||
// Wine 酒
|
||||
type Wine struct {
|
||||
types.BaseDbModel
|
||||
Name string `gorm:"column:name;type:varchar(255);comment:酒名;NOT NULL" json:"name"`
|
||||
ChineseName string `gorm:"column:chinese_name;type:varchar(255);comment:中文酒名;NOT NULL" json:"chinese_name"`
|
||||
Ingredients string `gorm:"column:ingredients;type:varchar(255);comment:配料;NOT NULL" json:"ingredients"`
|
||||
Quote string `gorm:"column:quote;type:varchar(255);comment:引用;NOT NULL" json:"quote"`
|
||||
CategoryId uint `gorm:"column:category_id;type:int(11) unsigned;comment:分类ID;NOT NULL" json:"category_id"`
|
||||
Steps string `gorm:"column:steps;type:varchar(255);comment:步骤;NOT NULL" json:"steps"`
|
||||
Context string `gorm:"column:context;type:varchar(255);comment:酒文;NOT NULL" json:"context"`
|
||||
types.Model
|
||||
WineId int `gorm:"column:wine_id;type:int(11) unsigned;primarykey;comment:酒ID;NOT NULL" json:"wine_id"`
|
||||
Name string `gorm:"column:name;type:varchar(255);comment:酒名;NOT NULL" json:"name"`
|
||||
ChineseName string `gorm:"column:chinese_name;type:varchar(255);comment:中文酒名;NOT NULL" json:"chinese_name"`
|
||||
Quote string `gorm:"column:quote;type:varchar(255);comment:引用;NOT NULL" json:"quote"`
|
||||
Category string `gorm:"column:category;type:varchar(255);comment:分类;NOT NULL" json:"category"`
|
||||
Steps string `gorm:"column:steps;type:varchar(255);comment:步骤;NOT NULL" json:"steps"`
|
||||
Context string `gorm:"column:context;type:varchar(255);comment:酒文;NOT NULL" json:"context"`
|
||||
Materials []Material `gorm:"many2many:wine_materials"`
|
||||
UserId int `gorm:"column:user_id;type:int(11) unsigned;comment:用户ID;NOT NULL" json:"user_id"`
|
||||
}
|
||||
|
||||
// TableName 设置表名
|
||||
func (Wine) TableName() string {
|
||||
return "wines"
|
||||
}
|
||||
|
@ -1,12 +1,16 @@
|
||||
package param
|
||||
|
||||
import "Lee-WineList/common/constant"
|
||||
|
||||
// Login 用户登录入参
|
||||
type Login struct {
|
||||
VerifyId string `json:"verifyId" form:"verifyId"` // 验证Id
|
||||
VerifyCode string `json:"verifyCode" form:"verifyCode"` // 验证码
|
||||
Username string `json:"username" form:"username" binding:"required"` // 邮箱或手机号
|
||||
Password string `json:"password" form:"password"` // 密码
|
||||
Code string `json:"code" form:"code"` // 微信小程序登录code
|
||||
Username string `json:"username" form:"username" binding:"required"` // 邮箱或手机号
|
||||
Password string `json:"password" form:"password"` // 密码
|
||||
TypeCode constant.LoginType `json:"type" form:"type" binding:"required"` // 登录方式,默认为空,可选值参见自定义类型
|
||||
UserIdentity constant.UserIdentity `json:"identity" form:"identity" binding:"required"` // 用户身份,默认为空,可选值参见自定义类型
|
||||
InviteCode string `json:"invite_code" form:"invite_code"` // 邀请码
|
||||
NickName string `json:"nickName" form:"nickName"` // 微信昵称
|
||||
AvatarUrl string `json:"avatarUrl" form:"avatarUrl"` // 微信头像
|
||||
}
|
||||
|
||||
// RefreshToken 刷新Token入参
|
||||
|
@ -1,23 +1,29 @@
|
||||
package param
|
||||
|
||||
import (
|
||||
"Lee-WineList/common/constant"
|
||||
)
|
||||
|
||||
// BindingWeChat 绑定微信
|
||||
type BindingWeChat struct {
|
||||
Code string `json:"code" form:"code" binding:"required"` // 微信code
|
||||
}
|
||||
|
||||
//GetUserList 获取普通用户
|
||||
type GetUserList struct {
|
||||
page
|
||||
Phone string `json:"phone" form:"phone"` // 手机号
|
||||
Status string `json:"status" form:"status" binding:"oneof='' NORMAL DISABLE"` // 用户状态
|
||||
StartAt string `json:"startAt" form:"startAt"` // 开始时间
|
||||
EndAt string `json:"endAt" form:"endAt"` // 结束时间
|
||||
Name string `json:"name" form:"name"` //用户名
|
||||
}
|
||||
|
||||
// ChangeUserInfo 修改普通用户信息
|
||||
type ChangeUserInfo struct {
|
||||
Nickname string `json:"nickname" form:"nickname"` // 昵称
|
||||
Avatar string `json:"avatar" form:"avatar"` // 头像
|
||||
Birthday string `json:"birthday" form:"birthday"` // 生日
|
||||
Nickname string `json:"nickname" form:"nickname"` // 昵称
|
||||
Avatar string `json:"avatar" form:"avatar"` // 头像
|
||||
Sex constant.UserSex `json:"sex" form:"sex"` // 性别
|
||||
}
|
||||
|
||||
// ChangePassword 修改密码
|
||||
@ -29,8 +35,10 @@ type ChangePassword struct {
|
||||
|
||||
// SaveUser 保存用户信息
|
||||
type SaveUser struct {
|
||||
Id int `json:"id" form:"id"` // 用户ID
|
||||
Username string `json:"username" form:"username"` // 用户名
|
||||
Nickname string `json:"nickname" form:"nickname"` // 昵称
|
||||
Password string `json:"password" form:"password"` // 密码
|
||||
Id string `json:"id" form:"id"` // 用户ID
|
||||
Username string `json:"username" form:"username"` // 用户名
|
||||
Nickname string `json:"nickname" form:"nickname"` // 昵称
|
||||
Password string `json:"password" form:"password"` // 密码
|
||||
Phone string `json:"phone" form:"phone"`
|
||||
Status constant.UserStatus `json:"status" form:"status" binding:"oneof=NORMAL DISABLE"` // 用户状态
|
||||
}
|
||||
|
@ -1,14 +1,15 @@
|
||||
package param
|
||||
|
||||
import "Lee-WineList/common/types"
|
||||
|
||||
type Wine struct {
|
||||
types.BaseDbModel
|
||||
Name string `gorm:"column:name;type:varchar(255);comment:酒名;NOT NULL" json:"name"`
|
||||
ChineseName string `gorm:"column:chinese_name;type:varchar(255);comment:中文酒名;NOT NULL" json:"chinese_name"`
|
||||
Ingredients string `json:"ingredients"`
|
||||
Quote string `gorm:"column:quote;type:varchar(255);comment:引用;NOT NULL" json:"quote"`
|
||||
CategoryId uint `gorm:"column:category_id;type:int(11) unsigned;comment:分类ID;NOT NULL" json:"category_id"`
|
||||
Steps string `gorm:"column:steps;type:varchar(255);comment:步骤;NOT NULL" json:"steps"`
|
||||
Context string `gorm:"column:context;type:varchar(255);comment:酒文;NOT NULL" json:"context"`
|
||||
type GetWineList struct {
|
||||
page
|
||||
Category string `json:"category" form:"category"` // 分类
|
||||
UserId int `json:"userId" form:"userId"` // 用户ID
|
||||
}
|
||||
|
||||
type GetWineListByUser struct {
|
||||
page
|
||||
Category string `json:"category" form:"category"` // 分类
|
||||
UserId int `json:"userId" form:"userId"` // 用户ID
|
||||
}
|
||||
|
||||
type AddWine struct{}
|
||||
|
@ -1,22 +0,0 @@
|
||||
package resp
|
||||
|
||||
// Code2Session 用户登录凭证校验模型
|
||||
type Code2Session struct {
|
||||
Code string
|
||||
AppId string
|
||||
AppSecret string
|
||||
}
|
||||
|
||||
// Code2SessionResult 凭证校验后返回的JSON数据包模型
|
||||
type Code2SessionResult struct {
|
||||
OpenId string `json:"openid"`
|
||||
SessionKey string `json:"session_key"`
|
||||
UnionId string `json:"unionid"`
|
||||
ErrCode uint `json:"errcode"`
|
||||
ErrMsg string `json:"errmsg"`
|
||||
}
|
||||
|
||||
// UserInfo 用户信息,OpenID用户唯一标识
|
||||
type UserInfo struct {
|
||||
OpenId string `json:"openId"`
|
||||
}
|
38
model/vo/user.go
Normal file
38
model/vo/user.go
Normal file
@ -0,0 +1,38 @@
|
||||
package vo
|
||||
|
||||
import (
|
||||
"Lee-WineList/common/constant"
|
||||
"Lee-WineList/common/types"
|
||||
"Lee-WineList/model/entity"
|
||||
"Lee-WineList/utils"
|
||||
)
|
||||
|
||||
// UserVO 管理员信息
|
||||
type UserVO struct {
|
||||
Id int `json:"id"`
|
||||
Nickname string `json:"nickname"`
|
||||
Username string `json:"username"`
|
||||
Phone string `json:"phone"`
|
||||
Status constant.UserStatus `json:"status"`
|
||||
Sex constant.UserSex `json:"sex"`
|
||||
Avatar string `json:"avatar"`
|
||||
CreatedAt types.DateTime `json:"createdAt"`
|
||||
}
|
||||
|
||||
// ParseOrdinary 转换为VO
|
||||
func (auv *UserVO) ParseOrdinary(u entity.User) {
|
||||
auv.Id = u.Id
|
||||
auv.Phone = utils.Desensitization().Phone(u.Phone)
|
||||
auv.Nickname = u.Nickname
|
||||
auv.Status = u.Status
|
||||
auv.Sex = u.Sex
|
||||
auv.Avatar = u.Avatar
|
||||
auv.CreatedAt = u.CreatedAt
|
||||
}
|
||||
|
||||
// UserMiniVO 简要信息
|
||||
type UserMiniVO struct {
|
||||
Id string `json:"id"`
|
||||
Nickname string `json:"nickname"`
|
||||
Avatar string `json:"avatar"`
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package resp
|
||||
package vo
|
||||
|
||||
import "Lee-WineList/common/types"
|
||||
|
166
oauth2/handle/oauth2.go
Normal file
166
oauth2/handle/oauth2.go
Normal file
@ -0,0 +1,166 @@
|
||||
package handle
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/common/constant"
|
||||
"Lee-WineList/model/cache"
|
||||
"Lee-WineList/model/entity"
|
||||
"Lee-WineList/repository"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"github.com/go-oauth2/oauth2/v4"
|
||||
"github.com/go-oauth2/oauth2/v4/errors"
|
||||
"net/http"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
// UserAuthorizationHandler 获取用户Id
|
||||
func UserAuthorizationHandler(w http.ResponseWriter, r *http.Request) (userId string, err error) {
|
||||
loginType := constant.LoginType(r.FormValue("type")) // 登录类型
|
||||
userIdentity := constant.UserIdentity(r.FormValue("identity")) // 身份类型
|
||||
account := r.FormValue("username") // 用户传入账号(或者授权Code)
|
||||
nikeName := r.FormValue("nickName") // 昵称
|
||||
avatarUrl := r.FormValue("avatarUrl") // 头像
|
||||
|
||||
log.Debugf("预处理用户登录请求,身份类型: %v => 登录类型: %s => 账号: %v", userIdentity, loginType, account)
|
||||
|
||||
// 普通用户
|
||||
userId, err = getUser(account, loginType, nikeName, avatarUrl)
|
||||
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
atoi, _ := strconv.Atoi(userId)
|
||||
// 组装缓存用户信息
|
||||
m := cache.UserInfo{
|
||||
UserId: atoi,
|
||||
UserType: userIdentity.String(),
|
||||
}
|
||||
userInfo, err := m.String()
|
||||
if err != nil {
|
||||
err = errors.New("登录失败,请联系管理员")
|
||||
return
|
||||
}
|
||||
if err = client.Redis.Set(context.Background(), fmt.Sprintf("%s%v", constant.OAuth2UserCacheKey, userId), userInfo, time.Hour*24*7).Err(); err != nil {
|
||||
log.Errorf("缓存用户信息失败,用户ID:%v,错误信息:%s", userId, err.Error())
|
||||
err = errors.New("登录失败,请联系管理员")
|
||||
return
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// LoginWithPassword 账号密码登录模式
|
||||
func LoginWithPassword(ctx context.Context, clientId, userId, password string) (userID string, err error) {
|
||||
log.Debugf("[%v]处理登录请求,用户Id:%s --> %s", clientId, userId, password)
|
||||
|
||||
userID = userId
|
||||
return
|
||||
}
|
||||
|
||||
// CheckClient 检查是否允许该客户端通过该授权模式请求令牌
|
||||
func CheckClient(clientID string, grant oauth2.GrantType) (allowed bool, err error) {
|
||||
// 解出租户Id和传入的客户端Id
|
||||
c := entity.OAuth2Client{ClientId: clientID}
|
||||
|
||||
// 查询客户端配置信息
|
||||
if err = repository.OAuth2Client().FindOne(&c); err != nil {
|
||||
log.Errorf("客户端信息查询失败: %v", err.Error())
|
||||
err = errors.New("客户端信息查询失败: " + err.Error())
|
||||
allowed = false
|
||||
return
|
||||
}
|
||||
// 判断是否包含授权范围
|
||||
allowed = strings.Contains(c.Grant, string(grant))
|
||||
if !allowed {
|
||||
err = errors.New("不受允许的grant_type")
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// ExtensionFields 自定义响应Token的扩展字段
|
||||
func ExtensionFields(ti oauth2.TokenInfo) (fieldsValue map[string]any) {
|
||||
fieldsValue = map[string]any{}
|
||||
fieldsValue["license"] = "Made By Lee"
|
||||
|
||||
// 取出用户信息
|
||||
var userInfo entity.User
|
||||
|
||||
userInfo.Id, _ = strconv.Atoi(ti.GetUserID())
|
||||
//if err := repository.User().GetUser(&userInfo); err != nil {
|
||||
// return
|
||||
//}
|
||||
repository.User().GetUser(&userInfo)
|
||||
fieldsValue["newUser"] = time.Now().Sub(userInfo.CreatedAt.ToTime()).Minutes() <= 1
|
||||
|
||||
fieldsValue["nickname"] = userInfo.Nickname
|
||||
fieldsValue["phone"] = userInfo.Phone
|
||||
fieldsValue["userId"] = userInfo.Id
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// ResponseToken 返回Token生成结果
|
||||
func ResponseToken(w http.ResponseWriter, data map[string]any, header http.Header, statusCode ...int) error {
|
||||
log.Debugf("返回Token原始数据: %+v", data)
|
||||
type response struct {
|
||||
Code int `json:"code"`
|
||||
Data map[string]any `json:"data"`
|
||||
Msg string `json:"message"`
|
||||
}
|
||||
|
||||
status := http.StatusOK
|
||||
msg := "login success"
|
||||
if len(statusCode) > 0 && statusCode[0] > 0 {
|
||||
status = statusCode[0]
|
||||
msg = fmt.Sprintf("%v", data["error_description"])
|
||||
// 处理特殊返回 - 刷新Token到期了
|
||||
switch data["error"] {
|
||||
case "invalid_grant":
|
||||
msg = "登录已过期,请重新授权登录"
|
||||
case "invalid_request":
|
||||
msg = "登录参数错误"
|
||||
default:
|
||||
log.Errorf("收到未定义的登录错误: %v", data["error_description"])
|
||||
}
|
||||
data = nil
|
||||
}
|
||||
|
||||
res := response{
|
||||
Code: status,
|
||||
Msg: msg,
|
||||
Data: data,
|
||||
}
|
||||
|
||||
jsonBytes, err := json.Marshal(res)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
w.Header().Set("Content-Type", "application/json;charset=UTF-8")
|
||||
w.Header().Set("Cache-Control", "no-store")
|
||||
w.Header().Set("Pragma", "no-cache")
|
||||
|
||||
for key := range header {
|
||||
w.Header().Set(key, header.Get(key))
|
||||
}
|
||||
|
||||
w.WriteHeader(status)
|
||||
_, err = w.Write(jsonBytes)
|
||||
if err != nil {
|
||||
log.Errorf("返回Token失败: %v", err.Error())
|
||||
return err
|
||||
}
|
||||
return err
|
||||
}
|
||||
|
||||
// InternalErrorHandler 自定义内部错误处理
|
||||
func InternalErrorHandler(err error) (re *errors.Response) {
|
||||
re = errors.NewResponse(err, http.StatusUnauthorized)
|
||||
re.Description = err.Error()
|
||||
return
|
||||
}
|
65
oauth2/handle/token_gen.go
Normal file
65
oauth2/handle/token_gen.go
Normal file
@ -0,0 +1,65 @@
|
||||
package handle
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/common/constant"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"github.com/go-oauth2/oauth2/v4"
|
||||
"github.com/google/uuid"
|
||||
"strings"
|
||||
)
|
||||
|
||||
func NewAccessGenerate() *AccessGenerate {
|
||||
return &AccessGenerate{}
|
||||
}
|
||||
|
||||
type AccessGenerate struct {
|
||||
}
|
||||
|
||||
// Token 手动实现Token生成,直接生成UUID,替换掉自带的那个憨得一批的长长的字符串
|
||||
func (ag *AccessGenerate) Token(ctx context.Context, data *oauth2.GenerateBasic, isGenRefresh bool) (string, string, error) {
|
||||
u, _ := uuid.NewUUID()
|
||||
access := strings.ReplaceAll(u.String(), "-", "")
|
||||
|
||||
refresh := ""
|
||||
if isGenRefresh {
|
||||
u, _ = uuid.NewUUID()
|
||||
refresh = strings.ReplaceAll(u.String(), "-", "")
|
||||
}
|
||||
// 生成新的,清理掉旧的
|
||||
ag.clearOldToken(ctx, data.UserID)
|
||||
// 返回结果
|
||||
return access, refresh, nil
|
||||
}
|
||||
|
||||
// 清理掉旧的Token和RefreshToken
|
||||
func (ag *AccessGenerate) clearOldToken(ctx context.Context, userId string) {
|
||||
rdsKey := constant.OAuth2RedisKey + "*-*"
|
||||
// 获取所有符合条件的Key
|
||||
keys, err := client.Redis.Keys(ctx, rdsKey).Result()
|
||||
if err != nil {
|
||||
log.Errorf("清理失败,跳过清理")
|
||||
return
|
||||
}
|
||||
for _, key := range keys {
|
||||
dataStr, err := client.Redis.Get(ctx, key).Result()
|
||||
if err != nil {
|
||||
continue
|
||||
}
|
||||
var m map[string]any
|
||||
if err = json.Unmarshal([]byte(dataStr), &m); err != nil {
|
||||
continue
|
||||
}
|
||||
// 找到匹配的数据
|
||||
if m["UserID"] == userId {
|
||||
// 删除AccessToken
|
||||
client.Redis.Del(ctx, fmt.Sprintf("%v%v", constant.OAuth2RedisKey, m["Access"]))
|
||||
client.Redis.Del(ctx, fmt.Sprintf("%v%v", constant.OAuth2RedisKey, m["Refresh"]))
|
||||
client.Redis.Del(ctx, key)
|
||||
continue
|
||||
}
|
||||
}
|
||||
}
|
68
oauth2/handle/user.go
Normal file
68
oauth2/handle/user.go
Normal file
@ -0,0 +1,68 @@
|
||||
package handle
|
||||
|
||||
import (
|
||||
"Lee-WineList/common/constant"
|
||||
"Lee-WineList/model/entity"
|
||||
"Lee-WineList/repository"
|
||||
"Lee-WineList/utils"
|
||||
"errors"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"strconv"
|
||||
)
|
||||
|
||||
// 获取普通用户信息
|
||||
func getUser(account string, loginType constant.LoginType, nikeName string, avatarUrl string) (userId string, err error) {
|
||||
// 根据登录类型获取用户信息
|
||||
|
||||
// 定义微信小程序信息
|
||||
//var unionId, openId, sessionKey string
|
||||
var mobile string
|
||||
// 定义用户信息
|
||||
var user entity.User
|
||||
switch loginType {
|
||||
case constant.LoginTypeWeChatMiniApp:
|
||||
mobile, err = utils.WeChatUtils().GetPhoneNumber(account)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
if mobile == "" {
|
||||
err = errors.New("获取手机号失败")
|
||||
return
|
||||
}
|
||||
user.Phone = mobile
|
||||
user.Nickname = nikeName
|
||||
user.Avatar = avatarUrl
|
||||
default:
|
||||
user.Phone = account
|
||||
user.Nickname = nikeName
|
||||
user.Avatar = avatarUrl
|
||||
}
|
||||
|
||||
// 查询用户信息
|
||||
if err = repository.User().GetOrCreate(&user); err != nil {
|
||||
log.Errorf("获取用户信息或创建用户失败,错误信息:%s", err.Error())
|
||||
err = errors.New("登录失败,请联系管理员")
|
||||
return
|
||||
}
|
||||
|
||||
// 校验用户状态
|
||||
if user.Status == constant.UserStatusDisabled {
|
||||
err = errors.New("账户已被禁用")
|
||||
return
|
||||
}
|
||||
|
||||
// 异步缓存小程序SessionKey
|
||||
//go func() {
|
||||
// if loginType == constant.LoginTypeWeChatMiniApp {
|
||||
// // 缓存SessionKey
|
||||
// if client.Redis.Set(context.Background(), constant.WeChatSessionKey+user.Id, sessionKey, 3*24*time.Hour).Err() != nil {
|
||||
// log.Errorf("缓存SessionKey失败,用户Id:%s", user.Id)
|
||||
// }
|
||||
// }
|
||||
//}()
|
||||
|
||||
// 返回用户Id
|
||||
userId = strconv.Itoa(user.Id)
|
||||
|
||||
return
|
||||
}
|
74
oauth2/server.go
Normal file
74
oauth2/server.go
Normal file
@ -0,0 +1,74 @@
|
||||
package oauth2
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/common/constant"
|
||||
"Lee-WineList/model/entity"
|
||||
"Lee-WineList/oauth2/handle"
|
||||
"Lee-WineList/repository"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"github.com/go-oauth2/oauth2/v4/manage"
|
||||
"github.com/go-oauth2/oauth2/v4/models"
|
||||
"github.com/go-oauth2/oauth2/v4/server"
|
||||
"github.com/go-oauth2/oauth2/v4/store"
|
||||
od "github.com/go-oauth2/redis/v4"
|
||||
"time"
|
||||
)
|
||||
|
||||
var OAuthServer *server.Server // Oauth服务
|
||||
|
||||
// InitOAuth2Server 初始化OAuth2服务端
|
||||
func InitOAuth2Server() {
|
||||
manager := manage.NewDefaultManager()
|
||||
// 配置信息
|
||||
cfg := &manage.Config{
|
||||
AccessTokenExp: time.Hour * 3, // 访问令牌过期时间,三小时
|
||||
RefreshTokenExp: time.Hour * 24 * 7, // 更新令牌过期时间,一周
|
||||
IsGenerateRefresh: true, // 是否生成新的更新令牌
|
||||
}
|
||||
// 设置密码模式的配置参数
|
||||
manager.SetPasswordTokenCfg(cfg)
|
||||
|
||||
manager.MapTokenStorage(od.NewRedisStoreWithCli(client.Redis, constant.OAuth2RedisKey))
|
||||
// 生成Token方式
|
||||
manager.MapAccessGenerate(handle.NewAccessGenerate())
|
||||
|
||||
// 配置客户端
|
||||
clientStore := store.NewClientStore()
|
||||
// 从数据库查询所有client信息
|
||||
var clients []entity.OAuth2Client
|
||||
if err := repository.OAuth2Client().FinAll(&clients); err != nil {
|
||||
log.Panicf("OAuth2服务启动失败[Client信息拉取失败]: %v", err.Error())
|
||||
}
|
||||
if len(clients) == 0 {
|
||||
log.Panic("未配置OAuth2客户端信息")
|
||||
}
|
||||
// 组装数据
|
||||
for _, c := range clients {
|
||||
_ = clientStore.Set(c.ClientId, &models.Client{
|
||||
ID: c.ClientId,
|
||||
Secret: c.ClientSecret,
|
||||
})
|
||||
}
|
||||
log.Debug("客户端信息初始化完成")
|
||||
manager.MapClientStorage(clientStore)
|
||||
|
||||
srv := server.NewServer(server.NewConfig(), manager)
|
||||
// 设置密码登录模式处理逻辑
|
||||
srv.SetPasswordAuthorizationHandler(handle.LoginWithPassword)
|
||||
|
||||
// 客户端ID和授权模式检查
|
||||
srv.SetClientAuthorizedHandler(handle.CheckClient)
|
||||
// 自定义响应Token的扩展字段
|
||||
srv.SetExtensionFieldsHandler(handle.ExtensionFields)
|
||||
// 自定义返回数据接口
|
||||
srv.SetResponseTokenHandler(handle.ResponseToken)
|
||||
// 自定义内部错误处理
|
||||
srv.SetInternalErrorHandler(handle.InternalErrorHandler)
|
||||
// 响应错误处理(支持自定义URI及错误明细)
|
||||
//srv.SetResponseErrorHandler(handle.ResponseErrorHandler)
|
||||
// 自定义解析用户Id函数
|
||||
srv.SetUserAuthorizationHandler(handle.UserAuthorizationHandler)
|
||||
|
||||
OAuthServer = srv
|
||||
}
|
9
repository/login.go
Normal file
9
repository/login.go
Normal file
@ -0,0 +1,9 @@
|
||||
package repository
|
||||
|
||||
type login struct {
|
||||
}
|
||||
|
||||
// Login ...
|
||||
func Login() *login {
|
||||
return &login{}
|
||||
}
|
23
repository/oauth2_client.go
Normal file
23
repository/oauth2_client.go
Normal file
@ -0,0 +1,23 @@
|
||||
package repository
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/model/entity"
|
||||
)
|
||||
|
||||
type oauth2Client struct{}
|
||||
|
||||
// OAuth2Client ...
|
||||
func OAuth2Client() *oauth2Client {
|
||||
return &oauth2Client{}
|
||||
}
|
||||
|
||||
// FinAll 查询所有客户端
|
||||
func (oauth2Client) FinAll(clients *[]entity.OAuth2Client) error {
|
||||
return client.MySQL.Find(&clients).Error
|
||||
}
|
||||
|
||||
// FindOne 查询某一个
|
||||
func (oauth2Client) FindOne(c *entity.OAuth2Client) error {
|
||||
return client.MySQL.Take(&c, c).Error
|
||||
}
|
@ -2,15 +2,10 @@ package repository
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/config"
|
||||
"Lee-WineList/model/entity"
|
||||
"Lee-WineList/model/resp"
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
"gorm.io/gorm"
|
||||
"net/http"
|
||||
)
|
||||
|
||||
type user struct {
|
||||
@ -26,54 +21,16 @@ func (user) GetUser(user *entity.User) (err error) {
|
||||
return client.MySQL.Take(&user, user).Error
|
||||
}
|
||||
|
||||
// Login Code登录
|
||||
func (u *user) Login(code string) *entity.User {
|
||||
var acsJson resp.Code2SessionResult
|
||||
acs := resp.Code2Session{
|
||||
Code: code,
|
||||
AppId: config.Scd.Tencent.MiniApp.AppId,
|
||||
AppSecret: config.Scd.Tencent.MiniApp.AppSecret,
|
||||
}
|
||||
api := "https://api.weixin.qq.com/sns/jscode2session?appid=%s&secret=%s&js_code=%s&grant_type=authorization_code"
|
||||
res, err := http.DefaultClient.Get(fmt.Sprintf(api, acs.AppId, acs.AppSecret, acs.Code))
|
||||
if err != nil {
|
||||
fmt.Println("微信登录凭证校验接口请求错误")
|
||||
return nil
|
||||
}
|
||||
if err := json.NewDecoder(res.Body).Decode(&acsJson); err != nil {
|
||||
fmt.Println("decoder error...")
|
||||
return nil
|
||||
}
|
||||
|
||||
// 查看用户是否已经存在
|
||||
rows := client.MySQL.Where("open_id = ?", acsJson.OpenId).First(&entity.User{}).RowsAffected
|
||||
if rows == 0 {
|
||||
// 不存在,添加用户
|
||||
fmt.Println(acsJson.OpenId)
|
||||
user := entity.User{
|
||||
OpenId: acsJson.OpenId,
|
||||
}
|
||||
row := client.MySQL.Create(&user).RowsAffected
|
||||
if row == 0 {
|
||||
fmt.Println("add app user error...")
|
||||
return nil
|
||||
}
|
||||
}
|
||||
return &entity.User{OpenId: acsJson.OpenId}
|
||||
}
|
||||
|
||||
// GetOrCreate 查询或创建用户
|
||||
func (user) GetOrCreate(user *entity.User) (err error) {
|
||||
err = client.MySQL.Take(&user, user).Error
|
||||
//err = client.MySQL.Take(&user, user).Error
|
||||
err = client.MySQL.Model(&user).Where("phone = ?", user.Phone).First(&user).Error
|
||||
if err == nil {
|
||||
return
|
||||
}
|
||||
// 如果是没查询到记录,则创建用户
|
||||
if err == gorm.ErrRecordNotFound {
|
||||
// 用户不存在,创建用户
|
||||
user.Nickname = "用户"
|
||||
//user.Avatar = "https://hyxc-mini.oss-cn-beijing.aliyuncs.com/application/resource/miniapp/index/index-more-love.png"
|
||||
user.Avatar = "https://hyxc-mini.oss-cn-beijing.aliyuncs.com/avatar/mona-loading-dark.gif"
|
||||
if err = client.MySQL.Create(&user).Error; err != nil {
|
||||
log.Errorf("账号创建失败: %v", err)
|
||||
err = errors.New("登录失败")
|
||||
@ -86,7 +43,7 @@ func (user) GetOrCreate(user *entity.User) (err error) {
|
||||
// CheckUnionIdIsExist 检查UnionId和OpenId是否存在
|
||||
func (user) CheckUnionIdIsExist(unionId, openId string) bool {
|
||||
var count int64
|
||||
err := client.MySQL.Model(&entity.User{}).Where("union_id = ? and open_id = ?", unionId, openId).Count(&count).Error
|
||||
err := client.MySQL.Model(&entity.User{}).Where("wechat_union_id = ? and wechat_open_id = ?", unionId, openId).Count(&count).Error
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
|
40
repository/wine.go
Normal file
40
repository/wine.go
Normal file
@ -0,0 +1,40 @@
|
||||
package repository
|
||||
|
||||
import (
|
||||
"Lee-WineList/client"
|
||||
"Lee-WineList/model/entity"
|
||||
"Lee-WineList/model/param"
|
||||
"git.echol.cn/loser/logger/log"
|
||||
)
|
||||
|
||||
type wine struct {
|
||||
}
|
||||
|
||||
// Wine ...
|
||||
func Wine() *wine {
|
||||
return &wine{}
|
||||
}
|
||||
|
||||
// GetWineList 获取酒单列表
|
||||
func (w *wine) GetWineList(p param.GetWineList) (wines []entity.Wine, err error) {
|
||||
db := client.MySQL.Model(&wines).Preload("Materials").Scopes(page(p.Current, p.Size))
|
||||
|
||||
if p.UserId != 0 {
|
||||
db = db.Where("user_id = ?", p.UserId)
|
||||
}
|
||||
if p.Category != "" {
|
||||
db = db.Where("category = ?", p.Category)
|
||||
}
|
||||
err = db.Find(&wines).Error
|
||||
if err != nil {
|
||||
log.Errorf("获取酒单列表失败:%s", err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (w *wine) Add(p param.AddWine) (err error) {
|
||||
|
||||
return
|
||||
}
|
@ -1,8 +1,7 @@
|
||||
package app
|
||||
package router
|
||||
|
||||
import (
|
||||
"Lee-WineList/api/app"
|
||||
"Lee-WineList/middleware"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
@ -10,6 +9,6 @@ import (
|
||||
func login(g *gin.RouterGroup) {
|
||||
// 登录相关接口
|
||||
g.POST("/token", app.LoginApi().Login)
|
||||
g.POST("/token/refresh", app.LoginApi().Refresh)
|
||||
g.POST("/token/logout", middleware.AuthorizeToken(), app.LoginApi().Logout)
|
||||
//g.POST("/token/refresh", app.LoginApi().Refresh)
|
||||
//g.POST("/token/logout", middleware.AuthorizeToken(), app.LoginApi().Logout)
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package app
|
||||
package router
|
||||
|
||||
import (
|
||||
"Lee-WineList/middleware"
|
||||
@ -9,4 +9,5 @@ import (
|
||||
func InitRoute(g *gin.RouterGroup) {
|
||||
login(g) // 登录相关路由
|
||||
user(g.Group("/user", middleware.AuthorizeToken())) // 用户相关路由
|
||||
wine(g.Group("/wine"))
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package app
|
||||
package router
|
||||
|
||||
import (
|
||||
"Lee-WineList/api/app"
|
10
router/wine.go
Normal file
10
router/wine.go
Normal file
@ -0,0 +1,10 @@
|
||||
package router
|
||||
|
||||
import (
|
||||
"Lee-WineList/api/app"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
func wine(g *gin.RouterGroup) {
|
||||
g.GET("", app.WineApi().GetList)
|
||||
}
|
71
utils/jwt.go
71
utils/jwt.go
@ -1,71 +0,0 @@
|
||||
package utils
|
||||
|
||||
import (
|
||||
"Lee-WineList/config"
|
||||
"time"
|
||||
|
||||
"github.com/golang-jwt/jwt"
|
||||
)
|
||||
|
||||
type JWT struct {
|
||||
claims jwt.MapClaims
|
||||
}
|
||||
|
||||
// GenerateToken 根据UserId生成并返回Token
|
||||
func GenerateToken(userId uint64) string {
|
||||
jwtConfig := config.Scd.JWT
|
||||
now := time.Now().Unix()
|
||||
claims := make(jwt.MapClaims)
|
||||
claims["exp"] = now + jwtConfig.AccessExpire
|
||||
claims["iat"] = now
|
||||
claims["rft"] = now + jwtConfig.RefreshAfter
|
||||
claims["userId"] = userId
|
||||
|
||||
token := jwt.New(jwt.SigningMethodHS256)
|
||||
token.Claims = claims
|
||||
tokenStr, _ := token.SignedString([]byte(jwtConfig.AccessSecret))
|
||||
|
||||
return tokenStr
|
||||
}
|
||||
|
||||
// ParseToken 解析Token
|
||||
func ParseToken(tokenStr string) (*JWT, error) {
|
||||
token, err := jwt.Parse(tokenStr, func(token *jwt.Token) (interface{}, error) {
|
||||
return []byte(config.Scd.JWT.AccessSecret), nil
|
||||
})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &JWT{claims: token.Claims.(jwt.MapClaims)}, nil
|
||||
}
|
||||
|
||||
// Valid 验证token是否有效
|
||||
func (jwt *JWT) Valid() bool {
|
||||
if err := jwt.claims.Valid(); err != nil {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// CheckRefresh 检查是否可以刷新
|
||||
func (jwt *JWT) CheckRefresh() bool {
|
||||
if time.Now().Unix() > jwt.GetRefreshTime() {
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
func (jwt *JWT) RefreshToken() string {
|
||||
return GenerateToken(jwt.GetUserId())
|
||||
}
|
||||
|
||||
// GetUserId 从Token中解析userId
|
||||
func (jwt *JWT) GetUserId() uint64 {
|
||||
return uint64(jwt.claims["userId"].(float64))
|
||||
}
|
||||
|
||||
// GetRefreshTime 从Token中解析refreshTime
|
||||
func (jwt *JWT) GetRefreshTime() int64 {
|
||||
return int64(jwt.claims["rft"].(float64))
|
||||
}
|
104
utils/timer/timed_task.go
Normal file
104
utils/timer/timed_task.go
Normal file
@ -0,0 +1,104 @@
|
||||
package timer
|
||||
|
||||
import (
|
||||
"github.com/robfig/cron/v3"
|
||||
"sync"
|
||||
)
|
||||
|
||||
type Timer interface {
|
||||
AddTaskByFunc(taskName string, spec string, task func(), option ...cron.Option) (cron.EntryID, error)
|
||||
AddTaskByJob(taskName string, spec string, job interface{ Run() }, option ...cron.Option) (cron.EntryID, error)
|
||||
FindCron(taskName string) (*cron.Cron, bool)
|
||||
StartTask(taskName string)
|
||||
StopTask(taskName string)
|
||||
Remove(taskName string, id int)
|
||||
Clear(taskName string)
|
||||
Close()
|
||||
}
|
||||
|
||||
// timer 定时任务管理
|
||||
type timer struct {
|
||||
taskList map[string]*cron.Cron
|
||||
sync.Mutex
|
||||
}
|
||||
|
||||
// AddTaskByFunc 通过函数的方法添加任务
|
||||
func (t *timer) AddTaskByFunc(taskName string, spec string, task func(), option ...cron.Option) (cron.EntryID, error) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
if _, ok := t.taskList[taskName]; !ok {
|
||||
t.taskList[taskName] = cron.New(option...)
|
||||
}
|
||||
id, err := t.taskList[taskName].AddFunc(spec, task)
|
||||
t.taskList[taskName].Start()
|
||||
return id, err
|
||||
}
|
||||
|
||||
// AddTaskByJob 通过接口的方法添加任务
|
||||
func (t *timer) AddTaskByJob(taskName string, spec string, job interface{ Run() }, option ...cron.Option) (cron.EntryID, error) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
if _, ok := t.taskList[taskName]; !ok {
|
||||
t.taskList[taskName] = cron.New(option...)
|
||||
}
|
||||
id, err := t.taskList[taskName].AddJob(spec, job)
|
||||
t.taskList[taskName].Start()
|
||||
return id, err
|
||||
}
|
||||
|
||||
// FindCron 获取对应taskName的cron 可能会为空
|
||||
func (t *timer) FindCron(taskName string) (*cron.Cron, bool) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
v, ok := t.taskList[taskName]
|
||||
return v, ok
|
||||
}
|
||||
|
||||
// StartTask 开始任务
|
||||
func (t *timer) StartTask(taskName string) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
if v, ok := t.taskList[taskName]; ok {
|
||||
v.Start()
|
||||
}
|
||||
}
|
||||
|
||||
// StopTask 停止任务
|
||||
func (t *timer) StopTask(taskName string) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
if v, ok := t.taskList[taskName]; ok {
|
||||
v.Stop()
|
||||
}
|
||||
}
|
||||
|
||||
// Remove 从taskName 删除指定任务
|
||||
func (t *timer) Remove(taskName string, id int) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
if v, ok := t.taskList[taskName]; ok {
|
||||
v.Remove(cron.EntryID(id))
|
||||
}
|
||||
}
|
||||
|
||||
// Clear 清除任务
|
||||
func (t *timer) Clear(taskName string) {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
if v, ok := t.taskList[taskName]; ok {
|
||||
v.Stop()
|
||||
delete(t.taskList, taskName)
|
||||
}
|
||||
}
|
||||
|
||||
// Close 释放资源
|
||||
func (t *timer) Close() {
|
||||
t.Lock()
|
||||
defer t.Unlock()
|
||||
for _, v := range t.taskList {
|
||||
v.Stop()
|
||||
}
|
||||
}
|
||||
func NewTimerTask() Timer {
|
||||
return &timer{taskList: make(map[string]*cron.Cron)}
|
||||
}
|
61
utils/timer/timed_task_test.go
Normal file
61
utils/timer/timed_task_test.go
Normal file
@ -0,0 +1,61 @@
|
||||
package timer
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
var job = mockJob{}
|
||||
|
||||
type mockJob struct{}
|
||||
|
||||
func (job mockJob) Run() {
|
||||
mockFunc()
|
||||
}
|
||||
func mockFunc() {
|
||||
time.Sleep(time.Second)
|
||||
fmt.Println("1s...")
|
||||
}
|
||||
func TestNewTimerTask(t *testing.T) {
|
||||
tm := NewTimerTask()
|
||||
_tm := tm.(*timer)
|
||||
{
|
||||
_, err := tm.AddTaskByFunc("func", "@every 1s", mockFunc)
|
||||
assert.Nil(t, err)
|
||||
_, ok := _tm.taskList["func"]
|
||||
if !ok {
|
||||
t.Error("no find func")
|
||||
}
|
||||
}
|
||||
{
|
||||
_, err := tm.AddTaskByJob("job", "@every 1s", job)
|
||||
assert.Nil(t, err)
|
||||
_, ok := _tm.taskList["job"]
|
||||
if !ok {
|
||||
t.Error("no find job")
|
||||
}
|
||||
}
|
||||
{
|
||||
_, ok := tm.FindCron("func")
|
||||
if !ok {
|
||||
t.Error("no find func")
|
||||
}
|
||||
_, ok = tm.FindCron("job")
|
||||
if !ok {
|
||||
t.Error("no find job")
|
||||
}
|
||||
_, ok = tm.FindCron("none")
|
||||
if ok {
|
||||
t.Error("find none")
|
||||
}
|
||||
}
|
||||
{
|
||||
tm.Clear("func")
|
||||
_, ok := tm.FindCron("func")
|
||||
if ok {
|
||||
t.Error("find func")
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user