From e9fdefd16241ebd1c7d51ce658b980a11949a740 Mon Sep 17 00:00:00 2001 From: Sam Date: Thu, 23 Dec 2021 17:29:36 +0800 Subject: [PATCH 01/93] [update] Bumped version (#1284) --- .github/ISSUE_TEMPLATE/bug-report.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/ISSUE_TEMPLATE/bug-report.yaml b/.github/ISSUE_TEMPLATE/bug-report.yaml index f799746c..be575c6d 100644 --- a/.github/ISSUE_TEMPLATE/bug-report.yaml +++ b/.github/ISSUE_TEMPLATE/bug-report.yaml @@ -45,6 +45,7 @@ body: label: go-cqhttp 版本 description: 选择正在使用的版本 (未列出的版本为已不支持,请更新到最新版本。) options: + - v1.0.0-beta8-fix2 - v1.0.0-beta8-fix1 - v1.0.0-beta8 - v1.0.0-beta7-fix2 From 0cc0a20848d5e861014379f639cfa4052cde377c Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 22 Jan 2022 21:51:20 +0800 Subject: [PATCH 02/93] .github: update bug-report template --- .github/ISSUE_TEMPLATE/bug-report.yaml | 21 ++++----------------- 1 file changed, 4 insertions(+), 17 deletions(-) diff --git a/.github/ISSUE_TEMPLATE/bug-report.yaml b/.github/ISSUE_TEMPLATE/bug-report.yaml index be575c6d..0aacee17 100644 --- a/.github/ISSUE_TEMPLATE/bug-report.yaml +++ b/.github/ISSUE_TEMPLATE/bug-report.yaml @@ -26,7 +26,9 @@ body: options: - label: "我已经仔细阅读上述教程和 [\"提问前需知\"](https://github.com/Mrs4s/go-cqhttp/issues/633)" required: true - - label: 我已知晓并同意,如果我不遵循以下格式提交 Issue,或者我使用的并非最新版本,或者我没有提供足够的环境信息,我的 Issue 可能会被无条件自动关闭或/并锁定。 + - label: "我已经使用 dev 分支版本测试过,问题依旧存在。" + required: true + - label: "我已经在 [Issue Tracker](……/) 中找过我要提出的问题,没有找到相同问题的ISSUE。" required: true - label: 我已知晓并同意,此处仅用于汇报程序中存在的问题。若这个 Issue 是关于其他非程序本身问题,则我的 Issue 可能会被无条件自动关闭或/并锁定。(这些问题应当在 Discussion 板块提出。) required: true @@ -39,25 +41,10 @@ body: 请根据实际使用环境修改以下信息。 # Env | go-cqhttp Version - - type: dropdown + - type: input id: env-gocq-ver attributes: label: go-cqhttp 版本 - description: 选择正在使用的版本 (未列出的版本为已不支持,请更新到最新版本。) - options: - - v1.0.0-beta8-fix2 - - v1.0.0-beta8-fix1 - - v1.0.0-beta8 - - v1.0.0-beta7-fix2 - - v1.0.0-beta7-fix1 - - v1.0.0-beta7 - - v1.0.0-beta6 - - v1.0.0-beta5 - - v1.0.0-beta4 - - v1.0.0-beta3 - - v1.0.0-beta2 - - v1.0.0-beta1 - - 更老的版本 validations: required: true From b0fb02e890c9afa69026ad21e2878e3c28db7170 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 30 Jan 2022 16:02:26 +0800 Subject: [PATCH 03/93] .github: update bug-report template --- .github/ISSUE_TEMPLATE/bug-report.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/ISSUE_TEMPLATE/bug-report.yaml b/.github/ISSUE_TEMPLATE/bug-report.yaml index 0aacee17..29fc048f 100644 --- a/.github/ISSUE_TEMPLATE/bug-report.yaml +++ b/.github/ISSUE_TEMPLATE/bug-report.yaml @@ -26,9 +26,9 @@ body: options: - label: "我已经仔细阅读上述教程和 [\"提问前需知\"](https://github.com/Mrs4s/go-cqhttp/issues/633)" required: true - - label: "我已经使用 dev 分支版本测试过,问题依旧存在。" + - label: "我已经使用 [dev分支版本](https://github.com/Mrs4s/go-cqhttp/actions/workflows/ci.yml) 测试过,问题依旧存在。" required: true - - label: "我已经在 [Issue Tracker](……/) 中找过我要提出的问题,没有找到相同问题的ISSUE。" + - label: "我已经在 [Issue Tracker](https://github.com/Mrs4s/go-cqhttp/actions/workflows/ci.yml) 中找过我要提出的问题,没有找到相同问题的ISSUE。" required: true - label: 我已知晓并同意,此处仅用于汇报程序中存在的问题。若这个 Issue 是关于其他非程序本身问题,则我的 Issue 可能会被无条件自动关闭或/并锁定。(这些问题应当在 Discussion 板块提出。) required: true From f8fa906a952dff1cb111c40411d1ae8632e83326 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 30 Jan 2022 16:04:53 +0800 Subject: [PATCH 04/93] .github: fix issue link --- .github/ISSUE_TEMPLATE/bug-report.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/ISSUE_TEMPLATE/bug-report.yaml b/.github/ISSUE_TEMPLATE/bug-report.yaml index 29fc048f..1cee16c7 100644 --- a/.github/ISSUE_TEMPLATE/bug-report.yaml +++ b/.github/ISSUE_TEMPLATE/bug-report.yaml @@ -28,7 +28,7 @@ body: required: true - label: "我已经使用 [dev分支版本](https://github.com/Mrs4s/go-cqhttp/actions/workflows/ci.yml) 测试过,问题依旧存在。" required: true - - label: "我已经在 [Issue Tracker](https://github.com/Mrs4s/go-cqhttp/actions/workflows/ci.yml) 中找过我要提出的问题,没有找到相同问题的ISSUE。" + - label: "我已经在 [Issue Tracker](https://github.com/Mrs4s/go-cqhttp/issues) 中找过我要提出的问题,没有找到相同问题的ISSUE。" required: true - label: 我已知晓并同意,此处仅用于汇报程序中存在的问题。若这个 Issue 是关于其他非程序本身问题,则我的 Issue 可能会被无条件自动关闭或/并锁定。(这些问题应当在 Discussion 板块提出。) required: true From 1a78a4809a412ddda63970bdc13789b2e2313892 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 9 Feb 2022 22:33:53 +0800 Subject: [PATCH 05/93] server/http: delete tab in default config Fixes #1362 --- docs/config.md | 7 ------- server/http.go | 4 ++-- 2 files changed, 2 insertions(+), 9 deletions(-) diff --git a/docs/config.md b/docs/config.md index 3bd13690..d352b61e 100644 --- a/docs/config.md +++ b/docs/config.md @@ -79,13 +79,6 @@ default-middlewares: &default frequency: 1 # 令牌回复频率, 单位秒 bucket: 1 # 令牌桶大小 -database: # 数据库相关设置 - leveldb: - # 是否启用内置leveldb数据库 - # 启用将会增加10-20MB的内存占用和一定的磁盘空间 - # 关闭将无法使用 撤回 回复 get_msg 等上下文相关功能 - enable: true - # 连接服务列表 servers: # HTTP 通信设置 diff --git a/server/http.go b/server/http.go index 7d696c52..0a73db8f 100644 --- a/server/http.go +++ b/server/http.go @@ -87,11 +87,11 @@ const httpDefault = ` post: # 反向HTTP POST地址列表 #- url: '' # 地址 # secret: '' # 密钥 - # max-retries: 3 # 最大重试,0 时禁用 + # max-retries: 3 # 最大重试,0 时禁用 # retries-interval: 1500 # 重试时间,单位毫秒,0 时立即 #- url: http://127.0.0.1:5701/ # 地址 # secret: '' # 密钥 - # max-retries: 10 # 最大重试,0 时禁用 + # max-retries: 10 # 最大重试,0 时禁用 # retries-interval: 1000 # 重试时间,单位毫秒,0 时立即 ` From 115a5f1da75db26e02d5efe346c35f34ddde3aca Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8D=83=E6=A9=98=20=E9=9B=AB=E9=9C=9E?= Date: Wed, 9 Feb 2022 23:55:39 +0800 Subject: [PATCH 06/93] fix: examine errors that have been ignored in the 'CQ:at' parser (#1363) #1332 --- coolq/cqcode.go | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 80d59136..7f95b1fc 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -954,7 +954,10 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou if qq == "all" { return message.AtAll(), nil } - t, _ := strconv.ParseInt(qq, 10, 64) + t, err := strconv.ParseInt(qq, 10, 64) + if err != nil { + return nil, err + } name := strings.TrimSpace(d["name"]) if len(name) > 0 { name = "@" + name From cf9fa71646747754cd445b94ba45b58bb33cadd3 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 11 Feb 2022 14:17:54 +0800 Subject: [PATCH 07/93] coolq: fix private reply id Fixes #1368 --- coolq/cqcode.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 7f95b1fc..c30de373 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -114,7 +114,7 @@ func ToArrayMessage(e []message.IMessageElement, source MessageSource) (r []glob if reply != nil && source.SourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) rid := int64(source.PrimaryID) - if rid == 0 { + if source.SourceType == MessageSourcePrivate { rid = replyElem.Sender } if replyElem.GroupID != 0 { @@ -280,7 +280,7 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. if reply != nil && source.SourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) rid := int64(source.PrimaryID) - if rid == 0 { + if source.SourceType == MessageSourcePrivate { rid = replyElem.Sender } if replyElem.GroupID != 0 { From baecc2f8e6b3f4889185da1d6bcb0b251b89f4b5 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 12 Feb 2022 16:18:54 +0800 Subject: [PATCH 08/93] dep: update MiraiGo For #1368 --- db/leveldb/leveldb.go | 2 +- go.mod | 2 +- go.sum | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/db/leveldb/leveldb.go b/db/leveldb/leveldb.go index cfe7716e..2d86dbb5 100644 --- a/db/leveldb/leveldb.go +++ b/db/leveldb/leveldb.go @@ -50,7 +50,7 @@ func init() { func (ldb *LevelDBImpl) Open() error { p := path.Join("data", "leveldb-v2") d, err := leveldb.OpenFile(p, &opt.Options{ - WriteBuffer: 128 * opt.KiB, + WriteBuffer: 32 * opt.KiB, }) if err != nil { return errors.Wrap(err, "open leveldb error") diff --git a/go.mod b/go.mod index 852d52af..0d4896d6 100644 --- a/go.mod +++ b/go.mod @@ -5,7 +5,7 @@ go 1.17 require ( github.com/Baozisoftware/qrcode-terminal-go v0.0.0-20170407111555-c0650d8dff0f github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220209092529-5d071b034c17 + github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/dustin/go-humanize v1.0.0 github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index ba462251..9c788da0 100644 --- a/go.sum +++ b/go.sum @@ -2,8 +2,8 @@ github.com/Baozisoftware/qrcode-terminal-go v0.0.0-20170407111555-c0650d8dff0f h github.com/Baozisoftware/qrcode-terminal-go v0.0.0-20170407111555-c0650d8dff0f/go.mod h1:4a58ifQTEe2uwwsaqbh3i2un5/CBPg+At/qHpt18Tmk= github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220209092529-5d071b034c17 h1:OQVnlWt5if0TOFoNGDjILazBjVTncSlPxGXabD+4MvE= -github.com/Mrs4s/MiraiGo v0.0.0-20220209092529-5d071b034c17/go.mod h1:rtKLkhMEi2YjsrXaNztT4uagUOPBxf6a+TNREkG097I= +github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb h1:nc96MkGgqa2iW8bMzFMj2mdT9LUJYgsdez30zwo8qxg= +github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb/go.mod h1:rtKLkhMEi2YjsrXaNztT4uagUOPBxf6a+TNREkG097I= github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956 h1:hnaAkKz4t+xpSNVp5mnuloRMd3Rj2Lfg5biZ3emv//c= github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From ba808fff1d35258ce49f3bb4b2b0ef0a522d7ba4 Mon Sep 17 00:00:00 2001 From: Lin <767763591@qq.com> Date: Sat, 12 Feb 2022 16:48:06 +0800 Subject: [PATCH 09/93] =?UTF-8?q?=E9=87=8D=E6=9E=84=EF=BC=9A=E9=80=82?= =?UTF-8?q?=E9=85=8D=E8=87=AA=E5=AE=9A=E4=B9=89QR=E5=B0=BA=E5=AF=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: wdvxdr --- cmd/gocq/login.go | 39 ++++++++++++++++++++++++++++++++------- go.mod | 5 ----- go.sum | 12 ------------ 3 files changed, 32 insertions(+), 24 deletions(-) diff --git a/cmd/gocq/login.go b/cmd/gocq/login.go index 80ac10bc..bc191461 100644 --- a/cmd/gocq/login.go +++ b/cmd/gocq/login.go @@ -3,13 +3,14 @@ package gocq import ( "bufio" "bytes" + "image" + "image/png" "os" "strings" "time" - qrcodeTerminal "github.com/Baozisoftware/qrcode-terminal-go" "github.com/Mrs4s/MiraiGo/client" - "github.com/gocq/qrcode" + "github.com/mattn/go-colorable" "github.com/pkg/errors" log "github.com/sirupsen/logrus" @@ -53,12 +54,36 @@ func commonLogin() error { return loginResponseProcessor(res) } -func qrcodeLogin() error { - rsp, err := cli.FetchQRCode() +func printQRCode(imgData []byte) { + const ( + black = "\033[48;5;0m \033[0m" + white = "\033[48;5;7m \033[0m" + ) + img, err := png.Decode(bytes.NewReader(imgData)) if err != nil { - return err + log.Panic(err) + } + data := img.(*image.Gray).Pix + bound := img.Bounds().Max.X + buf := make([]byte, 0, (bound*4+1)*(bound)) + i := 0 + for y := 0; y < bound; y++ { + i = y * bound + for x := 0; x < bound; x++ { + if data[i] != 255 { + buf = append(buf, white...) + } else { + buf = append(buf, black...) + } + i++ + } + buf = append(buf, '\n') } - fi, err := qrcode.Decode(bytes.NewReader(rsp.ImageData)) + _, _ = colorable.NewColorableStdout().Write(buf) +} + +func qrcodeLogin() error { + rsp, err := cli.FetchQRCodeCustomSize(1, 2, 1) if err != nil { return err } @@ -70,7 +95,7 @@ func qrcodeLogin() error { log.Infof("请使用手机QQ扫描二维码 (qrcode.png) : ") } time.Sleep(time.Second) - qrcodeTerminal.New2(qrcodeTerminal.ConsoleColors.BrightBlack, qrcodeTerminal.ConsoleColors.BrightWhite, qrcodeTerminal.QRCodeRecoveryLevels.Low).Get(fi.Content).Print() + printQRCode(rsp.ImageData) s, err := cli.QueryQRCodeStatus(rsp.Sig) if err != nil { return err diff --git a/go.mod b/go.mod index 0d4896d6..43309d3b 100644 --- a/go.mod +++ b/go.mod @@ -3,14 +3,12 @@ module github.com/Mrs4s/go-cqhttp go 1.17 require ( - github.com/Baozisoftware/qrcode-terminal-go v0.0.0-20170407111555-c0650d8dff0f github.com/Microsoft/go-winio v0.5.1 github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/dustin/go-humanize v1.0.0 github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 - github.com/gocq/qrcode v0.0.0-20211114040510-366b953fcd98 github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0 github.com/klauspost/compress v1.13.6 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible @@ -34,17 +32,14 @@ require ( github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect - github.com/gocq/rs v1.0.1 // indirect github.com/golang/snappy v0.0.1 // indirect github.com/google/go-cmp v0.5.5 // indirect - github.com/google/uuid v1.1.0 // indirect github.com/jonboulle/clockwork v0.2.2 // indirect github.com/lestrrat-go/strftime v1.0.5 // indirect github.com/mattn/go-isatty v0.0.14 // indirect github.com/pierrec/lz4/v4 v4.1.11 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect github.com/remyoudompheng/bigfft v0.0.0-20200410134404-eec4a21b6bb0 // indirect - github.com/skip2/go-qrcode v0.0.0-20200617195104-da1b6568686e // indirect github.com/tidwall/match v1.1.1 // indirect github.com/tidwall/pretty v1.2.0 // indirect github.com/xdg-go/pbkdf2 v1.0.0 // indirect diff --git a/go.sum b/go.sum index 9c788da0..f8678e5f 100644 --- a/go.sum +++ b/go.sum @@ -1,5 +1,3 @@ -github.com/Baozisoftware/qrcode-terminal-go v0.0.0-20170407111555-c0650d8dff0f h1:2dk3eOnYllh+wUOuDhOoC2vUVoJF/5z478ryJ+wzEII= -github.com/Baozisoftware/qrcode-terminal-go v0.0.0-20170407111555-c0650d8dff0f/go.mod h1:4a58ifQTEe2uwwsaqbh3i2un5/CBPg+At/qHpt18Tmk= github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb h1:nc96MkGgqa2iW8bMzFMj2mdT9LUJYgsdez30zwo8qxg= @@ -8,8 +6,6 @@ github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956 h1:hnaAkKz4t+xpS github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= -github.com/bits-and-blooms/bitset v1.2.1 h1:M+/hrU9xlMp7t4TyTDQW97d3tRPVuKFC6zBEK16QnXY= -github.com/bits-and-blooms/bitset v1.2.1/go.mod h1:gIdJ4wp64HaoK2YrL1Q5/N7Y16edYb8uY+O0FJTyyDA= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -24,10 +20,6 @@ github.com/gabriel-vasile/mimetype v1.4.0 h1:Cn9dkdYsMIu56tGho+fqzh7XmvY2YyGU0Fn github.com/gabriel-vasile/mimetype v1.4.0/go.mod h1:fA8fi6KUiG7MgQQ+mEWotXoEOvmxRtOJlERCzSmRvr8= github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= -github.com/gocq/qrcode v0.0.0-20211114040510-366b953fcd98 h1:NJDZEa7gibUa0w4tie8qKeQFKdeKFUbecWyQDPdRx40= -github.com/gocq/qrcode v0.0.0-20211114040510-366b953fcd98/go.mod h1:E5TBHc60dsWtOL7sbXCb3P9i4xrj2J7Zm5sEJftIc1w= -github.com/gocq/rs v1.0.1 h1:ng7nhXmnx3SnfM0DOqmbP6GmQp1xGwRG9XmBiLFDWuM= -github.com/gocq/rs v1.0.1/go.mod h1:8oaQnRvqn1fMh8i5zsetgQo03OUXksJV1k+dpmExxcY= github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -36,8 +28,6 @@ github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEW github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/uuid v1.1.0 h1:Jf4mxPC/ziBnoPIdpQdPJ9OeiomAUHLvxmPRSPH9m4s= -github.com/google/uuid v1.1.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/hpcloud/tail v1.0.0 h1:nfCOvKYfkgYP8hkirhJocXT2+zOD8yUNjXaWfTlyFKI= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/jonboulle/clockwork v0.2.2 h1:UOGuzwb1PwsrDAObMuhUnj0p5ULPj8V/xJ7Kx9qUBdQ= @@ -82,8 +72,6 @@ github.com/segmentio/asm v1.1.3/go.mod h1:Ld3L4ZXGNcSLRg4JBsZ3//1+f/TjYl0Mzen/DQ github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= github.com/sirupsen/logrus v1.8.1 h1:dJKuHgqk1NNQlqoA6BTlM1Wf9DOH3NBjQyu0h9+AZZE= github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= -github.com/skip2/go-qrcode v0.0.0-20200617195104-da1b6568686e h1:MRM5ITcdelLK2j1vwZ3Je0FKVCfqOLp5zO6trqMLYs0= -github.com/skip2/go-qrcode v0.0.0-20200617195104-da1b6568686e/go.mod h1:XV66xRDqSt+GTGFMVlhk3ULuV0y9ZmzeVGR4mloJI3M= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= From 325bd427341db837f7782d2b9a3602e97addf644 Mon Sep 17 00:00:00 2001 From: ishkong Date: Sun, 13 Feb 2022 16:07:49 +0800 Subject: [PATCH 10/93] =?UTF-8?q?=F0=9F=93=9D=20Replace=20broken=20links?= =?UTF-8?q?=20in=20documentation=20(#1365)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/cqhttp.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/cqhttp.md b/docs/cqhttp.md index e861219c..71d7d201 100644 --- a/docs/cqhttp.md +++ b/docs/cqhttp.md @@ -244,7 +244,7 @@ Type: `node` | `seq` | message | 具体消息 | 用于自定义消息 | 特殊说明: **需要使用单独的API `/send_group_forward_msg` 发送,并且由于消息段较为复杂,仅支持Array形式入参。 如果引用消息和自定义消息同时出现,实际查看顺序将取消息段顺序. -另外按 [CQHTTP](https://git.io/JtxtN) 文档说明, `data` 应全为字符串, 但由于需要接收`message` 类型的消息, 所以 *仅限此Type的content字段* 支持Array套娃** +另外按 [Onebot v11](https://github.com/botuniverse/onebot-11/blob/master/message/array.md) 文档说明, `data` 应全为字符串, 但由于需要接收`message` 类型的消息, 所以 *仅限此Type的content字段* 支持Array套娃** 示例: From c609fd72f5b1e46c2a35dcd54330f6715b2cb839 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 13 Feb 2022 17:28:08 +0800 Subject: [PATCH 11/93] dep: update deps & drop github.com/klauspost/compress --- coolq/cqcode.go | 11 +---- go.mod | 12 ++--- go.sum | 71 ++++++++++++++++++++------- internal/selfupdate/update_others.go | 3 +- internal/selfupdate/update_windows.go | 3 +- 5 files changed, 61 insertions(+), 39 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index c30de373..46f72528 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -4,7 +4,6 @@ import ( "bytes" "crypto/md5" "encoding/hex" - xml2 "encoding/xml" "errors" "fmt" "io" @@ -1044,7 +1043,7 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou }, nil } xml := fmt.Sprintf(``, - XMLEscape(d["title"]), d["url"], d["image"], d["audio"], XMLEscape(d["title"]), XMLEscape(d["content"])) + utils.XmlEscape(d["title"]), d["url"], d["image"], d["audio"], utils.XmlEscape(d["title"]), utils.XmlEscape(d["content"])) return &message.ServiceElement{ Id: 60, Content: xml, @@ -1147,14 +1146,6 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou } } -// XMLEscape 将字符串c转义为XML字符串 -func XMLEscape(c string) string { - buf := global.NewBuffer() - defer global.PutBuffer(buf) - _ = xml2.EscapeText(buf, utils.S2B(c)) - return buf.String() -} - /*CQCodeEscapeText 将字符串raw中部分字符转义 & -> & diff --git a/go.mod b/go.mod index 43309d3b..80bf553f 100644 --- a/go.mod +++ b/go.mod @@ -4,23 +4,22 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb + github.com/Mrs4s/MiraiGo v0.0.0-20220213090811-8a518ee96c6b github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/dustin/go-humanize v1.0.0 github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0 - github.com/klauspost/compress v1.13.6 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible github.com/mattn/go-colorable v0.1.12 github.com/pkg/errors v0.9.1 github.com/segmentio/asm v1.1.3 github.com/sirupsen/logrus v1.8.1 github.com/stretchr/testify v1.7.0 - github.com/syndtr/goleveldb v1.0.0 - github.com/tidwall/gjson v1.12.1 + github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 + github.com/tidwall/gjson v1.14.0 github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60 - go.mongodb.org/mongo-driver v1.8.1 + go.mongodb.org/mongo-driver v1.8.3 golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3 golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 golang.org/x/time v0.0.0-20211116232009-f0f3c7e86c11 @@ -32,9 +31,10 @@ require ( github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect - github.com/golang/snappy v0.0.1 // indirect + github.com/golang/snappy v0.0.4 // indirect github.com/google/go-cmp v0.5.5 // indirect github.com/jonboulle/clockwork v0.2.2 // indirect + github.com/klauspost/compress v1.13.6 // indirect github.com/lestrrat-go/strftime v1.0.5 // indirect github.com/mattn/go-isatty v0.0.14 // indirect github.com/pierrec/lz4/v4 v4.1.11 // indirect diff --git a/go.sum b/go.sum index f8678e5f..71f6147b 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb h1:nc96MkGgqa2iW8bMzFMj2mdT9LUJYgsdez30zwo8qxg= -github.com/Mrs4s/MiraiGo v0.0.0-20220212081637-6692c4acb8eb/go.mod h1:rtKLkhMEi2YjsrXaNztT4uagUOPBxf6a+TNREkG097I= +github.com/Mrs4s/MiraiGo v0.0.0-20220213090811-8a518ee96c6b h1:RC+/HdXawl3FWYS7uqFdORHFTO3BNOQT0XQE6zJEdK8= +github.com/Mrs4s/MiraiGo v0.0.0-20220213090811-8a518ee96c6b/go.mod h1:BNKTKQjbsmv2Coh1u//NfsxsuOq2ByVN2ZbSSMwjQBc= github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956 h1:hnaAkKz4t+xpSNVp5mnuloRMd3Rj2Lfg5biZ3emv//c= github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= @@ -12,6 +12,8 @@ github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSs github.com/dustin/go-humanize v1.0.0 h1:VSnTsYCnlFHaM2/igO1h6X3HA71jcobQuxemgkq4zYo= github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= +github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4= +github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= github.com/fumiama/go-hide-param v0.1.4 h1:y7TRTzZMdCH9GOXnIzU3B+1BSkcmvejVGmGsz4t0DGU= github.com/fumiama/go-hide-param v0.1.4/go.mod h1:vJkQlJIEI56nIyp7tCQu1/2QOyKtZpudsnJkGk9U1aY= github.com/fumiama/imgsz v0.0.2 h1:fAkC0FnIscdKOXwAxlyw3EUba5NzxZdSxGaq3Uyfxak= @@ -21,14 +23,22 @@ github.com/gabriel-vasile/mimetype v1.4.0/go.mod h1:fA8fi6KUiG7MgQQ+mEWotXoEOvmx github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= +github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8= +github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA= +github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs= +github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= +github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= +github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= -github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= -github.com/golang/snappy v0.0.1 h1:Qgr9rKW7uDUkrbSmQeiDsGa8SjGyCOGtuasMWwvp2P4= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= +github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= +github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= +github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= +github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/hpcloud/tail v1.0.0 h1:nfCOvKYfkgYP8hkirhJocXT2+zOD8yUNjXaWfTlyFKI= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/jonboulle/clockwork v0.2.2 h1:UOGuzwb1PwsrDAObMuhUnj0p5ULPj8V/xJ7Kx9qUBdQ= github.com/jonboulle/clockwork v0.2.2/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= @@ -53,11 +63,15 @@ github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Ky github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y= github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94= github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc= +github.com/nxadm/tail v1.4.4 h1:DQuhQpB1tVlglWS2hLQ5OV6B5r8aGxSrPc5Qo6uTN78= +github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A= github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= -github.com/onsi/ginkgo v1.7.0 h1:WSHQ+IS43OoUrWtD1/bbclrwK8TTH5hzp+umCiuxHgs= -github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= -github.com/onsi/gomega v1.4.3 h1:RE1xgDvH7imwFD45h+u2SgIfERHlS2yNG4DObb5BSKU= -github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= +github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk= +github.com/onsi/ginkgo v1.14.0 h1:2mOpI4JVVPBN+WQRa0WKH2eXR+Ey+uK4n7Zj0aYpIQA= +github.com/onsi/ginkgo v1.14.0/go.mod h1:iSB4RoI2tjJc9BBv4NKIKWKya62Rps+oPG/Lv9klQyY= +github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY= +github.com/onsi/gomega v1.10.1 h1:o0+MgICZLuZ7xjH7Vx6zS/zcu93/BEp1VwkIW1mEXCE= +github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo= github.com/pierrec/lz4/v4 v4.1.11 h1:LVs17FAZJFOjgmJXl9Tf13WfLUvZq7/RjfEJrnwZ9OE= github.com/pierrec/lz4/v4 v4.1.11/go.mod h1:gZWDp/Ze/IJXGXf23ltt2EXimqmTUXEy0GFuRQyBid4= github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= @@ -78,11 +92,11 @@ github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UV github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/syndtr/goleveldb v1.0.0 h1:fBdIW9lB4Iz0n9khmH8w27SJ3QEJ7+IgjPEwGSZiFdE= -github.com/syndtr/goleveldb v1.0.0/go.mod h1:ZVVdQEZoIme9iO1Ch2Jdy24qqXrMMOU6lpPAyBWyWuQ= +github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= +github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= github.com/tidwall/gjson v1.11.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= -github.com/tidwall/gjson v1.12.1 h1:ikuZsLdhr8Ws0IdROXUS1Gi4v9Z4pGqpX/CvJkxvfpo= -github.com/tidwall/gjson v1.12.1/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= +github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= +github.com/tidwall/gjson v1.14.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA= github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM= github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= @@ -98,17 +112,20 @@ github.com/xdg-go/stringprep v1.0.2 h1:6iq84/ryjjeRmMJwxutI51F2GIPlP5BfTvXHeYjyh github.com/xdg-go/stringprep v1.0.2/go.mod h1:8F9zXuvzgwmyT5DUm4GUfZGDdT3W+LCvS6+da4O5kxM= github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d h1:splanxYIlg+5LfHAM6xpdFEAYOk8iySO56hMFq6uLyA= github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d/go.mod h1:rHwXgn7JulP+udvsHwJoVG1YGAP6VLg4y9I5dyZdqmA= -go.mongodb.org/mongo-driver v1.8.1 h1:OZE4Wni/SJlrcmSIBRYNzunX5TKxjrTS4jKSnA99oKU= -go.mongodb.org/mongo-driver v1.8.1/go.mod h1:0sQWfOeY63QTntERDJJ/0SuKK0T1uVSgKCuAROlKEPY= +go.mongodb.org/mongo-driver v1.8.3 h1:TDKlTkGDKm9kkJVUOAXDK5/fkqKHJVwYQSpoRfB43R4= +go.mongodb.org/mongo-driver v1.8.3/go.mod h1:0sQWfOeY63QTntERDJJ/0SuKK0T1uVSgKCuAROlKEPY= go.uber.org/atomic v1.9.0 h1:ECmE8Bn/WFTYwEW/bpKD3M8VtR/zQVbavAoalC1PYyE= go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20201216223049-8b5274cf687f/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I= golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3 h1:0es+/5331RGQPcXlMfP+WrnIIS6dNnNRe0WB02W0F4M= golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= +golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= @@ -120,8 +137,15 @@ golang.org/x/sync v0.0.0-20210220032951-036812b2e83c h1:5KslGYwFpkhGh+Q16bwMP3cO golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200519105757-fe76b779f299/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200814200057-3d37ad5750ed/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -137,6 +161,8 @@ golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9sn golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 h1:JGgROgKl9N8DuW20oFS5gxc+lE67/N3FcwmBPMe7ArY= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/text v0.3.0/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.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= @@ -144,19 +170,26 @@ golang.org/x/time v0.0.0-20211116232009-f0f3c7e86c11 h1:GZokNIeuVkl3aZHJchRrr13W golang.org/x/time v0.0.0-20211116232009-f0f3c7e86c11/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20190531172133-b3315ee88b7d/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE= +golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= +google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= +google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM= +google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= +google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= +google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/fsnotify.v1 v1.4.7 h1:xOHLXZwVvI9hhs+cLKq5+I5onOuwQLhQwiu63xxlHs4= gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkepLTh2hOroT7a+7czfdQ= gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw= -gopkg.in/yaml.v2 v2.2.1 h1:mUhvW9EsL+naU5Q3cakzfE91YhliOondGd6ZrsDBHQE= -gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU= +gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/internal/selfupdate/update_others.go b/internal/selfupdate/update_others.go index b18bb6bb..1bd535dd 100644 --- a/internal/selfupdate/update_others.go +++ b/internal/selfupdate/update_others.go @@ -6,12 +6,11 @@ package selfupdate import ( "archive/tar" "bytes" + "compress/gzip" "crypto/sha256" "errors" "io" "net/http" - - "github.com/klauspost/compress/gzip" ) // update go-cqhttp自我更新 diff --git a/internal/selfupdate/update_windows.go b/internal/selfupdate/update_windows.go index 235b48f9..cb32e1a5 100644 --- a/internal/selfupdate/update_windows.go +++ b/internal/selfupdate/update_windows.go @@ -1,13 +1,12 @@ package selfupdate import ( + "archive/zip" "bytes" "crypto/sha256" "errors" "io" "net/http" - - "github.com/klauspost/compress/zip" ) // update go-cqhttp自我更新 From da9bad44e2e6a74c07c7dd887d1e111260832924 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 14 Feb 2022 00:54:13 +0800 Subject: [PATCH 12/93] dep: update MiraiGo reduce binary size about 550KiB --- go.mod | 4 ++-- go.sum | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/go.mod b/go.mod index 80bf553f..20fcd9a4 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220213090811-8a518ee96c6b + github.com/Mrs4s/MiraiGo v0.0.0-20220213165136-d53bf8503e18 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/dustin/go-humanize v1.0.0 github.com/fumiama/go-hide-param v0.1.4 @@ -27,7 +27,7 @@ require ( ) require ( - github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956 // indirect + github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect diff --git a/go.sum b/go.sum index 71f6147b..9efb487e 100644 --- a/go.sum +++ b/go.sum @@ -1,9 +1,9 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220213090811-8a518ee96c6b h1:RC+/HdXawl3FWYS7uqFdORHFTO3BNOQT0XQE6zJEdK8= -github.com/Mrs4s/MiraiGo v0.0.0-20220213090811-8a518ee96c6b/go.mod h1:BNKTKQjbsmv2Coh1u//NfsxsuOq2ByVN2ZbSSMwjQBc= -github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956 h1:hnaAkKz4t+xpSNVp5mnuloRMd3Rj2Lfg5biZ3emv//c= -github.com/RomiChan/protobuf v0.0.0-20211223055824-048df49a8956/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= +github.com/Mrs4s/MiraiGo v0.0.0-20220213165136-d53bf8503e18 h1:eM2KdNvC9DffdhBUSMjSCzdedQp2PmnNkiI+TAM1iDQ= +github.com/Mrs4s/MiraiGo v0.0.0-20220213165136-d53bf8503e18/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= +github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= +github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= From f2e26d0e134c5ebb431f7d946f1536c2e60b5cd0 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 14 Feb 2022 16:30:47 +0800 Subject: [PATCH 13/93] dep: update MiraiGo Fixes #1095 --- go.mod | 2 +- go.sum | 11 ++--------- 2 files changed, 3 insertions(+), 10 deletions(-) diff --git a/go.mod b/go.mod index 20fcd9a4..5a94b4f5 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220213165136-d53bf8503e18 + github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/dustin/go-humanize v1.0.0 github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index 9efb487e..7d2a4743 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220213165136-d53bf8503e18 h1:eM2KdNvC9DffdhBUSMjSCzdedQp2PmnNkiI+TAM1iDQ= -github.com/Mrs4s/MiraiGo v0.0.0-20220213165136-d53bf8503e18/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= +github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715 h1:6tSKbzugDl1V+htbVtTpiuVTpINGGXIRD8PBB64Sjoc= +github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= @@ -29,7 +29,6 @@ github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrU github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= -github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -94,7 +93,6 @@ github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5Cc github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= -github.com/tidwall/gjson v1.11.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= github.com/tidwall/gjson v1.14.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA= @@ -127,7 +125,6 @@ golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -150,10 +147,8 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20211110154304-99a53858aa08/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220111092808-5a964db01320 h1:0jf+tOCoZ3LyutmCOWpVni1chK4VfFLhRsDK7MhqGRY= golang.org/x/sys v0.0.0-20220111092808-5a964db01320/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= @@ -179,8 +174,6 @@ google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQ google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= -google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= From 9054d4cee89b4102fd3e0ad620d68169e3343b70 Mon Sep 17 00:00:00 2001 From: wdvxdr1123 <34832863+wdvxdr1123@users.noreply.github.com> Date: Tue, 15 Feb 2022 22:24:27 +0800 Subject: [PATCH 14/93] db/leveldb: impl index read/write drop `encoding/gob` (#1370) Two benefit below: * shrink go-cqhttp binary size about 200KiB * shrink database file from 2.8M to 1.56M compared with v2 database Also provide a tool to migrate v2 database: https://github.com/RomiChan/gocq-leveldb-migrate --- db/leveldb/const.go | 25 ++++++ db/leveldb/database_gen.go | 177 +++++++++++++++++++++++++++++++++++++ db/leveldb/leveldb.go | 131 +++++++++++---------------- db/leveldb/mkrw.go | 129 +++++++++++++++++++++++++++ db/leveldb/reader.go | 154 ++++++++++++++++++++++++++++++++ db/leveldb/writer.go | 149 +++++++++++++++++++++++++++++++ modules/config/config.go | 5 -- 7 files changed, 687 insertions(+), 83 deletions(-) create mode 100644 db/leveldb/const.go create mode 100644 db/leveldb/database_gen.go create mode 100644 db/leveldb/mkrw.go create mode 100644 db/leveldb/reader.go create mode 100644 db/leveldb/writer.go diff --git a/db/leveldb/const.go b/db/leveldb/const.go new file mode 100644 index 00000000..1e630313 --- /dev/null +++ b/db/leveldb/const.go @@ -0,0 +1,25 @@ +package leveldb + +const dataVersion = 1 + +const ( + group = 0x0 + private = 0x1 + guildChannel = 0x2 +) + +type coder byte + +const ( + coderNil coder = iota + coderInt + coderUint + coderInt32 + coderUint32 + coderInt64 + coderUint64 + coderString + coderMSG // global.MSG + coderArrayMSG // []global.MSG + coderStruct // struct{} +) diff --git a/db/leveldb/database_gen.go b/db/leveldb/database_gen.go new file mode 100644 index 00000000..929aeac1 --- /dev/null +++ b/db/leveldb/database_gen.go @@ -0,0 +1,177 @@ +// Code generated by mkrw.go; DO NOT EDIT. + +package leveldb + +import "github.com/Mrs4s/go-cqhttp/db" + +func (w *writer) writeStoredGroupMessage(x *db.StoredGroupMessage) { + if x == nil { + w.nil() + return + } + w.coder(coderStruct) + w.string(x.ID) + w.int32(x.GlobalID) + w.writeStoredMessageAttribute(x.Attribute) + w.string(x.SubType) + w.writeQuotedInfo(x.QuotedInfo) + w.int64(x.GroupCode) + w.string(x.AnonymousID) + w.arrayMsg(x.Content) +} + +func (r *reader) readStoredGroupMessage() *db.StoredGroupMessage { + coder := r.coder() + if coder == coderNil { + return nil + } + x := &db.StoredGroupMessage{} + x.ID = r.string() + x.GlobalID = r.int32() + x.Attribute = r.readStoredMessageAttribute() + x.SubType = r.string() + x.QuotedInfo = r.readQuotedInfo() + x.GroupCode = r.int64() + x.AnonymousID = r.string() + x.Content = r.arrayMsg() + return x +} + +func (w *writer) writeStoredPrivateMessage(x *db.StoredPrivateMessage) { + if x == nil { + w.nil() + return + } + w.coder(coderStruct) + w.string(x.ID) + w.int32(x.GlobalID) + w.writeStoredMessageAttribute(x.Attribute) + w.string(x.SubType) + w.writeQuotedInfo(x.QuotedInfo) + w.int64(x.SessionUin) + w.int64(x.TargetUin) + w.arrayMsg(x.Content) +} + +func (r *reader) readStoredPrivateMessage() *db.StoredPrivateMessage { + coder := r.coder() + if coder == coderNil { + return nil + } + x := &db.StoredPrivateMessage{} + x.ID = r.string() + x.GlobalID = r.int32() + x.Attribute = r.readStoredMessageAttribute() + x.SubType = r.string() + x.QuotedInfo = r.readQuotedInfo() + x.SessionUin = r.int64() + x.TargetUin = r.int64() + x.Content = r.arrayMsg() + return x +} + +func (w *writer) writeStoredGuildChannelMessage(x *db.StoredGuildChannelMessage) { + if x == nil { + w.nil() + return + } + w.coder(coderStruct) + w.string(x.ID) + w.writeStoredGuildMessageAttribute(x.Attribute) + w.uint64(x.GuildID) + w.uint64(x.ChannelID) + w.writeQuotedInfo(x.QuotedInfo) + w.arrayMsg(x.Content) +} + +func (r *reader) readStoredGuildChannelMessage() *db.StoredGuildChannelMessage { + coder := r.coder() + if coder == coderNil { + return nil + } + x := &db.StoredGuildChannelMessage{} + x.ID = r.string() + x.Attribute = r.readStoredGuildMessageAttribute() + x.GuildID = r.uint64() + x.ChannelID = r.uint64() + x.QuotedInfo = r.readQuotedInfo() + x.Content = r.arrayMsg() + return x +} + +func (w *writer) writeStoredMessageAttribute(x *db.StoredMessageAttribute) { + if x == nil { + w.nil() + return + } + w.coder(coderStruct) + w.int32(x.MessageSeq) + w.int32(x.InternalID) + w.int64(x.SenderUin) + w.string(x.SenderName) + w.int64(x.Timestamp) +} + +func (r *reader) readStoredMessageAttribute() *db.StoredMessageAttribute { + coder := r.coder() + if coder == coderNil { + return nil + } + x := &db.StoredMessageAttribute{} + x.MessageSeq = r.int32() + x.InternalID = r.int32() + x.SenderUin = r.int64() + x.SenderName = r.string() + x.Timestamp = r.int64() + return x +} + +func (w *writer) writeStoredGuildMessageAttribute(x *db.StoredGuildMessageAttribute) { + if x == nil { + w.nil() + return + } + w.coder(coderStruct) + w.uint64(x.MessageSeq) + w.uint64(x.InternalID) + w.uint64(x.SenderTinyID) + w.string(x.SenderName) + w.int64(x.Timestamp) +} + +func (r *reader) readStoredGuildMessageAttribute() *db.StoredGuildMessageAttribute { + coder := r.coder() + if coder == coderNil { + return nil + } + x := &db.StoredGuildMessageAttribute{} + x.MessageSeq = r.uint64() + x.InternalID = r.uint64() + x.SenderTinyID = r.uint64() + x.SenderName = r.string() + x.Timestamp = r.int64() + return x +} + +func (w *writer) writeQuotedInfo(x *db.QuotedInfo) { + if x == nil { + w.nil() + return + } + w.coder(coderStruct) + w.string(x.PrevID) + w.int32(x.PrevGlobalID) + w.arrayMsg(x.QuotedContent) +} + +func (r *reader) readQuotedInfo() *db.QuotedInfo { + coder := r.coder() + if coder == coderNil { + return nil + } + x := &db.QuotedInfo{} + x.PrevID = r.string() + x.PrevGlobalID = r.int32() + x.QuotedContent = r.arrayMsg() + return x +} diff --git a/db/leveldb/leveldb.go b/db/leveldb/leveldb.go index 2d86dbb5..7853e1b1 100644 --- a/db/leveldb/leveldb.go +++ b/db/leveldb/leveldb.go @@ -1,54 +1,40 @@ package leveldb import ( - "bytes" - "encoding/gob" "path" - "github.com/Mrs4s/MiraiGo/utils" - "github.com/Mrs4s/MiraiGo/binary" + "github.com/Mrs4s/MiraiGo/utils" "github.com/pkg/errors" "github.com/syndtr/goleveldb/leveldb" "github.com/syndtr/goleveldb/leveldb/opt" "gopkg.in/yaml.v3" "github.com/Mrs4s/go-cqhttp/db" - "github.com/Mrs4s/go-cqhttp/global" - "github.com/Mrs4s/go-cqhttp/modules/config" ) -type LevelDBImpl struct { +type database struct { db *leveldb.DB } -const ( - group byte = 0x0 - private byte = 0x1 - guildChannel byte = 0x2 -) +// config leveldb 相关配置 +type config struct { + Enable bool `yaml:"enable"` +} func init() { - gob.Register(db.StoredMessageAttribute{}) - gob.Register(db.StoredGuildMessageAttribute{}) - gob.Register(db.QuotedInfo{}) - gob.Register(global.MSG{}) - gob.Register(db.StoredGroupMessage{}) - gob.Register(db.StoredPrivateMessage{}) - gob.Register(db.StoredGuildChannelMessage{}) - db.Register("leveldb", func(node yaml.Node) db.Database { - conf := new(config.LevelDBConfig) + conf := new(config) _ = node.Decode(conf) if !conf.Enable { return nil } - return &LevelDBImpl{} + return &database{} }) } -func (ldb *LevelDBImpl) Open() error { - p := path.Join("data", "leveldb-v2") +func (ldb *database) Open() error { + p := path.Join("data", "leveldb-v3") d, err := leveldb.OpenFile(p, &opt.Options{ WriteBuffer: 32 * opt.KiB, }) @@ -59,31 +45,31 @@ func (ldb *LevelDBImpl) Open() error { return nil } -func (ldb *LevelDBImpl) GetMessageByGlobalID(id int32) (db.StoredMessage, error) { +func (ldb *database) GetMessageByGlobalID(id int32) (_ db.StoredMessage, err error) { v, err := ldb.db.Get(binary.ToBytes(id), nil) - if err != nil { + if err != nil || len(v) == 0 { return nil, errors.Wrap(err, "get value error") } - r := binary.NewReader(v) - switch r.ReadByte() { - case group: - g := &db.StoredGroupMessage{} - if err = gob.NewDecoder(bytes.NewReader(r.ReadAvailable())).Decode(g); err != nil { - return nil, errors.Wrap(err, "decode message error") + defer func() { + if r := recover(); r != nil { + err = errors.Errorf("%v", r) } - return g, nil + }() + r, err := newReader(utils.B2S(v)) + if err != nil { + return nil, err + } + switch r.uvarint() { + case group: + return r.readStoredGroupMessage(), nil case private: - p := &db.StoredPrivateMessage{} - if err = gob.NewDecoder(bytes.NewReader(r.ReadAvailable())).Decode(p); err != nil { - return nil, errors.Wrap(err, "decode message error") - } - return p, nil + return r.readStoredPrivateMessage(), nil default: return nil, errors.New("unknown message flag") } } -func (ldb *LevelDBImpl) GetGroupMessageByGlobalID(id int32) (*db.StoredGroupMessage, error) { +func (ldb *database) GetGroupMessageByGlobalID(id int32) (*db.StoredGroupMessage, error) { i, err := ldb.GetMessageByGlobalID(id) if err != nil { return nil, err @@ -95,7 +81,7 @@ func (ldb *LevelDBImpl) GetGroupMessageByGlobalID(id int32) (*db.StoredGroupMess return g, nil } -func (ldb *LevelDBImpl) GetPrivateMessageByGlobalID(id int32) (*db.StoredPrivateMessage, error) { +func (ldb *database) GetPrivateMessageByGlobalID(id int32) (*db.StoredPrivateMessage, error) { i, err := ldb.GetMessageByGlobalID(id) if err != nil { return nil, err @@ -107,59 +93,48 @@ func (ldb *LevelDBImpl) GetPrivateMessageByGlobalID(id int32) (*db.StoredPrivate return p, nil } -func (ldb *LevelDBImpl) GetGuildChannelMessageByID(id string) (*db.StoredGuildChannelMessage, error) { +func (ldb *database) GetGuildChannelMessageByID(id string) (*db.StoredGuildChannelMessage, error) { v, err := ldb.db.Get([]byte(id), nil) if err != nil { return nil, errors.Wrap(err, "get value error") } - r := binary.NewReader(v) - switch r.ReadByte() { - case guildChannel: - g := &db.StoredGuildChannelMessage{} - if err = gob.NewDecoder(bytes.NewReader(r.ReadAvailable())).Decode(g); err != nil { - return nil, errors.Wrap(err, "decode message error") + defer func() { + if r := recover(); r != nil { + err = errors.Errorf("%v", r) } - return g, nil + }() + r, err := newReader(utils.B2S(v)) + if err != nil { + return nil, err + } + switch r.uvarint() { + case guildChannel: + return r.readStoredGuildChannelMessage(), nil default: return nil, errors.New("unknown message flag") } } -func (ldb *LevelDBImpl) InsertGroupMessage(msg *db.StoredGroupMessage) error { - buf := global.NewBuffer() - defer global.PutBuffer(buf) - if err := gob.NewEncoder(buf).Encode(msg); err != nil { - return errors.Wrap(err, "encode message error") - } - err := ldb.db.Put(binary.ToBytes(msg.GlobalID), binary.NewWriterF(func(w *binary.Writer) { - w.WriteByte(group) - w.Write(buf.Bytes()) - }), nil) +func (ldb *database) InsertGroupMessage(msg *db.StoredGroupMessage) error { + w := newWriter() + w.uvarint(group) + w.writeStoredGroupMessage(msg) + err := ldb.db.Put(binary.ToBytes(msg.GlobalID), w.bytes(), nil) return errors.Wrap(err, "put data error") } -func (ldb *LevelDBImpl) InsertPrivateMessage(msg *db.StoredPrivateMessage) error { - buf := global.NewBuffer() - defer global.PutBuffer(buf) - if err := gob.NewEncoder(buf).Encode(msg); err != nil { - return errors.Wrap(err, "encode message error") - } - err := ldb.db.Put(binary.ToBytes(msg.GlobalID), binary.NewWriterF(func(w *binary.Writer) { - w.WriteByte(private) - w.Write(buf.Bytes()) - }), nil) +func (ldb *database) InsertPrivateMessage(msg *db.StoredPrivateMessage) error { + w := newWriter() + w.uvarint(private) + w.writeStoredPrivateMessage(msg) + err := ldb.db.Put(binary.ToBytes(msg.GlobalID), w.bytes(), nil) return errors.Wrap(err, "put data error") } -func (ldb *LevelDBImpl) InsertGuildChannelMessage(msg *db.StoredGuildChannelMessage) error { - buf := global.NewBuffer() - defer global.PutBuffer(buf) - if err := gob.NewEncoder(buf).Encode(msg); err != nil { - return errors.Wrap(err, "encode message error") - } - err := ldb.db.Put(utils.S2B(msg.ID), binary.NewWriterF(func(w *binary.Writer) { - w.WriteByte(guildChannel) - w.Write(buf.Bytes()) - }), nil) +func (ldb *database) InsertGuildChannelMessage(msg *db.StoredGuildChannelMessage) error { + w := newWriter() + w.uvarint(guildChannel) + w.writeStoredGuildChannelMessage(msg) + err := ldb.db.Put(utils.S2B(msg.ID), w.bytes(), nil) return errors.Wrap(err, "put data error") } diff --git a/db/leveldb/mkrw.go b/db/leveldb/mkrw.go new file mode 100644 index 00000000..d7a7489c --- /dev/null +++ b/db/leveldb/mkrw.go @@ -0,0 +1,129 @@ +//go:build ignore + +package main + +import ( + "bytes" + "fmt" + "go/ast" + "go/format" + "go/parser" + "go/token" + "os" +) + +var output bytes.Buffer + +func fprintf(format string, args ...interface{}) { + _, _ = fmt.Fprintf(&output, format, args...) +} + +func main() { + f, _ := parser.ParseFile(token.NewFileSet(), "./../database.go", nil, 0) + fprintf("// Code generated by mkrw.go; DO NOT EDIT.\n\n") + fprintf("package leveldb\n\n") + fprintf("import \"github.com/Mrs4s/go-cqhttp/db\"\n\n") + ast.Inspect(f, func(node ast.Node) bool { + switch node := node.(type) { + case *ast.FuncDecl: + return false + case *ast.TypeSpec: + if !node.Name.IsExported() { + return false + } + x, ok := node.Type.(*ast.StructType) + if !ok { + return false + } + if x.Fields != nil && x.Fields.List != nil { + mkWrite(node) + mkRead(node) + } + } + return true + }) + out, err := format.Source(output.Bytes()) + if err != nil { + fmt.Println(string(output.Bytes())) + panic(err) + } + os.WriteFile("database_gen.go", out, 0o644) +} + +func typeName(typ ast.Expr) string { + switch typ := typ.(type) { + case *ast.Ident: + return typ.Name + case *ast.ArrayType: + if typ.Len != nil { + panic("unexpected array type") + } + return "[]" + typeName(typ.Elt) + case *ast.SelectorExpr: + return typeName(typ.X) + "." + typ.Sel.Name + } + panic("unexpected type") +} + +func mkWrite(node *ast.TypeSpec) { + typename := node.Name.String() + structType := node.Type.(*ast.StructType) + fprintf("func (w *writer) write%s(x *db.%s) {\n", typename, typename) + fprintf("if x == nil {\n") + fprintf("w.nil()\n") + fprintf("return\n") + fprintf("}\n") + fprintf("w.coder(coderStruct)\n") + for _, field := range structType.Fields.List { + switch typ := field.Type.(type) { + case *ast.Ident: + for _, name := range field.Names { + fprintf("w.%s(x.%s)\n", typ.Name, name.Name) + } + case *ast.ArrayType: + if typeName(typ) != "[]global.MSG" { + panic("unexpected array type") + } + for _, name := range field.Names { + fprintf("w.arrayMsg(x.%s)\n", name.Name) + } + case *ast.StarExpr: + for _, name := range field.Names { + fprintf("w.write%s(x.%s)\n", typeName(typ.X), name.Name) + } + } + } + fprintf("}\n\n") +} + +func mkRead(node *ast.TypeSpec) { + typename := node.Name.String() + structType := node.Type.(*ast.StructType) + fprintf(`func (r *reader) read%s() *db.%s { + coder := r.coder() + if coder == coderNil { + return nil + }`+"\n", typename, typename) + fprintf("x := &db.%s{}\n", typename) + for _, field := range structType.Fields.List { + switch typ := field.Type.(type) { + case *ast.Ident: + for _, name := range field.Names { + fprintf("x.%s = r.%s()\n", name.Name, typ.Name) + } + case *ast.ArrayType: + if typeName(typ) != "[]global.MSG" { + panic("unexpected array type") + } + for _, name := range field.Names { + fprintf("x.%s = r.arrayMsg()\n", name.Name) + } + case *ast.StarExpr: + for _, name := range field.Names { + fprintf("x.%s = r.read%s()\n", name.Name, typeName(typ.X)) + } + } + } + fprintf("return x\n") + fprintf("}\n\n") +} diff --git a/db/leveldb/reader.go b/db/leveldb/reader.go new file mode 100644 index 00000000..ebc14cd8 --- /dev/null +++ b/db/leveldb/reader.go @@ -0,0 +1,154 @@ +package leveldb + +import ( + "encoding/binary" + "io" + "strconv" + "strings" + + "github.com/pkg/errors" + + "github.com/Mrs4s/go-cqhttp/global" +) + +type intReader struct { + data string + *strings.Reader +} + +func newIntReader(s string) intReader { + return intReader{ + data: s, + Reader: strings.NewReader(s), + } +} + +func (r *intReader) varint() int64 { + i, _ := binary.ReadVarint(r) + return i +} + +func (r *intReader) uvarint() uint64 { + i, _ := binary.ReadUvarint(r) + return i +} + +// reader implements the index read. +// data format is the same as the writer's +type reader struct { + data intReader + strings intReader + stringIndex map[uint64]string +} + +func (r *reader) coder() coder { o, _ := r.data.ReadByte(); return coder(o) } +func (r *reader) varint() int64 { return r.data.varint() } +func (r *reader) uvarint() uint64 { return r.data.uvarint() } + +func (r *reader) sync(c coder) { + if coder := r.coder(); coder != c { + panic("db/leveldb: bad sync expected " + strconv.Itoa(int(c)) + " but got " + strconv.Itoa(int(coder))) + } +} + +func (r *reader) int() int { + return int(r.varint()) +} + +func (r *reader) uint() uint { + return uint(r.uvarint()) +} + +func (r *reader) int32() int32 { + return int32(r.varint()) +} + +func (r *reader) uint32() uint32 { + return uint32(r.uvarint()) +} + +func (r *reader) int64() int64 { + return r.varint() +} + +func (r *reader) uint64() uint64 { + return r.uvarint() +} + +func (r *reader) string() string { + off := r.data.uvarint() + if s, ok := r.stringIndex[off]; ok { + return s + } + _, _ = r.strings.Seek(int64(off), io.SeekStart) + l := int64(r.strings.uvarint()) + whence, _ := r.strings.Seek(0, io.SeekCurrent) + s := r.strings.data[whence : whence+l] + r.stringIndex[off] = s + return s +} + +func (r *reader) msg() global.MSG { + length := r.uvarint() + msg := make(global.MSG, length) + for i := uint64(0); i < length; i++ { + s := r.string() + msg[s] = r.obj() + } + return msg +} + +func (r *reader) arrayMsg() []global.MSG { + length := r.uvarint() + msgs := make([]global.MSG, length) + for i := range msgs { + msgs[i] = r.msg() + } + return msgs +} + +func (r *reader) obj() interface{} { + switch coder := r.coder(); coder { + case coderNil: + return nil + case coderInt: + return int(r.varint()) + case coderUint: + return uint(r.uvarint()) + case coderInt32: + return int32(r.varint()) + case coderUint32: + return uint32(r.uvarint()) + case coderInt64: + return r.varint() + case coderUint64: + return r.uvarint() + case coderString: + return r.string() + case coderMSG: + return r.msg() + case coderArrayMSG: + return r.arrayMsg() + default: + panic("db/leveldb: invalid coder " + strconv.Itoa(int(coder))) + } +} + +func newReader(data string) (*reader, error) { + in := newIntReader(data) + v := in.uvarint() + if v != dataVersion { + return nil, errors.Errorf("db/leveldb: invalid data version %d", v) + } + sl := int64(in.uvarint()) + dl := int64(in.uvarint()) + whence, _ := in.Seek(0, io.SeekCurrent) + sData := data[whence : whence+sl] + dData := data[whence+sl : whence+sl+dl] + r := reader{ + data: newIntReader(dData), + strings: newIntReader(sData), + stringIndex: make(map[uint64]string), + } + return &r, nil +} diff --git a/db/leveldb/writer.go b/db/leveldb/writer.go new file mode 100644 index 00000000..c4add443 --- /dev/null +++ b/db/leveldb/writer.go @@ -0,0 +1,149 @@ +package leveldb + +import ( + "bytes" + "io" + + "github.com/Mrs4s/go-cqhttp/global" +) + +type intWriter struct { + bytes.Buffer +} + +func (w *intWriter) varint(x int64) { + w.uvarint(uint64(x)<<1 ^ uint64(x>>63)) +} + +func (w *intWriter) uvarint(x uint64) { + for x >= 0x80 { + w.WriteByte(byte(x) | 0x80) + x >>= 7 + } + w.WriteByte(byte(x)) +} + +// writer implements the index write. +// data format(use uvarint to encode integers): +// | version | string data length | index data length | string data | index data | +// for string data part, each string is encoded as: +// | string length | string | +// for index data part, each value is encoded as: +// | coder | value | +// * coder is the identifier of value's type. +// * specially for string, it's value is the offset in string data part. +type writer struct { + data intWriter + strings intWriter + stringIndex map[string]uint64 +} + +func newWriter() *writer { + return &writer{ + stringIndex: make(map[string]uint64), + } +} + +func (w *writer) coder(o coder) { w.data.WriteByte(byte(o)) } +func (w *writer) varint(x int64) { w.data.varint(x) } +func (w *writer) uvarint(x uint64) { w.data.uvarint(x) } +func (w *writer) nil() { w.coder(coderNil) } + +func (w *writer) int(i int) { + w.varint(int64(i)) +} + +func (w *writer) uint(i uint) { + w.uvarint(uint64(i)) +} + +func (w *writer) int32(i int32) { + w.varint(int64(i)) +} + +func (w *writer) uint32(i uint32) { + w.uvarint(uint64(i)) +} + +func (w *writer) int64(i int64) { + w.varint(i) +} + +func (w *writer) uint64(i uint64) { + w.uvarint(i) +} + +func (w *writer) string(s string) { + off, ok := w.stringIndex[s] + if !ok { + // not found write to string data part + // | string length | string | + off = uint64(w.strings.Len()) + w.strings.uvarint(uint64(len(s))) + _, _ = w.strings.WriteString(s) + w.stringIndex[s] = off + } + // write offset to index data part + w.uvarint(off) +} + +func (w *writer) msg(m global.MSG) { + w.uvarint(uint64(len(m))) + for s, obj := range m { + w.string(s) + w.obj(obj) + } +} + +func (w *writer) arrayMsg(a []global.MSG) { + w.uvarint(uint64(len(a))) + for _, v := range a { + w.msg(v) + } +} + +func (w *writer) obj(o interface{}) { + switch x := o.(type) { + case nil: + w.nil() + case int: + w.coder(coderInt) + w.int(x) + case int32: + w.coder(coderInt32) + w.int32(x) + case int64: + w.coder(coderInt64) + w.int64(x) + case uint: + w.coder(coderUint) + w.uint(x) + case uint32: + w.coder(coderUint32) + w.uint32(x) + case uint64: + w.coder(coderUint64) + w.uint64(x) + case string: + w.coder(coderString) + w.string(x) + case global.MSG: + w.coder(coderMSG) + w.msg(x) + case []global.MSG: + w.coder(coderArrayMSG) + w.arrayMsg(x) + default: + panic("unsupported type") + } +} + +func (w *writer) bytes() []byte { + var out intWriter + out.uvarint(dataVersion) + out.uvarint(uint64(w.strings.Len())) + out.uvarint(uint64(w.data.Len())) + _, _ = io.Copy(&out, &w.strings) + _, _ = io.Copy(&out, &w.data) + return out.Bytes() +} diff --git a/modules/config/config.go b/modules/config/config.go index 84c4a3e2..1386aa66 100644 --- a/modules/config/config.go +++ b/modules/config/config.go @@ -75,11 +75,6 @@ type Server struct { Default string } -// LevelDBConfig leveldb 相关配置 -type LevelDBConfig struct { - Enable bool `yaml:"enable"` -} - // MongoDBConfig mongodb 相关配置 type MongoDBConfig struct { Enable bool `yaml:"enable"` From 197ca5a3ead385835644117a67659701d8e233be Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Tue, 15 Feb 2022 22:52:49 +0800 Subject: [PATCH 15/93] disable pprof module by default --- main.go | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/main.go b/main.go index 09cd2f0d..0cd60791 100644 --- a/main.go +++ b/main.go @@ -3,10 +3,12 @@ package main import ( "github.com/Mrs4s/go-cqhttp/cmd/gocq" - _ "github.com/Mrs4s/go-cqhttp/db/leveldb" // leveldb - _ "github.com/Mrs4s/go-cqhttp/modules/mime" // mime检查模块 - _ "github.com/Mrs4s/go-cqhttp/modules/pprof" // pprof 性能分析 - _ "github.com/Mrs4s/go-cqhttp/modules/silk" // silk编码模块 + _ "github.com/Mrs4s/go-cqhttp/db/leveldb" // leveldb + _ "github.com/Mrs4s/go-cqhttp/modules/mime" // mime检查模块 + _ "github.com/Mrs4s/go-cqhttp/modules/silk" // silk编码模块 + // 其他模块 + // _ "github.com/Mrs4s/go-cqhttp/db/mongodb" // mongodb 数据库支持 + // _ "github.com/Mrs4s/go-cqhttp/modules/pprof" // pprof 性能分析 ) func main() { From 2a66896d43b87c8700c36dd5209bb36a16959fb1 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 16 Feb 2022 01:13:02 +0800 Subject: [PATCH 16/93] coolq: new package cqcode move cqcode escape&unescape to new package --- coolq/api.go | 3 +- coolq/converter.go | 71 +++++++++---------- coolq/cqcode.go | 124 ++++------------------------------ coolq/cqcode/escape.go | 97 ++++++++++++++++++++++++++ coolq/cqcode_test.go | 6 +- db/leveldb/reader.go | 35 ++-------- db/leveldb/writer.go | 30 ++------ go.mod | 2 - go.sum | 11 +-- internal/selfupdate/update.go | 27 ++++++-- server/http.go | 5 +- 11 files changed, 192 insertions(+), 219 deletions(-) create mode 100644 coolq/cqcode/escape.go diff --git a/coolq/api.go b/coolq/api.go index 2e9677dc..b9cf3527 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1984,8 +1984,7 @@ func OK(data interface{}) global.MSG { // Failed 生成失败返回值 func Failed(code int, msg ...string) global.MSG { - m := "" - w := "" + m, w := "", "" if len(msg) > 0 { m = msg[0] } diff --git a/coolq/converter.go b/coolq/converter.go index 44bc17cc..154f3540 100644 --- a/coolq/converter.go +++ b/coolq/converter.go @@ -13,38 +13,32 @@ import ( ) func convertGroupMemberInfo(groupID int64, m *client.GroupMemberInfo) global.MSG { + sex := "unknown" + if m.Gender == 1 { // unknown = 0xff + sex = "female" + } else if m.Gender == 0 { + sex = "male" + } + role := "member" + switch m.Permission { // nolint:exhaustive + case client.Owner: + role = "owner" + case client.Administrator: + role = "admin" + } return global.MSG{ - "group_id": groupID, - "user_id": m.Uin, - "nickname": m.Nickname, - "card": m.CardName, - "sex": func() string { - if m.Gender == 1 { - return "female" - } else if m.Gender == 0 { - return "male" - } - // unknown = 0xff - return "unknown" - }(), + "group_id": groupID, + "user_id": m.Uin, + "nickname": m.Nickname, + "card": m.CardName, + "sex": sex, "age": 0, "area": "", "join_time": m.JoinTime, "last_sent_time": m.LastSpeakTime, "shut_up_timestamp": m.ShutUpTimestamp, "level": strconv.FormatInt(int64(m.Level), 10), - "role": func() string { - switch m.Permission { - case client.Owner: - return "owner" - case client.Administrator: - return "admin" - case client.Member: - return "member" - default: - return "member" - } - }(), + "role": role, "unfriendly": false, "title": m.SpecialTitle, "title_expire_time": m.SpecialTitleExpireTime, @@ -71,6 +65,10 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { PrimaryID: uint64(m.GroupCode), } cqm := ToStringMessage(m.Elements, source, true) + postType := "message" + if m.Sender.Uin == bot.Client.Uin { + postType = "message_sent" + } gm := global.MSG{ "anonymous": nil, "font": 0, @@ -78,14 +76,9 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { "message": ToFormattedMessage(m.Elements, source, false), "message_type": "group", "message_seq": m.Id, - "post_type": func() string { - if m.Sender.Uin == bot.Client.Uin { - return "message_sent" - } - return "message" - }(), - "raw_message": cqm, - "self_id": bot.Client.Uin, + "post_type": postType, + "raw_message": cqm, + "self_id": bot.Client.Uin, "sender": global.MSG{ "age": 0, "area": "", @@ -122,16 +115,14 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { } } ms := gm["sender"].(global.MSG) - switch mem.Permission { + role := "member" + switch mem.Permission { // nolint:exhaustive case client.Owner: - ms["role"] = "owner" + role = "owner" case client.Administrator: - ms["role"] = "admin" - case client.Member: - ms["role"] = "member" - default: - ms["role"] = "member" + role = "admin" } + ms["role"] = role ms["nickname"] = mem.Nickname ms["card"] = mem.CardName ms["title"] = mem.SpecialTitle diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 46f72528..c2c77a19 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -22,6 +22,7 @@ import ( log "github.com/sirupsen/logrus" "github.com/tidwall/gjson" + "github.com/Mrs4s/go-cqhttp/coolq/cqcode" "github.com/Mrs4s/go-cqhttp/db" "github.com/Mrs4s/go-cqhttp/global" "github.com/Mrs4s/go-cqhttp/internal/base" @@ -289,7 +290,7 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. write("[CQ:reply,id=%d,seq=%d,qq=%d,time=%d,text=%s]", db.ToGlobalID(rid, replyElem.ReplySeq), replyElem.ReplySeq, replyElem.Sender, replyElem.Time, - CQCodeEscapeValue(ToStringMessage(replyElem.Elements, source))) + cqcode.EscapeValue(ToStringMessage(replyElem.Elements, source))) } else { write("[CQ:reply,id=%d]", db.ToGlobalID(rid, replyElem.ReplySeq)) } @@ -304,7 +305,7 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. } } case *message.TextElement: - sb.WriteString(CQCodeEscapeText(o.Content)) + sb.WriteString(cqcode.EscapeText(o.Content)) case *message.AtElement: if o.Target == 0 { write("[CQ:at,qq=all]") @@ -321,13 +322,13 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. if ur { write(`[CQ:record,file=%s]`, o.Name) } else { - write(`[CQ:record,file=%s,url=%s]`, o.Name, CQCodeEscapeValue(o.Url)) + write(`[CQ:record,file=%s,url=%s]`, o.Name, cqcode.EscapeValue(o.Url)) } case *message.ShortVideoElement: if ur { write(`[CQ:video,file=%s]`, o.Name) } else { - write(`[CQ:video,file=%s,url=%s]`, o.Name, CQCodeEscapeValue(o.Url)) + write(`[CQ:video,file=%s,url=%s]`, o.Name, cqcode.EscapeValue(o.Url)) } case *message.GroupImageElement: var arg string @@ -340,7 +341,7 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. if ur { write("[CQ:image,file=%s%s]", hex.EncodeToString(o.Md5)+".image", arg) } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", CQCodeEscapeValue(o.Url), arg) + write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url), arg) } case *message.FriendImageElement: var arg string @@ -350,22 +351,22 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. if ur { write("[CQ:image,file=%s%s]", hex.EncodeToString(o.Md5)+".image", arg) } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", CQCodeEscapeValue(o.Url), arg) + write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url), arg) } case *message.GuildImageElement: - write("[CQ:image,file=%s,url=%s]", hex.EncodeToString(o.Md5)+".image", CQCodeEscapeValue(o.Url)) + write("[CQ:image,file=%s,url=%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url)) case *message.DiceElement: write("[CQ:dice,value=%v]", o.Value) case *message.MarketFaceElement: sb.WriteString(o.Name) case *message.ServiceElement: if isOk := strings.Contains(o.Content, " 0 { if base.SplitURL { - for _, txt := range param.SplitURL(CQCodeUnescapeText(raw[:i])) { + for _, txt := range param.SplitURL(cqcode.UnescapeText(raw[:i])) { r = append(r, message.NewText(txt)) } } else { - r = append(r, message.NewText(CQCodeUnescapeText(raw[:i]))) + r = append(r, message.NewText(cqcode.UnescapeText(raw[:i]))) } } @@ -658,7 +659,7 @@ func (bot *CQBot) ConvertStringMessage(raw string, sourceType MessageSourceType) if i+1 > len(raw) { return } - d[key] = CQCodeUnescapeValue(raw[:i]) + d[key] = cqcode.UnescapeValue(raw[:i]) raw = raw[i:] i = 0 } @@ -1060,7 +1061,7 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou return message.NewDice(int32(i)), nil case "xml": resID := d["resid"] - template := CQCodeEscapeValue(d["data"]) + template := cqcode.EscapeValue(d["data"]) i, _ := strconv.ParseInt(resID, 10, 64) msg := message.NewRichXml(template, i) return msg, nil @@ -1146,101 +1147,6 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou } } -/*CQCodeEscapeText 将字符串raw中部分字符转义 - -& -> & - -[ -> [ - -] -> ] - -*/ -func CQCodeEscapeText(s string) string { - count := strings.Count(s, "&") - count += strings.Count(s, "[") - count += strings.Count(s, "]") - if count == 0 { - return s - } - - // Apply replacements to buffer. - var b strings.Builder - b.Grow(len(s) + count*4) - start := 0 - for i := 0; i < count; i++ { - j := start - for index, r := range s[start:] { - if r == '&' || r == '[' || r == ']' { - j += index - break - } - } - b.WriteString(s[start:j]) - switch s[j] { - case '&': - b.WriteString("&") - case '[': - b.WriteString("[") - case ']': - b.WriteString("]") - } - start = j + 1 - } - b.WriteString(s[start:]) - return b.String() -} - -/*CQCodeEscapeValue 将字符串value中部分字符转义 - -, -> , - -& -> & - -[ -> [ - -] -> ] - -*/ -func CQCodeEscapeValue(value string) string { - ret := CQCodeEscapeText(value) - ret = strings.ReplaceAll(ret, ",", ",") - return ret -} - -/*CQCodeUnescapeText 将字符串content中部分字符反转义 - -& -> & - -[ -> [ - -] -> ] - -*/ -func CQCodeUnescapeText(content string) string { - ret := content - ret = strings.ReplaceAll(ret, "[", "[") - ret = strings.ReplaceAll(ret, "]", "]") - ret = strings.ReplaceAll(ret, "&", "&") - return ret -} - -/*CQCodeUnescapeValue 将字符串content中部分字符反转义 - -, -> , - -& -> & - -[ -> [ - -] -> ] - -*/ -func CQCodeUnescapeValue(content string) string { - ret := strings.ReplaceAll(content, ",", ",") - ret = CQCodeUnescapeText(ret) - return ret -} - // makeImageOrVideoElem 图片 elem 生成器,单独拎出来,用于公用 func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceType MessageSourceType) (message.IMessageElement, error) { f := d["file"] diff --git a/coolq/cqcode/escape.go b/coolq/cqcode/escape.go new file mode 100644 index 00000000..a9f0cdf4 --- /dev/null +++ b/coolq/cqcode/escape.go @@ -0,0 +1,97 @@ +// Package cqcode provides CQCode util functions. +package cqcode + +import "strings" + +/*EscapeText 将字符串raw中部分字符转义 + +& -> & + +[ -> [ + +] -> ] + +*/ +func EscapeText(s string) string { + count := strings.Count(s, "&") + count += strings.Count(s, "[") + count += strings.Count(s, "]") + if count == 0 { + return s + } + + // Apply replacements to buffer. + var b strings.Builder + b.Grow(len(s) + count*4) + start := 0 + for i := 0; i < count; i++ { + j := start + for index, r := range s[start:] { + if r == '&' || r == '[' || r == ']' { + j += index + break + } + } + b.WriteString(s[start:j]) + switch s[j] { + case '&': + b.WriteString("&") + case '[': + b.WriteString("[") + case ']': + b.WriteString("]") + } + start = j + 1 + } + b.WriteString(s[start:]) + return b.String() +} + +/*EscapeValue 将字符串value中部分字符转义 + +, -> , + +& -> & + +[ -> [ + +] -> ] + +*/ +func EscapeValue(value string) string { + ret := EscapeText(value) + return strings.ReplaceAll(ret, ",", ",") +} + +/*UnescapeText 将字符串content中部分字符反转义 + +& -> & + +[ -> [ + +] -> ] + +*/ +func UnescapeText(content string) string { + ret := content + ret = strings.ReplaceAll(ret, "[", "[") + ret = strings.ReplaceAll(ret, "]", "]") + ret = strings.ReplaceAll(ret, "&", "&") + return ret +} + +/*UnescapeValue 将字符串content中部分字符反转义 + +, -> , + +& -> & + +[ -> [ + +] -> ] + +*/ +func UnescapeValue(content string) string { + ret := strings.ReplaceAll(content, ",", ",") + return UnescapeText(ret) +} diff --git a/coolq/cqcode_test.go b/coolq/cqcode_test.go index 338ca8f0..0c8bf7ed 100644 --- a/coolq/cqcode_test.go +++ b/coolq/cqcode_test.go @@ -8,6 +8,8 @@ import ( "github.com/Mrs4s/MiraiGo/utils" "github.com/stretchr/testify/assert" "github.com/tidwall/gjson" + + "github.com/Mrs4s/go-cqhttp/coolq/cqcode" ) var bot = CQBot{} @@ -41,7 +43,7 @@ const bText = `123456789[]&987654321[]&987654321[]&987654321[]&987654321[]&98765 func BenchmarkCQCodeEscapeText(b *testing.B) { for i := 0; i < b.N; i++ { ret := bText - CQCodeEscapeText(ret) + cqcode.EscapeText(ret) } } @@ -61,6 +63,6 @@ func TestCQCodeEscapeText(t *testing.T) { ret = strings.ReplaceAll(ret, "&", "&") ret = strings.ReplaceAll(ret, "[", "[") ret = strings.ReplaceAll(ret, "]", "]") - assert.Equal(t, ret, CQCodeEscapeText(rs)) + assert.Equal(t, ret, cqcode.EscapeText(rs)) } } diff --git a/db/leveldb/reader.go b/db/leveldb/reader.go index ebc14cd8..e8910364 100644 --- a/db/leveldb/reader.go +++ b/db/leveldb/reader.go @@ -44,36 +44,13 @@ type reader struct { func (r *reader) coder() coder { o, _ := r.data.ReadByte(); return coder(o) } func (r *reader) varint() int64 { return r.data.varint() } func (r *reader) uvarint() uint64 { return r.data.uvarint() } +func (r *reader) int32() int32 { return int32(r.varint()) } +func (r *reader) int64() int64 { return r.varint() } +func (r *reader) uint64() uint64 { return r.uvarint() } -func (r *reader) sync(c coder) { - if coder := r.coder(); coder != c { - panic("db/leveldb: bad sync expected " + strconv.Itoa(int(c)) + " but got " + strconv.Itoa(int(coder))) - } -} - -func (r *reader) int() int { - return int(r.varint()) -} - -func (r *reader) uint() uint { - return uint(r.uvarint()) -} - -func (r *reader) int32() int32 { - return int32(r.varint()) -} - -func (r *reader) uint32() uint32 { - return uint32(r.uvarint()) -} - -func (r *reader) int64() int64 { - return r.varint() -} - -func (r *reader) uint64() uint64 { - return r.uvarint() -} +// func (r *reader) uint32() uint32 { return uint32(r.uvarint()) } +// func (r *reader) int() int { return int(r.varint()) } +// func (r *reader) uint() uint { return uint(r.uvarint()) } func (r *reader) string() string { off := r.data.uvarint() diff --git a/db/leveldb/writer.go b/db/leveldb/writer.go index c4add443..a8fe7075 100644 --- a/db/leveldb/writer.go +++ b/db/leveldb/writer.go @@ -48,30 +48,12 @@ func (w *writer) coder(o coder) { w.data.WriteByte(byte(o)) } func (w *writer) varint(x int64) { w.data.varint(x) } func (w *writer) uvarint(x uint64) { w.data.uvarint(x) } func (w *writer) nil() { w.coder(coderNil) } - -func (w *writer) int(i int) { - w.varint(int64(i)) -} - -func (w *writer) uint(i uint) { - w.uvarint(uint64(i)) -} - -func (w *writer) int32(i int32) { - w.varint(int64(i)) -} - -func (w *writer) uint32(i uint32) { - w.uvarint(uint64(i)) -} - -func (w *writer) int64(i int64) { - w.varint(i) -} - -func (w *writer) uint64(i uint64) { - w.uvarint(i) -} +func (w *writer) int(i int) { w.varint(int64(i)) } +func (w *writer) uint(i uint) { w.uvarint(uint64(i)) } +func (w *writer) int32(i int32) { w.varint(int64(i)) } +func (w *writer) uint32(i uint32) { w.uvarint(uint64(i)) } +func (w *writer) int64(i int64) { w.varint(i) } +func (w *writer) uint64(i uint64) { w.uvarint(i) } func (w *writer) string(s string) { off, ok := w.stringIndex[s] diff --git a/go.mod b/go.mod index 5a94b4f5..6b0ef76d 100644 --- a/go.mod +++ b/go.mod @@ -6,10 +6,8 @@ require ( github.com/Microsoft/go-winio v0.5.1 github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc - github.com/dustin/go-humanize v1.0.0 github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 - github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible github.com/mattn/go-colorable v0.1.12 github.com/pkg/errors v0.9.1 diff --git a/go.sum b/go.sum index 7d2a4743..20d014bf 100644 --- a/go.sum +++ b/go.sum @@ -9,8 +9,6 @@ github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMm github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/dustin/go-humanize v1.0.0 h1:VSnTsYCnlFHaM2/igO1h6X3HA71jcobQuxemgkq4zYo= -github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= @@ -29,6 +27,7 @@ github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrU github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= +github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -41,8 +40,6 @@ github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/ github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/jonboulle/clockwork v0.2.2 h1:UOGuzwb1PwsrDAObMuhUnj0p5ULPj8V/xJ7Kx9qUBdQ= github.com/jonboulle/clockwork v0.2.2/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= -github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0 h1:iQTw/8FWTuc7uiaSepXwyf3o52HaUYcV+Tu66S3F5GA= -github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0/go.mod h1:1NbS8ALrpOvjt0rHPNLyCIeMtbizbir8U//inJ+zuB8= github.com/klauspost/compress v1.13.6 h1:P76CopJELS0TiO2mebmnzgWaajssP/EszplttgQxcgc= github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk= github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI= @@ -93,6 +90,7 @@ github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5Cc github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= +github.com/tidwall/gjson v1.11.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= github.com/tidwall/gjson v1.14.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA= @@ -125,6 +123,7 @@ golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -147,8 +146,10 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211110154304-99a53858aa08/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220111092808-5a964db01320 h1:0jf+tOCoZ3LyutmCOWpVni1chK4VfFLhRsDK7MhqGRY= golang.org/x/sys v0.0.0-20220111092808-5a964db01320/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= @@ -174,6 +175,8 @@ google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQ google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= +google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= +google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/internal/selfupdate/update.go b/internal/selfupdate/update.go index 2a05f606..5aa52a3a 100644 --- a/internal/selfupdate/update.go +++ b/internal/selfupdate/update.go @@ -7,13 +7,12 @@ import ( "fmt" "hash" "io" + "math" "os" "path/filepath" "runtime" "strings" - "github.com/dustin/go-humanize" - "github.com/kardianos/osext" "github.com/sirupsen/logrus" "github.com/tidwall/gjson" @@ -147,13 +146,33 @@ func (wc *writeSumCounter) Write(p []byte) (int, error) { wc.total += uint64(n) wc.hash.Write(p) fmt.Printf("\r ") - fmt.Printf("\rDownloading... %s complete", humanize.Bytes(wc.total)) + fmt.Printf("\rDownloading... %s complete", humanBytes(wc.total)) return n, nil } +func logn(n, b float64) float64 { + return math.Log(n) / math.Log(b) +} + +func humanBytes(s uint64) string { + sizes := []string{"B", "kB", "MB", "GB"} // GB对于go-cqhttp来说已经够用了 + if s < 10 { + return fmt.Sprintf("%d B", s) + } + e := math.Floor(logn(float64(s), 1000)) + suffix := sizes[int(e)] + val := math.Floor(float64(s)/math.Pow(1000, e)*10+0.5) / 10 + f := "%.0f %s" + if val < 10 { + f = "%.1f %s" + } + return fmt.Sprintf(f, val, suffix) +} + // FromStream copy form getlantern/go-update func fromStream(updateWith io.Reader) (err error, errRecover error) { - updatePath, err := osext.Executable() + updatePath, err := os.Executable() + updatePath = filepath.Clean(updatePath) if err != nil { return } diff --git a/server/http.go b/server/http.go index 0a73db8f..b289eef8 100644 --- a/server/http.go +++ b/server/http.go @@ -51,7 +51,6 @@ type httpServerPost struct { } type httpServer struct { - HTTP *http.Server api *api.Caller accessToken string } @@ -259,11 +258,11 @@ func runHTTP(bot *coolq.CQBot, node yaml.Node) { go func() { log.Infof("CQ HTTP 服务器已启动: %v", addr) - s.HTTP = &http.Server{ + server := &http.Server{ Addr: addr, Handler: s, } - if err := s.HTTP.ListenAndServe(); err != nil && err != http.ErrServerClosed { + if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed { log.Error(err) log.Infof("HTTP 服务启动失败, 请检查端口是否被占用.") log.Warnf("将在五秒后退出.") From 83266850880c2ea5540d0bf820972d6eaa900ed9 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Feb 2022 15:09:57 +0800 Subject: [PATCH 17/93] coolq: only truncate replySeq to uint16 on private message --- coolq/cqcode.go | 39 ++++++++++++++++++++------------------- db/database.go | 24 ++++++++---------------- go.mod | 2 +- go.sum | 11 ++--------- 4 files changed, 31 insertions(+), 45 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index c2c77a19..dfd83e15 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -103,6 +103,20 @@ func (e *PokeElement) Type() message.ElementType { return message.At } +func replyID(r *message.ReplyElement, source MessageSource) int32 { + id := int64(source.PrimaryID) + seq := r.ReplySeq + if source.SourceType == MessageSourcePrivate { + // 私聊似乎腾讯服务器有bug? + seq = int32(uint16(seq)) + id = r.Sender + } + if r.GroupID != 0 { + id = r.GroupID + } + return db.ToGlobalID(id, seq) +} + // ToArrayMessage 将消息元素数组转为MSG数组以用于消息上报 func ToArrayMessage(e []message.IMessageElement, source MessageSource) (r []global.MSG) { r = make([]global.MSG, 0, len(e)) @@ -113,18 +127,12 @@ func ToArrayMessage(e []message.IMessageElement, source MessageSource) (r []glob }) if reply != nil && source.SourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) - rid := int64(source.PrimaryID) - if source.SourceType == MessageSourcePrivate { - rid = replyElem.Sender - } - if replyElem.GroupID != 0 { - rid = replyElem.GroupID - } + id := replyID(replyElem, source) if base.ExtraReplyData { r = append(r, global.MSG{ "type": "reply", "data": map[string]string{ - "id": strconv.FormatInt(int64(db.ToGlobalID(rid, replyElem.ReplySeq)), 10), + "id": strconv.FormatInt(int64(id), 10), "seq": strconv.FormatInt(int64(replyElem.ReplySeq), 10), "qq": strconv.FormatInt(replyElem.Sender, 10), "time": strconv.FormatInt(int64(replyElem.Time), 10), @@ -134,7 +142,7 @@ func ToArrayMessage(e []message.IMessageElement, source MessageSource) (r []glob } else { r = append(r, global.MSG{ "type": "reply", - "data": map[string]string{"id": strconv.FormatInt(int64(db.ToGlobalID(rid, replyElem.ReplySeq)), 10)}, + "data": map[string]string{"id": strconv.FormatInt(int64(id), 10)}, }) } } @@ -279,20 +287,13 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. }) if reply != nil && source.SourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) - rid := int64(source.PrimaryID) - if source.SourceType == MessageSourcePrivate { - rid = replyElem.Sender - } - if replyElem.GroupID != 0 { - rid = replyElem.GroupID - } + id := replyID(replyElem, source) if base.ExtraReplyData { write("[CQ:reply,id=%d,seq=%d,qq=%d,time=%d,text=%s]", - db.ToGlobalID(rid, replyElem.ReplySeq), - replyElem.ReplySeq, replyElem.Sender, replyElem.Time, + id, replyElem.ReplySeq, replyElem.Sender, replyElem.Time, cqcode.EscapeValue(ToStringMessage(replyElem.Elements, source))) } else { - write("[CQ:reply,id=%d]", db.ToGlobalID(rid, replyElem.ReplySeq)) + write("[CQ:reply,id=%d]", id) } } for i, elem := range e { diff --git a/db/database.go b/db/database.go index 6495f823..c19da97f 100644 --- a/db/database.go +++ b/db/database.go @@ -103,22 +103,14 @@ func ToGlobalID(code int64, msgID int32) int32 { return int32(crc32.ChecksumIEEE([]byte(fmt.Sprintf("%d-%d", code, msgID)))) } -func (m *StoredGroupMessage) GetID() string { return m.ID } - -func (m *StoredGroupMessage) GetType() string { return "group" } - -func (m *StoredGroupMessage) GetGlobalID() int32 { return m.GlobalID } - +func (m *StoredGroupMessage) GetID() string { return m.ID } +func (m *StoredGroupMessage) GetType() string { return "group" } +func (m *StoredGroupMessage) GetGlobalID() int32 { return m.GlobalID } func (m *StoredGroupMessage) GetAttribute() *StoredMessageAttribute { return m.Attribute } +func (m *StoredGroupMessage) GetContent() []global.MSG { return m.Content } -func (m *StoredGroupMessage) GetContent() []global.MSG { return m.Content } - -func (m *StoredPrivateMessage) GetID() string { return m.ID } - -func (m *StoredPrivateMessage) GetType() string { return "private" } - -func (m *StoredPrivateMessage) GetGlobalID() int32 { return m.GlobalID } - +func (m *StoredPrivateMessage) GetID() string { return m.ID } +func (m *StoredPrivateMessage) GetType() string { return "private" } +func (m *StoredPrivateMessage) GetGlobalID() int32 { return m.GlobalID } func (m *StoredPrivateMessage) GetAttribute() *StoredMessageAttribute { return m.Attribute } - -func (m *StoredPrivateMessage) GetContent() []global.MSG { return m.Content } +func (m *StoredPrivateMessage) GetContent() []global.MSG { return m.Content } diff --git a/go.mod b/go.mod index 6b0ef76d..6459e606 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715 + github.com/Mrs4s/MiraiGo v0.0.0-20220218065747-0578942d86ab github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index 20d014bf..bb1a78cc 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715 h1:6tSKbzugDl1V+htbVtTpiuVTpINGGXIRD8PBB64Sjoc= -github.com/Mrs4s/MiraiGo v0.0.0-20220214082717-0e68a1e7b715/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= +github.com/Mrs4s/MiraiGo v0.0.0-20220218065747-0578942d86ab h1:kYJNHTBfkmEByDVIOvdCT5NMH9xbx915MOmpKGGXLWs= +github.com/Mrs4s/MiraiGo v0.0.0-20220218065747-0578942d86ab/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= @@ -27,7 +27,6 @@ github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrU github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= -github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -90,7 +89,6 @@ github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5Cc github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= -github.com/tidwall/gjson v1.11.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= github.com/tidwall/gjson v1.14.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA= @@ -123,7 +121,6 @@ golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -146,10 +143,8 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20211110154304-99a53858aa08/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220111092808-5a964db01320 h1:0jf+tOCoZ3LyutmCOWpVni1chK4VfFLhRsDK7MhqGRY= golang.org/x/sys v0.0.0-20220111092808-5a964db01320/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= @@ -175,8 +170,6 @@ google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQ google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= -google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= From a85f846a5f8e9c9dcfdbeffddf146063c9beaea4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=BA=90=E6=96=87=E9=9B=A8?= <41315874+fumiama@users.noreply.github.com> Date: Fri, 18 Feb 2022 18:38:58 +0800 Subject: [PATCH 18/93] fix: get_msg returns nil on local image element (#1342) * fix: get_msg returns nil on local image element * fix: make lint happy --- coolq/cqcode.go | 35 ++++++++++++++++++++++++++++++----- 1 file changed, 30 insertions(+), 5 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index dfd83e15..b08dc252 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -45,6 +45,7 @@ type PokeElement struct { type LocalImageElement struct { Stream io.ReadSeeker File string + Url string Flash bool EffectID int32 @@ -354,6 +355,20 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. } else { write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url), arg) } + case *LocalImageElement: + var arg string + if o.Flash { + arg = ",type=flash" + } + data, err := os.ReadFile(o.File) + if err == nil { + m := md5.Sum(data) + if ur { + write("[CQ:image,file=%s%s]", hex.EncodeToString(m[:])+".image", arg) + } else { + write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(m[:])+".image", CQCodeEscapeValue(o.Url), arg) + } + } case *message.GuildImageElement: write("[CQ:image,file=%s,url=%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url)) case *message.DiceElement: @@ -796,7 +811,13 @@ func (bot *CQBot) ConvertContentMessage(content []global.MSG, sourceType Message case "text": r = append(r, message.NewText(data["text"].(string))) case "image": - e, err := bot.makeImageOrVideoElem(map[string]string{"file": data["file"].(string)}, false, sourceType) + u, ok := data["url"] + d := make(map[string]string, 2) + if ok { + d["url"] = u.(string) + } + d["file"] = data["file"].(string) + e, err := bot.makeImageOrVideoElem(d, false, sourceType) if err != nil { log.Warnf("make image elem error: %v", err) continue @@ -1151,6 +1172,10 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou // makeImageOrVideoElem 图片 elem 生成器,单独拎出来,用于公用 func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceType MessageSourceType) (message.IMessageElement, error) { f := d["file"] + u, ok := d["url"] + if !ok { + u = "" + } if strings.HasPrefix(f, "http") { hash := md5.Sum([]byte(f)) cacheFile := path.Join(global.CachePath, hex.EncodeToString(hash[:])+".cache") @@ -1173,7 +1198,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy if video { return &LocalVideoElement{File: cacheFile}, nil } - return &LocalImageElement{File: cacheFile}, nil + return &LocalImageElement{File: cacheFile, Url: f}, nil } if strings.HasPrefix(f, "file") { fu, err := url.Parse(f) @@ -1199,14 +1224,14 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy if info.Size() == 0 || info.Size() >= maxImageSize { return nil, errors.New("invalid image size") } - return &LocalImageElement{File: fu.Path}, nil + return &LocalImageElement{File: fu.Path, Url: f}, nil } if strings.HasPrefix(f, "base64") && !video { b, err := param.Base64DecodeString(strings.TrimPrefix(f, "base64://")) if err != nil { return nil, err } - return &LocalImageElement{Stream: bytes.NewReader(b)}, nil + return &LocalImageElement{Stream: bytes.NewReader(b), Url: f}, nil } rawPath := path.Join(global.ImagePath, f) if video { @@ -1255,7 +1280,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy return nil, errors.New("invalid image") } if path.Ext(rawPath) != ".image" { - return &LocalImageElement{File: rawPath}, nil + return &LocalImageElement{File: rawPath, Url: u}, nil } b, err := os.ReadFile(rawPath) if err != nil { From 75bed6aabc24b083cc5afe05b711298ff8fd840e Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Feb 2022 19:11:43 +0800 Subject: [PATCH 19/93] coolq: clean readImageCache --- cmd/gocq/main.go | 2 +- coolq/cqcode.go | 45 +++++++++++++++++---------------------------- 2 files changed, 18 insertions(+), 29 deletions(-) diff --git a/cmd/gocq/main.go b/cmd/gocq/main.go index 2ce945b3..2b5952c9 100644 --- a/cmd/gocq/main.go +++ b/cmd/gocq/main.go @@ -81,7 +81,7 @@ func Main() { mkCacheDir := func(path string, _type string) { if !global.PathExists(path) { - if err := os.MkdirAll(path, 0o755); err != nil { + if err := os.MkdirAll(path, 0o644); err != nil { log.Fatalf("创建%s缓存文件夹失败: %v", _type, err) } } diff --git a/coolq/cqcode.go b/coolq/cqcode.go index b08dc252..1aa9b94d 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -45,7 +45,7 @@ type PokeElement struct { type LocalImageElement struct { Stream io.ReadSeeker File string - Url string + URL string Flash bool EffectID int32 @@ -366,7 +366,7 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. if ur { write("[CQ:image,file=%s%s]", hex.EncodeToString(m[:])+".image", arg) } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(m[:])+".image", CQCodeEscapeValue(o.Url), arg) + write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(m[:])+".image", cqcode.EscapeValue(o.URL), arg) } } case *message.GuildImageElement: @@ -1198,7 +1198,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy if video { return &LocalVideoElement{File: cacheFile}, nil } - return &LocalImageElement{File: cacheFile, Url: f}, nil + return &LocalImageElement{File: cacheFile, URL: f}, nil } if strings.HasPrefix(f, "file") { fu, err := url.Parse(f) @@ -1224,14 +1224,14 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy if info.Size() == 0 || info.Size() >= maxImageSize { return nil, errors.New("invalid image size") } - return &LocalImageElement{File: fu.Path, Url: f}, nil + return &LocalImageElement{File: fu.Path, URL: f}, nil } if strings.HasPrefix(f, "base64") && !video { b, err := param.Base64DecodeString(strings.TrimPrefix(f, "base64://")) if err != nil { return nil, err } - return &LocalImageElement{Stream: bytes.NewReader(b), Url: f}, nil + return &LocalImageElement{Stream: bytes.NewReader(b), URL: f}, nil } rawPath := path.Join(global.ImagePath, f) if video { @@ -1280,7 +1280,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy return nil, errors.New("invalid image") } if path.Ext(rawPath) != ".image" { - return &LocalImageElement{File: rawPath, Url: u}, nil + return &LocalImageElement{File: rawPath, URL: u}, nil } b, err := os.ReadFile(rawPath) if err != nil { @@ -1299,38 +1299,27 @@ func (bot *CQBot) readImageCache(b []byte, sourceType MessageSourceType) (messag size := r.ReadInt32() r.ReadString() imageURL := r.ReadString() - if size == 0 { - if imageURL != "" { - return bot.makeImageOrVideoElem(map[string]string{"file": imageURL}, false, sourceType) - } - return nil, errors.New("img size is 0") - } - if len(hash) != 16 { - return nil, errors.New("invalid hash") + if size == 0 && imageURL != "" { + return bot.makeImageOrVideoElem(map[string]string{"file": imageURL}, false, sourceType) } var rsp message.IMessageElement - if sourceType == MessageSourceGroup { + switch sourceType { // nolint:exhaustive + case MessageSourceGroup: rsp, err = bot.Client.QueryGroupImage(int64(rand.Uint32()), hash, size) - goto ok - } - if sourceType == MessageSourceGuildChannel { + case MessageSourceGuildChannel: if len(bot.Client.GuildService.Guilds) == 0 { err = errors.New("cannot query guild image: not any joined guild") - goto ok + break } guild := bot.Client.GuildService.Guilds[0] rsp, err = bot.Client.GuildService.QueryImage(guild.GuildId, guild.Channels[0].ChannelId, hash, uint64(size)) - goto ok + default: + rsp, err = bot.Client.QueryFriendImage(int64(rand.Uint32()), hash, size) } - rsp, err = bot.Client.QueryFriendImage(int64(rand.Uint32()), hash, size) -ok: - if err != nil { - if imageURL != "" { - return bot.makeImageOrVideoElem(map[string]string{"file": imageURL}, false, sourceType) - } - return nil, err + if err != nil && imageURL != "" { + return bot.makeImageOrVideoElem(map[string]string{"file": imageURL}, false, sourceType) } - return rsp, nil + return rsp, err } func (bot *CQBot) readVideoCache(b []byte) message.IMessageElement { From e6904d8dde3960f6f4ba06a2859220746cccf839 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 19 Feb 2022 18:55:28 +0800 Subject: [PATCH 20/93] internal/btree: implement file lock For #1366 --- internal/btree/btree.go | 18 ++++++++++++ internal/btree/file_lock_unix.go | 45 +++++++++++++++++++++++++++++ internal/btree/file_lock_windows.go | 28 ++++++++++++++++++ 3 files changed, 91 insertions(+) create mode 100644 internal/btree/file_lock_unix.go create mode 100644 internal/btree/file_lock_windows.go diff --git a/internal/btree/btree.go b/internal/btree/btree.go index 7b3b49cb..81adcb90 100644 --- a/internal/btree/btree.go +++ b/internal/btree/btree.go @@ -18,6 +18,10 @@ const ( tableStructSize = int(unsafe.Sizeof(table{})) ) +type fileLock interface { + release() error +} + type item struct { hash [hashSize]byte offset int64 @@ -48,6 +52,7 @@ type DB struct { alloc int64 cache [cacheSlots]cache + flock fileLock inAllocator bool deleteLarger bool fqueue [freeQueueLen]chunk @@ -108,6 +113,10 @@ func (d *DB) flushSuper() { // Open opens an existed btree file func Open(name string) (*DB, error) { + lock, err := newFileLock(name + ".lock") + if err != nil { + return nil, errors.New("文件被其他进程占用") + } btree := new(DB) fd, err := os.OpenFile(name, os.O_RDWR, 0o644) if err != nil { @@ -120,17 +129,23 @@ func Open(name string) (*DB, error) { btree.top = super.top btree.freeTop = super.freeTop btree.alloc = super.alloc + btree.flock = lock return btree, errors.Wrap(err, "btree read meta info failed") } // Create creates a database func Create(name string) (*DB, error) { + lock, err := newFileLock(name + ".lock") + if err != nil { + return nil, errors.New("文件被其他进程占用") + } btree := new(DB) fd, err := os.OpenFile(name, os.O_RDWR|os.O_TRUNC|os.O_CREATE, 0o644) if err != nil { return nil, errors.Wrap(err, "btree open file failed") } + btree.flock = lock btree.fd = fd btree.alloc = int64(superSize) btree.flushSuper() @@ -140,6 +155,9 @@ func Create(name string) (*DB, error) { // Close closes the database func (d *DB) Close() error { _ = d.fd.Sync() + if err := d.flock.release(); err != nil { + return err + } err := d.fd.Close() for i := 0; i < cacheSlots; i++ { d.cache[i] = cache{} diff --git a/internal/btree/file_lock_unix.go b/internal/btree/file_lock_unix.go new file mode 100644 index 00000000..89742843 --- /dev/null +++ b/internal/btree/file_lock_unix.go @@ -0,0 +1,45 @@ +//go:build darwin || dragonfly || freebsd || linux || netbsd || openbsd + +package btree + +import ( + "os" + "syscall" +) + +type unixFileLock struct { + f *os.File +} + +func (fl *unixFileLock) release() error { + if err := setFileLock(fl.f, false); err != nil { + return err + } + return fl.f.Close() +} + +func newFileLock(path string) (fl fileLock, err error) { + flag := os.O_RDWR + f, err := os.OpenFile(path, flag, 0) + if os.IsNotExist(err) { + f, err = os.OpenFile(path, flag|os.O_CREATE, 0644) + } + if err != nil { + return + } + err = setFileLock(f, true) + if err != nil { + f.Close() + return + } + fl = &unixFileLock{f: f} + return +} + +func setFileLock(f *os.File, lock bool) error { + how := syscall.LOCK_UN + if lock { + how = syscall.LOCK_EX + } + return syscall.Flock(int(f.Fd()), how|syscall.LOCK_NB) +} diff --git a/internal/btree/file_lock_windows.go b/internal/btree/file_lock_windows.go new file mode 100644 index 00000000..becdfade --- /dev/null +++ b/internal/btree/file_lock_windows.go @@ -0,0 +1,28 @@ +package btree + +import "syscall" + +type windowsFileLock struct { + fd syscall.Handle +} + +func (fl *windowsFileLock) release() error { + return syscall.Close(fl.fd) +} + +func newFileLock(path string) (fileLock, error) { + pathp, err := syscall.UTF16PtrFromString(path) + if err != nil { + return nil, err + } + + const access uint32 = syscall.GENERIC_READ | syscall.GENERIC_WRITE + fd, err := syscall.CreateFile(pathp, access, 0, nil, syscall.OPEN_EXISTING, syscall.FILE_ATTRIBUTE_NORMAL, 0) + if err == syscall.ERROR_FILE_NOT_FOUND { + fd, err = syscall.CreateFile(pathp, access, 0, nil, syscall.OPEN_ALWAYS, syscall.FILE_ATTRIBUTE_NORMAL, 0) + } + if err != nil { + return nil, err + } + return &windowsFileLock{fd: fd}, nil +} From ee749a45fceb39911966ef0993a3b1dd49273d33 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" <41898282+github-actions[bot]@users.noreply.github.com> Date: Sat, 19 Feb 2022 10:56:44 +0000 Subject: [PATCH 21/93] ci(chore): Fix stylings --- internal/btree/temp.1353328705.db.lock | 0 internal/btree/temp.1925824040.db.lock | 0 internal/btree/temp.2099670424.db.lock | 0 internal/btree/temp.2437681929.db.lock | 0 internal/btree/temp.315143417.db.lock | 0 internal/btree/temp.3409689178.db.lock | 0 6 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 internal/btree/temp.1353328705.db.lock create mode 100644 internal/btree/temp.1925824040.db.lock create mode 100644 internal/btree/temp.2099670424.db.lock create mode 100644 internal/btree/temp.2437681929.db.lock create mode 100644 internal/btree/temp.315143417.db.lock create mode 100644 internal/btree/temp.3409689178.db.lock diff --git a/internal/btree/temp.1353328705.db.lock b/internal/btree/temp.1353328705.db.lock new file mode 100644 index 00000000..e69de29b diff --git a/internal/btree/temp.1925824040.db.lock b/internal/btree/temp.1925824040.db.lock new file mode 100644 index 00000000..e69de29b diff --git a/internal/btree/temp.2099670424.db.lock b/internal/btree/temp.2099670424.db.lock new file mode 100644 index 00000000..e69de29b diff --git a/internal/btree/temp.2437681929.db.lock b/internal/btree/temp.2437681929.db.lock new file mode 100644 index 00000000..e69de29b diff --git a/internal/btree/temp.315143417.db.lock b/internal/btree/temp.315143417.db.lock new file mode 100644 index 00000000..e69de29b diff --git a/internal/btree/temp.3409689178.db.lock b/internal/btree/temp.3409689178.db.lock new file mode 100644 index 00000000..e69de29b From 31cdd337677fc607e6cf8adca203541cb7379aab Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 19 Feb 2022 20:19:17 +0800 Subject: [PATCH 22/93] internal/btree: remove lock file after testing --- .gitignore | 2 ++ internal/btree/btree_test.go | 11 ++++++++--- internal/btree/temp.1353328705.db.lock | 0 internal/btree/temp.1925824040.db.lock | 0 internal/btree/temp.2099670424.db.lock | 0 internal/btree/temp.2437681929.db.lock | 0 internal/btree/temp.315143417.db.lock | 0 internal/btree/temp.3409689178.db.lock | 0 8 files changed, 10 insertions(+), 3 deletions(-) delete mode 100644 internal/btree/temp.1353328705.db.lock delete mode 100644 internal/btree/temp.1925824040.db.lock delete mode 100644 internal/btree/temp.2099670424.db.lock delete mode 100644 internal/btree/temp.2437681929.db.lock delete mode 100644 internal/btree/temp.315143417.db.lock delete mode 100644 internal/btree/temp.3409689178.db.lock diff --git a/.gitignore b/.gitignore index d2ee21bf..43a051cd 100644 --- a/.gitignore +++ b/.gitignore @@ -7,3 +7,5 @@ session.token device.json data/ logs/ +internal/btree/*.lock +internal/btree/*.db \ No newline at end of file diff --git a/internal/btree/btree_test.go b/internal/btree/btree_test.go index 5d16c541..464c7ac7 100644 --- a/internal/btree/btree_test.go +++ b/internal/btree/btree_test.go @@ -16,16 +16,21 @@ func tempfile(t *testing.T) string { return temp.Name() } +func removedb(name string) { + os.Remove(name) + os.Remove(name + ".lock") +} + func TestCreate(t *testing.T) { f := tempfile(t) _, err := Create(f) assert2.NoError(t, err) - defer os.Remove(f) + defer removedb(f) } func TestBtree(t *testing.T) { f := tempfile(t) - defer os.Remove(f) + defer removedb(f) bt, err := Create(f) assert := assert2.New(t) assert.NoError(err) @@ -73,7 +78,7 @@ func testForeach(t *testing.T, elemSize int) { expected[i] = utils.RandomString(20) } f := tempfile(t) - defer os.Remove(f) + defer removedb(f) bt, err := Create(f) assert2.NoError(t, err) for _, v := range expected { diff --git a/internal/btree/temp.1353328705.db.lock b/internal/btree/temp.1353328705.db.lock deleted file mode 100644 index e69de29b..00000000 diff --git a/internal/btree/temp.1925824040.db.lock b/internal/btree/temp.1925824040.db.lock deleted file mode 100644 index e69de29b..00000000 diff --git a/internal/btree/temp.2099670424.db.lock b/internal/btree/temp.2099670424.db.lock deleted file mode 100644 index e69de29b..00000000 diff --git a/internal/btree/temp.2437681929.db.lock b/internal/btree/temp.2437681929.db.lock deleted file mode 100644 index e69de29b..00000000 diff --git a/internal/btree/temp.315143417.db.lock b/internal/btree/temp.315143417.db.lock deleted file mode 100644 index e69de29b..00000000 diff --git a/internal/btree/temp.3409689178.db.lock b/internal/btree/temp.3409689178.db.lock deleted file mode 100644 index e69de29b..00000000 From 2709c5d448fd285c7169d04fdffeb1c0adecf22b Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 20 Feb 2022 23:36:29 +0800 Subject: [PATCH 23/93] dep: update MiraiGo & revert disabling multi-thread upload --- coolq/bot.go | 9 ++------- go.mod | 2 +- go.sum | 11 +++++++++-- 3 files changed, 12 insertions(+), 10 deletions(-) diff --git a/coolq/bot.go b/coolq/bot.go index 099be8aa..950f63f4 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -7,7 +7,6 @@ import ( "fmt" "io" "os" - "path" "runtime/debug" "sync" "time" @@ -144,7 +143,7 @@ func (bot *CQBot) UploadLocalImageAsGroup(groupCode int64, img *LocalImageElemen if lawful, mime := base.IsLawfulImage(img.Stream); !lawful { return nil, errors.New("image type error: " + mime) } - i, err = bot.Client.UploadGroupImage(groupCode, img.Stream) + i, err = bot.Client.UploadGroupImage(groupCode, img.Stream, 4) if i != nil { i.Flash = img.Flash i.EffectID = img.EffectID @@ -159,11 +158,7 @@ func (bot *CQBot) UploadLocalVideo(target int64, v *LocalVideoElement) (*message return nil, err } defer func() { _ = video.Close() }() - hash, _ := utils.ComputeMd5AndLength(io.MultiReader(video, v.thumb)) - cacheFile := path.Join(global.CachePath, hex.EncodeToString(hash)+".cache") - _, _ = video.Seek(0, io.SeekStart) - _, _ = v.thumb.Seek(0, io.SeekStart) - return bot.Client.UploadGroupShortVideo(target, video, v.thumb, cacheFile) + return bot.Client.UploadGroupShortVideo(target, video, v.thumb, 4) } // UploadLocalImageAsPrivate 上传本地图片至私聊 diff --git a/go.mod b/go.mod index 6459e606..4f70cc18 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220218065747-0578942d86ab + github.com/Mrs4s/MiraiGo v0.0.0-20220220152607-5e8a5126989d github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index bb1a78cc..8ffb3232 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220218065747-0578942d86ab h1:kYJNHTBfkmEByDVIOvdCT5NMH9xbx915MOmpKGGXLWs= -github.com/Mrs4s/MiraiGo v0.0.0-20220218065747-0578942d86ab/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= +github.com/Mrs4s/MiraiGo v0.0.0-20220220152607-5e8a5126989d h1:Og/CXvf7cNq+GFpIe3Tjll500qD8L8wunTXC6bQRUxI= +github.com/Mrs4s/MiraiGo v0.0.0-20220220152607-5e8a5126989d/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= @@ -27,6 +27,7 @@ github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrU github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= +github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -89,6 +90,7 @@ github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5Cc github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= +github.com/tidwall/gjson v1.11.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= github.com/tidwall/gjson v1.14.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA= @@ -121,6 +123,7 @@ golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -143,8 +146,10 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20211110154304-99a53858aa08/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220111092808-5a964db01320 h1:0jf+tOCoZ3LyutmCOWpVni1chK4VfFLhRsDK7MhqGRY= golang.org/x/sys v0.0.0-20220111092808-5a964db01320/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= @@ -170,6 +175,8 @@ google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQ google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= +google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= +google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= From b833193926a8ab98bccbe6f7898585011d0d6d3e Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" <41898282+github-actions[bot]@users.noreply.github.com> Date: Sun, 20 Feb 2022 15:37:25 +0000 Subject: [PATCH 24/93] ci(chore): Fix stylings --- internal/param/param.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/internal/param/param.go b/internal/param/param.go index c38bf1cb..99e0e766 100644 --- a/internal/param/param.go +++ b/internal/param/param.go @@ -30,7 +30,7 @@ func EnsureBool(p interface{}, defaultVal bool) bool { if !j.Exists() { return defaultVal } - switch j.Type { // nolint + switch j.Type { case gjson.True: return true case gjson.False: From 19230b15113ae08e2fc26fdcde8d4379fee0555c Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 21 Feb 2022 17:49:02 +0800 Subject: [PATCH 25/93] coolq: move MessageSource to MiraiGo/message --- coolq/api.go | 40 ++++++++++++++++---------------- coolq/bot.go | 43 ++++++++++++++++------------------- coolq/converter.go | 6 ++--- coolq/cqcode.go | 54 ++++++++++++++------------------------------ coolq/cqcode_test.go | 7 +++--- coolq/event.go | 32 +++++++++++++------------- go.mod | 2 +- go.sum | 4 ++-- 8 files changed, 82 insertions(+), 106 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index b9cf3527..35a5d1d8 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -712,7 +712,7 @@ func (bot *CQBot) CQSendGroupMessage(groupID int64, m gjson.Result, autoEscape b var elem []message.IMessageElement if m.Type == gjson.JSON { - elem = bot.ConvertObjectMessage(m, MessageSourceGroup) + elem = bot.ConvertObjectMessage(m, message.SourceGroup) } else { str := m.String() if str == "" { @@ -722,7 +722,7 @@ func (bot *CQBot) CQSendGroupMessage(groupID int64, m gjson.Result, autoEscape b if autoEscape { elem = []message.IMessageElement{message.NewText(str)} } else { - elem = bot.ConvertStringMessage(str, MessageSourceGroup) + elem = bot.ConvertStringMessage(str, message.SourceGroup) } } fixAt(elem) @@ -766,7 +766,7 @@ func (bot *CQBot) CQSendGuildChannelMessage(guildID, channelID uint64, m gjson.R var elem []message.IMessageElement if m.Type == gjson.JSON { - elem = bot.ConvertObjectMessage(m, MessageSourceGuildChannel) + elem = bot.ConvertObjectMessage(m, message.SourceGuildChannel) } else { str := m.String() if str == "" { @@ -776,7 +776,7 @@ func (bot *CQBot) CQSendGuildChannelMessage(guildID, channelID uint64, m gjson.R if autoEscape { elem = []message.IMessageElement{message.NewText(str)} } else { - elem = bot.ConvertStringMessage(str, MessageSourceGuildChannel) + elem = bot.ConvertStringMessage(str, message.SourceGuildChannel) } } fixAt(elem) @@ -833,7 +833,7 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F } return int32(msgTime) }(), - Message: resolveElement(bot.ConvertContentMessage(m.Content, MessageSourceGroup)), + Message: resolveElement(bot.ConvertContentMessage(m.Content, message.SourceGroup)), } } log.Warnf("警告: 引用消息 %v 错误或数据库未开启.", e.Get("data.id").Str) @@ -865,7 +865,7 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F } } } - content := bot.ConvertObjectMessage(c, MessageSourceGroup) + content := bot.ConvertObjectMessage(c, message.SourceGroup) if uin != 0 && name != "" && len(content) > 0 { return &message.ForwardNode{ SenderId: uin, @@ -932,7 +932,7 @@ func (bot *CQBot) CQSendGroupForwardMessage(groupID int64, m gjson.Result) globa func (bot *CQBot) CQSendPrivateMessage(userID int64, groupID int64, m gjson.Result, autoEscape bool) global.MSG { var elem []message.IMessageElement if m.Type == gjson.JSON { - elem = bot.ConvertObjectMessage(m, MessageSourcePrivate) + elem = bot.ConvertObjectMessage(m, message.SourcePrivate) } else { str := m.String() if str == "" { @@ -941,7 +941,7 @@ func (bot *CQBot) CQSendPrivateMessage(userID int64, groupID int64, m gjson.Resu if autoEscape { elem = []message.IMessageElement{message.NewText(str)} } else { - elem = bot.ConvertStringMessage(str, MessageSourcePrivate) + elem = bot.ConvertStringMessage(str, message.SourcePrivate) } } mid := bot.SendPrivateMessage(userID, groupID, &message.SendingMessage{Elements: elem}) @@ -1525,7 +1525,7 @@ func (bot *CQBot) CQGetForwardMessage(resID string) global.MSG { r := make([]global.MSG, len(nodes)) for i, n := range nodes { bot.checkMedia(n.Message, 0) - content := ToFormattedMessage(n.Message, MessageSource{SourceType: MessageSourceGroup}, false) + content := ToFormattedMessage(n.Message, message.Source{SourceType: message.SourceGroup}, false) if len(n.Message) == 1 { if forward, ok := n.Message[0].(*message.ForwardMessage); ok { content = transformNodes(forward.Nodes) @@ -1573,9 +1573,9 @@ func (bot *CQBot) CQGetMessage(messageID int32) global.MSG { switch o := msg.(type) { case *db.StoredGroupMessage: m["group_id"] = o.GroupCode - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, MessageSourceGroup), MessageSource{SourceType: MessageSourceGroup, PrimaryID: uint64(o.GroupCode)}, false) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, message.SourceGroup), message.Source{SourceType: message.SourceGroup, PrimaryID: o.GroupCode}, false) case *db.StoredPrivateMessage: - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, MessageSourcePrivate), MessageSource{SourceType: MessageSourcePrivate}, false) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, message.SourcePrivate), message.Source{SourceType: message.SourcePrivate}, false) } return OK(m) } @@ -1591,21 +1591,21 @@ func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { m := global.MSG{ "message_id": messageID, "message_source": func() string { - if source.SourceType == MessageSourceGuildDirect { + if source.SourceType == message.SourceGuildDirect { return "direct" } return "channel" }(), "message_seq": seq, - "guild_id": fU64(source.PrimaryID), + "guild_id": fU64(uint64(source.PrimaryID)), "reactions": []int{}, } // nolint: exhaustive switch source.SourceType { - case MessageSourceGuildChannel: - m["channel_id"] = fU64(source.SubID) + case message.SourceGuildChannel: + m["channel_id"] = fU64(uint64(source.SecondaryID)) if noCache { - pull, err := bot.Client.GuildService.PullGuildChannelMessage(source.PrimaryID, source.SubID, seq, seq) + pull, err := bot.Client.GuildService.PullGuildChannelMessage(uint64(source.PrimaryID), uint64(source.SecondaryID), seq, seq) if err != nil { log.Warnf("获取消息时出现错误: %v", err) return Failed(100, "API_ERROR", err.Error()) @@ -1635,11 +1635,11 @@ func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { "tiny_id": fU64(channelMsgByDB.Attribute.SenderTinyID), "nickname": channelMsgByDB.Attribute.SenderName, } - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(channelMsgByDB.Content, MessageSourceGuildChannel), *source) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(channelMsgByDB.Content, message.SourceGuildChannel), *source) } - case MessageSourceGuildDirect: + case message.SourceGuildDirect: // todo(mrs4s): 支持 direct 消息 - m["tiny_id"] = fU64(source.SubID) + m["tiny_id"] = fU64(uint64(source.SecondaryID)) } return OK(m) } @@ -1737,7 +1737,7 @@ func (bot *CQBot) CQCanSendRecord() global.MSG { // @route(ocr_image,".ocr_image") // @rename(image_id->image) func (bot *CQBot) CQOcrImage(imageID string) global.MSG { - img, err := bot.makeImageOrVideoElem(map[string]string{"file": imageID}, false, MessageSourceGroup) + img, err := bot.makeImageOrVideoElem(map[string]string{"file": imageID}, false, message.SourceGroup) if err != nil { log.Warnf("load image error: %v", err) return Failed(100, "LOAD_FILE_ERROR", err.Error()) diff --git a/coolq/bot.go b/coolq/bot.go index 950f63f4..931c99b4 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -5,7 +5,6 @@ import ( "encoding/hex" "encoding/json" "fmt" - "io" "os" "runtime/debug" "sync" @@ -152,13 +151,13 @@ func (bot *CQBot) UploadLocalImageAsGroup(groupCode int64, img *LocalImageElemen } // UploadLocalVideo 上传本地短视频至群聊 -func (bot *CQBot) UploadLocalVideo(target int64, v *LocalVideoElement) (*message.ShortVideoElement, error) { +func (bot *CQBot) UploadLocalVideo(target message.Source, v *LocalVideoElement) (*message.ShortVideoElement, error) { video, err := os.Open(v.File) if err != nil { return nil, err } defer func() { _ = video.Close() }() - return bot.Client.UploadGroupShortVideo(target, video, v.thumb, 4) + return bot.Client.UploadShortVideo(target, video, v.thumb, 4) } // UploadLocalImageAsPrivate 上传本地图片至私聊 @@ -197,18 +196,6 @@ func (bot *CQBot) UploadLocalImageAsGuildChannel(guildID, channelID uint64, img return bot.Client.GuildService.UploadGuildImage(guildID, channelID, img.Stream) } -func (bot *CQBot) uploadGuildVideo(i *LocalVideoElement, guildID, channelID uint64) (*message.ShortVideoElement, error) { - video, err := os.Open(i.File) - if err != nil { - return nil, err - } - defer func() { _ = video.Close() }() - _, _ = video.Seek(0, io.SeekStart) - _, _ = i.thumb.Seek(0, io.SeekStart) - n, err := bot.Client.UploadGuildShortVideo(guildID, channelID, video, i.thumb) - return n, err -} - // SendGroupMessage 发送群消息 func (bot *CQBot) SendGroupMessage(groupID int64, m *message.SendingMessage) int32 { newElem := make([]message.IMessageElement, 0, len(m.Elements)) @@ -368,7 +355,11 @@ func (bot *CQBot) SendGuildChannelMessage(guildID, channelID uint64, m *message. e = n case *LocalVideoElement: - n, err := bot.uploadGuildVideo(i, guildID, channelID) + n, err := bot.UploadLocalVideo(message.Source{ + SourceType: message.SourceGuildChannel, + PrimaryID: int64(guildID), + SecondaryID: int64(channelID), + }, i) if err != nil { log.Warnf("警告: 频道 %d 消息%s上传失败: %v", channelID, e.Type().String(), err) continue @@ -518,7 +509,7 @@ func (bot *CQBot) InsertTempMessage(target int64, m *message.TempMessage) int32 // InsertGuildChannelMessage 频道消息入数据库 func (bot *CQBot) InsertGuildChannelMessage(m *message.GuildChannelMessage) string { - id := encodeGuildMessageID(m.GuildId, m.ChannelId, m.Id, MessageSourceGuildChannel) + id := encodeGuildMessageID(m.GuildId, m.ChannelId, m.Id, message.SourceGuildChannel) msg := &db.StoredGuildChannelMessage{ ID: id, Attribute: &db.StoredGuildMessageAttribute{ @@ -597,7 +588,11 @@ func (bot *CQBot) uploadMedia(raw message.IMessageElement, target int64, group b } return bot.Client.UploadPrivatePtt(target, bytes.NewReader(m.Data)) case *LocalVideoElement: - return bot.UploadLocalVideo(target, m) + source := message.Source{ + SourceType: message.SourceGroup, + PrimaryID: target, + } + return bot.UploadLocalVideo(source, m) } return nil, errors.New("unsupported message element type") } @@ -613,7 +608,7 @@ func encodeMessageID(target int64, seq int32) string { // encodeGuildMessageID 将频道信息编码为字符串 // 当信息来源为 Channel 时 primaryID 为 guildID , subID 为 channelID // 当信息来源为 Direct 时 primaryID 为 guildID , subID 为 tinyID -func encodeGuildMessageID(primaryID, subID, seq uint64, source MessageSourceType) string { +func encodeGuildMessageID(primaryID, subID, seq uint64, source message.SourceType) string { return base64.StdEncoding.EncodeToString(binary.NewWriterF(func(w *binary.Writer) { w.WriteByte(byte(source)) w.WriteUInt64(primaryID) @@ -622,16 +617,16 @@ func encodeGuildMessageID(primaryID, subID, seq uint64, source MessageSourceType })) } -func decodeGuildMessageID(id string) (source *MessageSource, seq uint64) { +func decodeGuildMessageID(id string) (source *message.Source, seq uint64) { b, _ := base64.StdEncoding.DecodeString(id) if len(b) < 25 { return } r := binary.NewReader(b) - source = &MessageSource{ - SourceType: MessageSourceType(r.ReadByte()), - PrimaryID: uint64(r.ReadInt64()), - SubID: uint64(r.ReadInt64()), + source = &message.Source{ + SourceType: message.SourceType(r.ReadByte()), + PrimaryID: r.ReadInt64(), + SecondaryID: r.ReadInt64(), } seq = uint64(r.ReadInt64()) return diff --git a/coolq/converter.go b/coolq/converter.go index 154f3540..fbe3d4c5 100644 --- a/coolq/converter.go +++ b/coolq/converter.go @@ -60,9 +60,9 @@ func convertGuildMemberInfo(m []*client.GuildMemberInfo) (r []global.MSG) { } func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { - source := MessageSource{ - SourceType: MessageSourceGroup, - PrimaryID: uint64(m.GroupCode), + source := message.Source{ + SourceType: message.SourceGroup, + PrimaryID: m.GroupCode, } cqm := ToStringMessage(m.Elements, source, true) postType := "message" diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 1aa9b94d..5434d8df 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -63,26 +63,6 @@ type LocalVideoElement struct { thumb io.ReadSeeker } -// MessageSource 消息来源 -// 如果为私聊或者群聊, PrimaryID 将代表群号/QQ号 -// 如果为频道, PrimaryID 为 GuildID, SubID 为 ChannelID -type MessageSource struct { - SourceType MessageSourceType - PrimaryID uint64 - SubID uint64 -} - -// MessageSourceType 消息来源类型 -type MessageSourceType byte - -// MessageSourceType 常量 -const ( - MessageSourcePrivate MessageSourceType = 1 << iota - MessageSourceGroup - MessageSourceGuildChannel - MessageSourceGuildDirect -) - const ( maxImageSize = 1024 * 1024 * 30 // 30MB maxVideoSize = 1024 * 1024 * 100 // 100MB @@ -104,10 +84,10 @@ func (e *PokeElement) Type() message.ElementType { return message.At } -func replyID(r *message.ReplyElement, source MessageSource) int32 { +func replyID(r *message.ReplyElement, source message.Source) int32 { id := int64(source.PrimaryID) seq := r.ReplySeq - if source.SourceType == MessageSourcePrivate { + if source.SourceType == message.SourcePrivate { // 私聊似乎腾讯服务器有bug? seq = int32(uint16(seq)) id = r.Sender @@ -119,14 +99,14 @@ func replyID(r *message.ReplyElement, source MessageSource) int32 { } // ToArrayMessage 将消息元素数组转为MSG数组以用于消息上报 -func ToArrayMessage(e []message.IMessageElement, source MessageSource) (r []global.MSG) { +func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []global.MSG) { r = make([]global.MSG, 0, len(e)) m := &message.SendingMessage{Elements: e} reply := m.FirstOrNil(func(e message.IMessageElement) bool { _, ok := e.(*message.ReplyElement) return ok }) - if reply != nil && source.SourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { + if reply != nil && source.SourceType&(message.SourceGroup|message.SourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) id := replyID(replyElem, source) if base.ExtraReplyData { @@ -270,7 +250,7 @@ func ToArrayMessage(e []message.IMessageElement, source MessageSource) (r []glob } // ToStringMessage 将消息元素数组转为字符串以用于消息上报 -func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw ...bool) (r string) { +func ToStringMessage(e []message.IMessageElement, source message.Source, isRaw ...bool) (r string) { sb := global.NewBuffer() sb.Reset() write := func(format string, a ...interface{}) { @@ -286,7 +266,7 @@ func ToStringMessage(e []message.IMessageElement, source MessageSource, isRaw .. _, ok := e.(*message.ReplyElement) return ok }) - if reply != nil && source.SourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { + if reply != nil && source.SourceType&(message.SourceGroup|message.SourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) id := replyID(replyElem, source) if base.ExtraReplyData { @@ -511,7 +491,7 @@ func ToMessageContent(e []message.IMessageElement) (r []global.MSG) { } // ConvertStringMessage 将消息字符串转为消息元素数组 -func (bot *CQBot) ConvertStringMessage(raw string, sourceType MessageSourceType) (r []message.IMessageElement) { +func (bot *CQBot) ConvertStringMessage(raw string, sourceType message.SourceType) (r []message.IMessageElement) { var t, key string d := map[string]string{} @@ -684,11 +664,11 @@ func (bot *CQBot) ConvertStringMessage(raw string, sourceType MessageSourceType) } // ConvertObjectMessage 将消息JSON对象转为消息元素数组 -func (bot *CQBot) ConvertObjectMessage(m gjson.Result, sourceType MessageSourceType) (r []message.IMessageElement) { +func (bot *CQBot) ConvertObjectMessage(m gjson.Result, sourceType message.SourceType) (r []message.IMessageElement) { d := make(map[string]string) convertElem := func(e gjson.Result) { t := e.Get("type").Str - if t == "reply" && sourceType&(MessageSourceGroup|MessageSourcePrivate) != 0 { + if t == "reply" && sourceType&(message.SourceGroup|message.SourcePrivate) != 0 { if len(r) > 0 { if _, ok := r[0].(*message.ReplyElement); ok { log.Warnf("警告: 一条信息只能包含一个 Reply 元素.") @@ -804,7 +784,7 @@ func (bot *CQBot) ConvertObjectMessage(m gjson.Result, sourceType MessageSourceT } // ConvertContentMessage 将数据库用的 content 转换为消息元素数组 -func (bot *CQBot) ConvertContentMessage(content []global.MSG, sourceType MessageSourceType) (r []message.IMessageElement) { +func (bot *CQBot) ConvertContentMessage(content []global.MSG, sourceType message.SourceType) (r []message.IMessageElement) { for _, c := range content { data := c["data"].(global.MSG) switch c["type"] { @@ -883,7 +863,7 @@ func (bot *CQBot) ConvertContentMessage(content []global.MSG, sourceType Message // 返回 interface{} 存在三种类型 // // message.IMessageElement []message.IMessageElement nil -func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSourceType) (m interface{}, err error) { +func (bot *CQBot) ToElement(t string, d map[string]string, sourceType message.SourceType) (m interface{}, err error) { switch t { case "text": if base.SplitURL { @@ -1117,7 +1097,7 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou if err != nil { return nil, errors.New("send cardimage faild") } - return bot.makeShowPic(img, source, brief, icon, minWidth, minHeight, maxWidth, maxHeight, sourceType == MessageSourceGroup) + return bot.makeShowPic(img, source, brief, icon, minWidth, minHeight, maxWidth, maxHeight, sourceType == message.SourceGroup) case "video": file, err := bot.makeImageOrVideoElem(d, true, sourceType) if err != nil { @@ -1170,7 +1150,7 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType MessageSou } // makeImageOrVideoElem 图片 elem 生成器,单独拎出来,用于公用 -func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceType MessageSourceType) (message.IMessageElement, error) { +func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceType message.SourceType) (message.IMessageElement, error) { f := d["file"] u, ok := d["url"] if !ok { @@ -1254,7 +1234,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy return bot.readVideoCache(b), nil } // 目前频道内上传的图片均无法被查询到, 需要单独处理 - if sourceType == MessageSourceGuildChannel { + if sourceType == message.SourceGuildChannel { cacheFile := path.Join(global.ImagePath, "guild-images", f) if global.PathExists(cacheFile) { return &LocalImageElement{File: cacheFile}, nil @@ -1289,7 +1269,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy return bot.readImageCache(b, sourceType) } -func (bot *CQBot) readImageCache(b []byte, sourceType MessageSourceType) (message.IMessageElement, error) { +func (bot *CQBot) readImageCache(b []byte, sourceType message.SourceType) (message.IMessageElement, error) { var err error if len(b) < 20 { return nil, errors.New("invalid cache") @@ -1304,9 +1284,9 @@ func (bot *CQBot) readImageCache(b []byte, sourceType MessageSourceType) (messag } var rsp message.IMessageElement switch sourceType { // nolint:exhaustive - case MessageSourceGroup: + case message.SourceGroup: rsp, err = bot.Client.QueryGroupImage(int64(rand.Uint32()), hash, size) - case MessageSourceGuildChannel: + case message.SourceGuildChannel: if len(bot.Client.GuildService.Guilds) == 0 { err = errors.New("cannot query guild image: not any joined guild") break diff --git a/coolq/cqcode_test.go b/coolq/cqcode_test.go index 0c8bf7ed..30c16369 100644 --- a/coolq/cqcode_test.go +++ b/coolq/cqcode_test.go @@ -5,6 +5,7 @@ import ( "strings" "testing" + "github.com/Mrs4s/MiraiGo/message" "github.com/Mrs4s/MiraiGo/utils" "github.com/stretchr/testify/assert" "github.com/tidwall/gjson" @@ -15,7 +16,7 @@ import ( var bot = CQBot{} func TestCQBot_ConvertStringMessage(t *testing.T) { - for _, v := range bot.ConvertStringMessage(`[CQ:face,id=115,text=111][CQ:face,id=217]] [CQ:text,text=123] [`, MessageSourcePrivate) { + for _, v := range bot.ConvertStringMessage(`[CQ:face,id=115,text=111][CQ:face,id=217]] [CQ:text,text=123] [`, message.SourcePrivate) { fmt.Println(v) } } @@ -27,14 +28,14 @@ var ( func BenchmarkCQBot_ConvertStringMessage(b *testing.B) { for i := 0; i < b.N; i++ { - bot.ConvertStringMessage(bench, MessageSourcePrivate) + bot.ConvertStringMessage(bench, message.SourcePrivate) } b.SetBytes(int64(len(bench))) } func BenchmarkCQBot_ConvertObjectMessage(b *testing.B) { for i := 0; i < b.N; i++ { - bot.ConvertObjectMessage(benchArray, MessageSourcePrivate) + bot.ConvertObjectMessage(benchArray, message.SourcePrivate) } } diff --git a/coolq/event.go b/coolq/event.go index d89707db..fd2f9413 100644 --- a/coolq/event.go +++ b/coolq/event.go @@ -21,7 +21,7 @@ import ( ) // ToFormattedMessage 将给定[]message.IMessageElement转换为通过coolq.SetMessageFormat所定义的消息上报格式 -func ToFormattedMessage(e []message.IMessageElement, source MessageSource, isRaw ...bool) (r interface{}) { +func ToFormattedMessage(e []message.IMessageElement, source message.Source, isRaw ...bool) (r interface{}) { if base.PostFormat == "string" { r = ToStringMessage(e, source, isRaw...) } else if base.PostFormat == "array" { @@ -32,9 +32,9 @@ func ToFormattedMessage(e []message.IMessageElement, source MessageSource, isRaw func (bot *CQBot) privateMessageEvent(c *client.QQClient, m *message.PrivateMessage) { bot.checkMedia(m.Elements, m.Sender.Uin) - source := MessageSource{ - SourceType: MessageSourcePrivate, - PrimaryID: uint64(m.Sender.Uin), + source := message.Source{ + SourceType: message.SourcePrivate, + PrimaryID: m.Sender.Uin, } cqm := ToStringMessage(m.Elements, source, true) id := bot.InsertPrivateMessage(m) @@ -89,9 +89,9 @@ func (bot *CQBot) groupMessageEvent(c *client.QQClient, m *message.GroupMessage) return } } - source := MessageSource{ - SourceType: MessageSourceGroup, - PrimaryID: uint64(m.GroupCode), + source := message.Source{ + SourceType: message.SourceGroup, + PrimaryID: m.GroupCode, } cqm := ToStringMessage(m.Elements, source, true) id := bot.InsertGroupMessage(m) @@ -107,9 +107,9 @@ func (bot *CQBot) groupMessageEvent(c *client.QQClient, m *message.GroupMessage) func (bot *CQBot) tempMessageEvent(c *client.QQClient, e *client.TempMessageEvent) { m := e.Message bot.checkMedia(m.Elements, m.Sender.Uin) - source := MessageSource{ - SourceType: MessageSourcePrivate, - PrimaryID: uint64(e.Session.Sender), + source := message.Source{ + SourceType: message.SourcePrivate, + PrimaryID: e.Session.Sender, } cqm := ToStringMessage(m.Elements, source, true) bot.tempSessionCache.Store(m.Sender.Uin, e.Session) @@ -149,10 +149,10 @@ func (bot *CQBot) guildChannelMessageEvent(c *client.QQClient, m *message.GuildC return } channel := guild.FindChannel(m.ChannelId) - source := MessageSource{ - SourceType: MessageSourceGuildChannel, - PrimaryID: m.GuildId, - SubID: m.ChannelId, + source := message.Source{ + SourceType: message.SourceGuildChannel, + PrimaryID: int64(m.GuildId), + SecondaryID: int64(m.ChannelId), } log.Infof("收到来自频道 %v(%v) 子频道 %v(%v) 内 %v(%v) 的消息: %v", guild.GuildName, guild.GuildId, channel.ChannelName, m.ChannelId, m.Sender.Nickname, m.Sender.TinyId, ToStringMessage(m.Elements, source, true)) id := bot.InsertGuildChannelMessage(m) @@ -181,7 +181,7 @@ func (bot *CQBot) guildMessageReactionsUpdatedEvent(c *client.QQClient, e *clien if guild == nil { return } - msgID := encodeGuildMessageID(e.GuildId, e.ChannelId, e.MessageId, MessageSourceGuildChannel) + msgID := encodeGuildMessageID(e.GuildId, e.ChannelId, e.MessageId, message.SourceGuildChannel) str := fmt.Sprintf("频道 %v(%v) 消息 %v 表情贴片已更新: ", guild.GuildName, guild.GuildId, msgID) currentReactions := make([]global.MSG, len(e.CurrentReactions)) for i, r := range e.CurrentReactions { @@ -228,7 +228,7 @@ func (bot *CQBot) guildChannelMessageRecalledEvent(c *client.QQClient, e *client log.Errorf("处理频道撤回事件时出现错误: 获取操作者资料时出现错误 %v", err) return } - msgID := encodeGuildMessageID(e.GuildId, e.ChannelId, e.MessageId, MessageSourceGuildChannel) + msgID := encodeGuildMessageID(e.GuildId, e.ChannelId, e.MessageId, message.SourceGuildChannel) log.Infof("用户 %v(%v) 撤回了频道 %v(%v) 子频道 %v(%v) 的消息 %v", operator.Nickname, operator.TinyId, guild.GuildName, guild.GuildId, channel.ChannelName, channel.ChannelId, msgID) bot.dispatchEventMessage(global.MSG{ "post_type": "notice", diff --git a/go.mod b/go.mod index 4f70cc18..2ee23ee4 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220220152607-5e8a5126989d + github.com/Mrs4s/MiraiGo v0.0.0-20220221093105-1e32793eef06 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index 8ffb3232..f8c754d9 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220220152607-5e8a5126989d h1:Og/CXvf7cNq+GFpIe3Tjll500qD8L8wunTXC6bQRUxI= -github.com/Mrs4s/MiraiGo v0.0.0-20220220152607-5e8a5126989d/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= +github.com/Mrs4s/MiraiGo v0.0.0-20220221093105-1e32793eef06 h1:9V7AhNUPJ1vqLAoXjwLdpv06hJWs15UdgYbKaHww60s= +github.com/Mrs4s/MiraiGo v0.0.0-20220221093105-1e32793eef06/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From c7f0aed1b771a458e868af68150cbafc1ad9a6df Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 21 Feb 2022 23:44:49 +0800 Subject: [PATCH 26/93] coolq: adapt new MiraiGo upload api --- coolq/api.go | 16 ++++- coolq/bot.go | 148 +++++++++++++++------------------------- coolq/cqcode.go | 16 ++--- go.mod | 2 +- go.sum | 4 +- internal/param/param.go | 2 +- 6 files changed, 80 insertions(+), 108 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 35a5d1d8..bcb7830a 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -791,6 +791,7 @@ func (bot *CQBot) CQSendGuildChannelMessage(guildID, channelID uint64, m gjson.R func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.ForwardElement { ts := time.Now().Add(-time.Minute * 5) fm := message.NewForwardMessage() + source := message.Source{SourceType: message.SourceGroup, PrimaryID: groupID} var lazyUpload []func() var wg sync.WaitGroup @@ -798,11 +799,22 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F for i, elem := range elems { iescape := i switch o := elem.(type) { - case *LocalImageElement, *LocalVideoElement: + case *LocalVideoElement: wg.Add(1) lazyUpload = append(lazyUpload, func() { defer wg.Done() - gm, err := bot.uploadMedia(o, groupID, true) + gm, err := bot.uploadLocalVideo(source, o) + if err != nil { + log.Warnf("警告: 群 %d %s上传失败: %v", groupID, o.Type().String(), err) + } else { + elems[iescape] = gm + } + }) + case *LocalImageElement: + wg.Add(1) + lazyUpload = append(lazyUpload, func() { + defer wg.Done() + gm, err := bot.uploadLocalImage(source, o) if err != nil { log.Warnf("警告: 群 %d %s上传失败: %v", groupID, o.Type().String(), err) } else { diff --git a/coolq/bot.go b/coolq/bot.go index 931c99b4..00a53c8c 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -129,8 +129,8 @@ func (bot *CQBot) OnEventPush(f func(e *Event)) { bot.lock.Unlock() } -// UploadLocalImageAsGroup 上传本地图片至群聊 -func (bot *CQBot) UploadLocalImageAsGroup(groupCode int64, img *LocalImageElement) (i *message.GroupImageElement, err error) { +// uploadLocalImage 上传本地图片 +func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement) (i message.IMessageElement, err error) { if img.File != "" { f, err := os.Open(img.File) if err != nil { @@ -142,16 +142,19 @@ func (bot *CQBot) UploadLocalImageAsGroup(groupCode int64, img *LocalImageElemen if lawful, mime := base.IsLawfulImage(img.Stream); !lawful { return nil, errors.New("image type error: " + mime) } - i, err = bot.Client.UploadGroupImage(groupCode, img.Stream, 4) - if i != nil { + i, err = bot.Client.UploadImage(target, img.Stream, 4) + switch i := i.(type) { + case *message.GroupImageElement: i.Flash = img.Flash i.EffectID = img.EffectID + case *message.FriendImageElement: + i.Flash = img.Flash } return } -// UploadLocalVideo 上传本地短视频至群聊 -func (bot *CQBot) UploadLocalVideo(target message.Source, v *LocalVideoElement) (*message.ShortVideoElement, error) { +// uploadLocalVideo 上传本地短视频至群聊 +func (bot *CQBot) uploadLocalVideo(target message.Source, v *LocalVideoElement) (*message.ShortVideoElement, error) { video, err := os.Open(v.File) if err != nil { return nil, err @@ -160,55 +163,52 @@ func (bot *CQBot) UploadLocalVideo(target message.Source, v *LocalVideoElement) return bot.Client.UploadShortVideo(target, video, v.thumb, 4) } -// UploadLocalImageAsPrivate 上传本地图片至私聊 -func (bot *CQBot) UploadLocalImageAsPrivate(userID int64, img *LocalImageElement) (i *message.FriendImageElement, err error) { - if img.File != "" { - f, err := os.Open(img.File) - if err != nil { - return nil, errors.Wrap(err, "open image error") +func (bot *CQBot) uploadMedia(target message.Source, elements []message.IMessageElement) []message.IMessageElement { + var j int + for _, m := range elements { + raw := m // upload failed will make m nil, so copy it + var err error + switch e := m.(type) { + case *LocalImageElement: + m, err = bot.uploadLocalImage(target, e) + case *message.VoiceElement: + if target.SourceType == message.SourceGuildChannel { + continue // todo + } + m, err = bot.Client.UploadVoice(target, bytes.NewReader(e.Data)) + case *LocalVideoElement: + m, err = bot.uploadLocalVideo(target, e) } - defer func() { _ = f.Close() }() - img.Stream = f - } - if lawful, mime := base.IsLawfulImage(img.Stream); !lawful { - return nil, errors.New("image type error: " + mime) - } - i, err = bot.Client.UploadPrivateImage(userID, img.Stream) - if i != nil { - i.Flash = img.Flash - } - return -} - -// UploadLocalImageAsGuildChannel 上传本地图片至频道 -func (bot *CQBot) UploadLocalImageAsGuildChannel(guildID, channelID uint64, img *LocalImageElement) (*message.GuildImageElement, error) { - if img.File != "" { - f, err := os.Open(img.File) if err != nil { - return nil, errors.Wrap(err, "open image error") + var source string + switch target.SourceType { // nolint:exhaustive + case message.SourceGroup: + source = "群" + case message.SourcePrivate: + source = "私聊" + case message.SourceGuildChannel: + source = "频道" + } + log.Warnf("警告: %s %d %s上传失败: %v", source, target.PrimaryID, raw.Type().String(), err) + continue } - defer func() { _ = f.Close() }() - img.Stream = f - } - if lawful, mime := base.IsLawfulImage(img.Stream); !lawful { - return nil, errors.New("image type error: " + mime) + elements[j] = m + j++ } - return bot.Client.GuildService.UploadGuildImage(guildID, channelID, img.Stream) + return elements[:j] } // SendGroupMessage 发送群消息 func (bot *CQBot) SendGroupMessage(groupID int64, m *message.SendingMessage) int32 { newElem := make([]message.IMessageElement, 0, len(m.Elements)) group := bot.Client.FindGroup(groupID) + source := message.Source{ + SourceType: message.SourceGroup, + PrimaryID: groupID, + } + m.Elements = bot.uploadMedia(source, m.Elements) for _, e := range m.Elements { switch i := e.(type) { - case *LocalImageElement, *message.VoiceElement, *LocalVideoElement: - i, err := bot.uploadMedia(i, groupID, true) - if err != nil { - log.Warnf("警告: 群 %d 消息%s上传失败: %v", groupID, e.Type().String(), err) - continue - } - e = i case *PokeElement: if group != nil { if mem := group.FindMember(i.Target); mem != nil { @@ -247,15 +247,13 @@ func (bot *CQBot) SendGroupMessage(groupID int64, m *message.SendingMessage) int // SendPrivateMessage 发送私聊消息 func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.SendingMessage) int32 { newElem := make([]message.IMessageElement, 0, len(m.Elements)) + source := message.Source{ + SourceType: message.SourcePrivate, + PrimaryID: target, + } + m.Elements = bot.uploadMedia(source, m.Elements) for _, e := range m.Elements { switch i := e.(type) { - case *LocalImageElement, *message.VoiceElement, *LocalVideoElement: - i, err := bot.uploadMedia(i, target, false) - if err != nil { - log.Warnf("警告: 私聊 %d 消息%s上传失败: %v", target, e.Type().String(), err) - continue - } - e = i case *PokeElement: bot.Client.SendFriendPoke(i.Target) return 0 @@ -344,33 +342,19 @@ func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.Sen // SendGuildChannelMessage 发送频道消息 func (bot *CQBot) SendGuildChannelMessage(guildID, channelID uint64, m *message.SendingMessage) string { newElem := make([]message.IMessageElement, 0, len(m.Elements)) + source := message.Source{ + SourceType: message.SourceGuildChannel, + PrimaryID: int64(guildID), + SecondaryID: int64(channelID), + } + m.Elements = bot.uploadMedia(source, m.Elements) for _, e := range m.Elements { switch i := e.(type) { - case *LocalImageElement: - n, err := bot.UploadLocalImageAsGuildChannel(guildID, channelID, i) - if err != nil { - log.Warnf("警告: 频道 %d 消息%s上传失败: %v", channelID, e.Type().String(), err) - continue - } - e = n - - case *LocalVideoElement: - n, err := bot.UploadLocalVideo(message.Source{ - SourceType: message.SourceGuildChannel, - PrimaryID: int64(guildID), - SecondaryID: int64(channelID), - }, i) - if err != nil { - log.Warnf("警告: 频道 %d 消息%s上传失败: %v", channelID, e.Type().String(), err) - continue - } - e = n - case *message.MusicShareElement: bot.Client.SendGuildMusicShare(guildID, channelID, i) return "-1" // todo: fix this - case *LocalVoiceElement, *PokeElement: + case *message.VoiceElement, *PokeElement: log.Warnf("警告: 频道暂不支持发送 %v 消息", i.Type().String()) continue } @@ -575,28 +559,6 @@ func formatMemberName(mem *client.GroupMemberInfo) string { return fmt.Sprintf("%s(%d)", mem.DisplayName(), mem.Uin) } -func (bot *CQBot) uploadMedia(raw message.IMessageElement, target int64, group bool) (message.IMessageElement, error) { - switch m := raw.(type) { - case *LocalImageElement: - if group { - return bot.UploadLocalImageAsGroup(target, m) - } - return bot.UploadLocalImageAsPrivate(target, m) - case *message.VoiceElement: - if group { - return bot.Client.UploadGroupPtt(target, bytes.NewReader(m.Data)) - } - return bot.Client.UploadPrivatePtt(target, bytes.NewReader(m.Data)) - case *LocalVideoElement: - source := message.Source{ - SourceType: message.SourceGroup, - PrimaryID: target, - } - return bot.UploadLocalVideo(source, m) - } - return nil, errors.New("unsupported message element type") -} - // encodeMessageID 临时先这样, 暂时用不上 func encodeMessageID(target int64, seq int32) string { return hex.EncodeToString(binary.NewWriterF(func(w *binary.Writer) { diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 5434d8df..48c1cf13 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -51,12 +51,6 @@ type LocalImageElement struct { EffectID int32 } -// LocalVoiceElement 本地语音 -type LocalVoiceElement struct { - message.VoiceElement - Stream io.ReadSeeker -} - // LocalVideoElement 本地视频 type LocalVideoElement struct { File string @@ -85,7 +79,7 @@ func (e *PokeElement) Type() message.ElementType { } func replyID(r *message.ReplyElement, source message.Source) int32 { - id := int64(source.PrimaryID) + id := source.PrimaryID seq := r.ReplySeq if source.SourceType == message.SourcePrivate { // 私聊似乎腾讯服务器有bug? @@ -1321,9 +1315,13 @@ func (bot *CQBot) makeShowPic(elem message.IMessageElement, source string, brief if brief == "" { brief = "[分享]我看到一张很赞的图片,分享给你,快来看!" } - if _, ok := elem.(*LocalImageElement); ok { + if local, ok := elem.(*LocalImageElement); ok { r := rand.Uint32() - e, err := bot.uploadMedia(elem, int64(r), group) + typ := message.SourceGroup + if !group { + typ = message.SourcePrivate + } + e, err := bot.uploadLocalImage(message.Source{SourceType: typ, PrimaryID: int64(r)}, local) if err != nil { log.Warnf("警告: 图片上传失败: %v", err) return nil, err diff --git a/go.mod b/go.mod index 2ee23ee4..d4a5d597 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220221093105-1e32793eef06 + github.com/Mrs4s/MiraiGo v0.0.0-20220221153544-6b5e7d35f04d github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index f8c754d9..780331ee 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220221093105-1e32793eef06 h1:9V7AhNUPJ1vqLAoXjwLdpv06hJWs15UdgYbKaHww60s= -github.com/Mrs4s/MiraiGo v0.0.0-20220221093105-1e32793eef06/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= +github.com/Mrs4s/MiraiGo v0.0.0-20220221153544-6b5e7d35f04d h1:qnots7MzDtJHOvHPRG60gehAw2pUPBGa0GKBsUQNjRM= +github.com/Mrs4s/MiraiGo v0.0.0-20220221153544-6b5e7d35f04d/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= diff --git a/internal/param/param.go b/internal/param/param.go index 99e0e766..fd86b746 100644 --- a/internal/param/param.go +++ b/internal/param/param.go @@ -30,7 +30,7 @@ func EnsureBool(p interface{}, defaultVal bool) bool { if !j.Exists() { return defaultVal } - switch j.Type { + switch j.Type { // nolint: exhaustive case gjson.True: return true case gjson.False: From d1f143ebf7601c04a630481db818887d436ee371 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8D=83=E6=A9=98=20=E9=9B=AB=E9=9C=9E?= Date: Tue, 22 Feb 2022 13:38:42 +0800 Subject: [PATCH 27/93] feat: set qq profile (#1389) * feat: set qq profile * refactor: support empty field --- coolq/api.go | 21 +++++++++++++++++++++ modules/api/api.go | 7 +++++++ 2 files changed, 28 insertions(+) diff --git a/coolq/api.go b/coolq/api.go index bcb7830a..621a666f 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1981,6 +1981,27 @@ func (bot *CQBot) CQMarkMessageAsRead(msgID int32) global.MSG { return OK(nil) } +// CQSetQQProfile 设置 QQ 资料 +// +// @route(set_qq_profile) +func (bot *CQBot) CQSetQQProfile(nickname, company, email, college, personalNote gjson.Result) global.MSG { + u := client.NewProfileDetailUpdate() + + fi := func(f gjson.Result, do func(value string) client.ProfileDetailUpdate) { + if f.Exists() { + do(f.String()) + } + } + + fi(nickname, u.Nick) + fi(company, u.Company) + fi(email, u.Email) + fi(college, u.College) + fi(personalNote, u.PersonalNote) + bot.Client.UpdateProfile(u) + return OK(nil) +} + // CQReloadEventFilter 重载事件过滤器 // // @route(reload_event_filter) diff --git a/modules/api/api.go b/modules/api/api.go index 5ece4768..e936269a 100644 --- a/modules/api/api.go +++ b/modules/api/api.go @@ -304,6 +304,13 @@ func (c *Caller) call(action string, p Getter) global.MSG { p2 := p.Get("role_id").Uint() p3 := p.Get("users") return c.bot.CQSetGuildMemberRole(p0, p1, p2, p3) + case "set_qq_profile": + p0 := p.Get("nickname") + p1 := p.Get("company") + p2 := p.Get("email") + p3 := p.Get("college") + p4 := p.Get("personal_note") + return c.bot.CQSetQQProfile(p0, p1, p2, p3, p4) case "update_guild_role": p0 := p.Get("guild_id").Uint() p1 := p.Get("role_id").Uint() From 987daad785839a9cb0425a27edc90a0a695f5c84 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Tue, 22 Feb 2022 14:45:50 +0800 Subject: [PATCH 28/93] coolq: allow upload media concurrently for normal message --- coolq/api.go | 29 +++++---------- coolq/bot.go | 103 ++++++++++++++++++++++++++++++++++++--------------- 2 files changed, 82 insertions(+), 50 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 621a666f..6cbdde64 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -12,7 +12,6 @@ import ( "runtime" "strconv" "strings" - "sync" "time" "github.com/segmentio/asm/base64" @@ -793,32 +792,27 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F fm := message.NewForwardMessage() source := message.Source{SourceType: message.SourceGroup, PrimaryID: groupID} - var lazyUpload []func() - var wg sync.WaitGroup + var w worker resolveElement := func(elems []message.IMessageElement) []message.IMessageElement { for i, elem := range elems { - iescape := i + p := &elems[i] switch o := elem.(type) { case *LocalVideoElement: - wg.Add(1) - lazyUpload = append(lazyUpload, func() { - defer wg.Done() + w.do(func() { gm, err := bot.uploadLocalVideo(source, o) if err != nil { - log.Warnf("警告: 群 %d %s上传失败: %v", groupID, o.Type().String(), err) + log.Warnf(uploadFailedTemplate, "群", groupID, "视频", err) } else { - elems[iescape] = gm + *p = gm } }) case *LocalImageElement: - wg.Add(1) - lazyUpload = append(lazyUpload, func() { - defer wg.Done() + w.do(func() { gm, err := bot.uploadLocalImage(source, o) if err != nil { - log.Warnf("警告: 群 %d %s上传失败: %v", groupID, o.Type().String(), err) + log.Warnf(uploadFailedTemplate, "群", groupID, "图片", err) } else { - elems[iescape] = gm + *p = gm } }) } @@ -903,12 +897,7 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F fm.AddNode(node) } } - - for _, upload := range lazyUpload { - go upload() - } - wg.Wait() - + w.wait() return bot.Client.UploadGroupForwardMessage(groupID, fm) } diff --git a/coolq/bot.go b/coolq/bot.go index 00a53c8c..529b5fd3 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -129,6 +129,22 @@ func (bot *CQBot) OnEventPush(f func(e *Event)) { bot.lock.Unlock() } +type worker struct { + wg sync.WaitGroup +} + +func (w *worker) do(f func()) { + w.wg.Add(1) + go func() { + defer w.wg.Done() + f() + }() +} + +func (w *worker) wait() { + w.wg.Wait() +} + // uploadLocalImage 上传本地图片 func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement) (i message.IMessageElement, err error) { if img.File != "" { @@ -163,39 +179,70 @@ func (bot *CQBot) uploadLocalVideo(target message.Source, v *LocalVideoElement) return bot.Client.UploadShortVideo(target, video, v.thumb, 4) } -func (bot *CQBot) uploadMedia(target message.Source, elements []message.IMessageElement) []message.IMessageElement { +func removeLocalElement(elements []message.IMessageElement) []message.IMessageElement { var j int - for _, m := range elements { - raw := m // upload failed will make m nil, so copy it - var err error + for i, e := range elements { + switch e.(type) { + case *LocalImageElement, *LocalVideoElement: + case *message.VoiceElement: // 未上传的语音消息, 也删除 + default: + if j < i { + elements[j] = e + } + j++ + } + } + return elements[:j] +} + +const uploadFailedTemplate = "警告: %s %d %s上传失败: %v" + +func (bot *CQBot) uploadMedia(target message.Source, elements []message.IMessageElement) []message.IMessageElement { + var w worker + var source string + switch target.SourceType { // nolint:exhaustive + case message.SourceGroup: + source = "群" + case message.SourcePrivate: + source = "私聊" + case message.SourceGuildChannel: + source = "频道" + } + + for i, m := range elements { + p := &elements[i] switch e := m.(type) { case *LocalImageElement: - m, err = bot.uploadLocalImage(target, e) + w.do(func() { + m, err := bot.uploadLocalImage(target, e) + if err != nil { + log.Warnf(uploadFailedTemplate, source, target.PrimaryID, "图片", err) + } else { + *p = m + } + }) case *message.VoiceElement: - if target.SourceType == message.SourceGuildChannel { - continue // todo - } - m, err = bot.Client.UploadVoice(target, bytes.NewReader(e.Data)) + w.do(func() { + m, err := bot.Client.UploadVoice(target, bytes.NewReader(e.Data)) + if err != nil { + log.Warnf(uploadFailedTemplate, source, target.PrimaryID, "语音", err) + } else { + *p = m + } + }) case *LocalVideoElement: - m, err = bot.uploadLocalVideo(target, e) - } - if err != nil { - var source string - switch target.SourceType { // nolint:exhaustive - case message.SourceGroup: - source = "群" - case message.SourcePrivate: - source = "私聊" - case message.SourceGuildChannel: - source = "频道" - } - log.Warnf("警告: %s %d %s上传失败: %v", source, target.PrimaryID, raw.Type().String(), err) - continue + w.do(func() { + m, err := bot.uploadLocalVideo(target, e) + if err != nil { + log.Warnf(uploadFailedTemplate, source, target.PrimaryID, "视频", err) + } else { + *p = m + } + }) } - elements[j] = m - j++ } - return elements[:j] + w.wait() + return removeLocalElement(elements) } // SendGroupMessage 发送群消息 @@ -514,10 +561,6 @@ func (bot *CQBot) InsertGuildChannelMessage(m *message.GuildChannelMessage) stri return msg.ID } -// Release 释放Bot实例 -func (bot *CQBot) Release() { -} - func (bot *CQBot) dispatchEventMessage(m global.MSG) { bot.lock.RLock() defer bot.lock.RUnlock() From dfcad8082bc1d81468ca0c332b22fe7744d90148 Mon Sep 17 00:00:00 2001 From: Mrs4s Date: Thu, 24 Feb 2022 01:11:27 +0800 Subject: [PATCH 29/93] feat: check reset working dir exists --- internal/base/flag.go | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/internal/base/flag.go b/internal/base/flag.go index 27940538..c6ff2974 100644 --- a/internal/base/flag.go +++ b/internal/base/flag.go @@ -11,6 +11,7 @@ import ( "strings" "time" + "github.com/Mrs4s/go-cqhttp/global" log "github.com/sirupsen/logrus" "gopkg.in/yaml.v3" @@ -140,6 +141,9 @@ func ResetWorkingDir() { } } p, _ := filepath.Abs(os.Args[0]) + if !global.PathExists(p) { + log.Fatalf("重置工作目录时出现错误: 无法找到路径 %v", p) + } proc := exec.Command(p, args...) proc.Stdin = os.Stdin proc.Stdout = os.Stdout From d4c2b62e5e856e3c20fcf9e0797869bcdfda8022 Mon Sep 17 00:00:00 2001 From: Mrs4s Date: Thu, 24 Feb 2022 01:15:42 +0800 Subject: [PATCH 30/93] fix: import cycle --- internal/base/flag.go | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/internal/base/flag.go b/internal/base/flag.go index c6ff2974..5e9bd7bb 100644 --- a/internal/base/flag.go +++ b/internal/base/flag.go @@ -11,7 +11,7 @@ import ( "strings" "time" - "github.com/Mrs4s/go-cqhttp/global" + "github.com/pkg/errors" log "github.com/sirupsen/logrus" "gopkg.in/yaml.v3" @@ -141,7 +141,8 @@ func ResetWorkingDir() { } } p, _ := filepath.Abs(os.Args[0]) - if !global.PathExists(p) { + _, err := os.Stat(p) + if !(err == nil || errors.Is(err, os.ErrExist)) { log.Fatalf("重置工作目录时出现错误: 无法找到路径 %v", p) } proc := exec.Command(p, args...) @@ -149,7 +150,7 @@ func ResetWorkingDir() { proc.Stdout = os.Stdout proc.Stderr = os.Stderr proc.Dir = wd - err := proc.Run() + err = proc.Run() if err != nil { panic(err) } From 6687d226432ec32fd3c7e53a5c4c6579af916e6c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=BA=90=E6=96=87=E9=9B=A8?= <41315874+fumiama@users.noreply.github.com> Date: Thu, 24 Feb 2022 21:58:48 +0800 Subject: [PATCH 31/93] fix: uploadLocalImage SIGSEGV (#1392) * fix: uploadLocalImage SIGSEGV * fix: removeLocalElement nil ptr --- coolq/bot.go | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/coolq/bot.go b/coolq/bot.go index 529b5fd3..f3beca25 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -146,7 +146,7 @@ func (w *worker) wait() { } // uploadLocalImage 上传本地图片 -func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement) (i message.IMessageElement, err error) { +func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement) (message.IMessageElement, error) { if img.File != "" { f, err := os.Open(img.File) if err != nil { @@ -158,7 +158,10 @@ func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement if lawful, mime := base.IsLawfulImage(img.Stream); !lawful { return nil, errors.New("image type error: " + mime) } - i, err = bot.Client.UploadImage(target, img.Stream, 4) + i, err := bot.Client.UploadImage(target, img.Stream, 4) + if err != nil { + return nil, err + } switch i := i.(type) { case *message.GroupImageElement: i.Flash = img.Flash @@ -166,7 +169,7 @@ func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement case *message.FriendImageElement: i.Flash = img.Flash } - return + return i, err } // uploadLocalVideo 上传本地短视频至群聊 @@ -185,6 +188,7 @@ func removeLocalElement(elements []message.IMessageElement) []message.IMessageEl switch e.(type) { case *LocalImageElement, *LocalVideoElement: case *message.VoiceElement: // 未上传的语音消息, 也删除 + case nil: default: if j < i { elements[j] = e From e1eef2cfc0dddd0738c5d7557892eb8489e0abaf Mon Sep 17 00:00:00 2001 From: fumiama Date: Sun, 27 Feb 2022 15:21:53 +0800 Subject: [PATCH 32/93] fix: *LocalImageElement dulplicate --- coolq/cqcode.go | 14 -------------- 1 file changed, 14 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index ef931545..48c1cf13 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -343,20 +343,6 @@ func ToStringMessage(e []message.IMessageElement, source message.Source, isRaw . write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(m[:])+".image", cqcode.EscapeValue(o.URL), arg) } } - case *LocalImageElement: - var arg string - if o.Flash { - arg = ",type=flash" - } - data, err := os.ReadFile(o.File) - if err == nil { - m := md5.Sum(data) - if ur { - write("[CQ:image,file=%s%s]", hex.EncodeToString(m[:])+".image", arg) - } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(m[:])+".image", CQCodeEscapeValue(o.Url), arg) - } - } case *message.GuildImageElement: write("[CQ:image,file=%s,url=%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url)) case *message.DiceElement: From 8d26e3aec4ce66d41ed422ef37ca407f6c92ba8d Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 27 Feb 2022 21:59:00 +0800 Subject: [PATCH 33/93] dep: update MiraiGo --- go.mod | 4 ++-- go.sum | 15 ++++----------- 2 files changed, 6 insertions(+), 13 deletions(-) diff --git a/go.mod b/go.mod index d4a5d597..c22aa4e3 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.17 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220221153544-6b5e7d35f04d + github.com/Mrs4s/MiraiGo v0.0.0-20220227135520-9884d9b0de20 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 @@ -25,7 +25,7 @@ require ( ) require ( - github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 // indirect + github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect diff --git a/go.sum b/go.sum index 780331ee..a0e74b2d 100644 --- a/go.sum +++ b/go.sum @@ -1,9 +1,9 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220221153544-6b5e7d35f04d h1:qnots7MzDtJHOvHPRG60gehAw2pUPBGa0GKBsUQNjRM= -github.com/Mrs4s/MiraiGo v0.0.0-20220221153544-6b5e7d35f04d/go.mod h1:T66Ua3SOfpJMx+DcfQxk95MeR8RmvAVmjYSkoQQ8nwI= -github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0 h1:8CK7Hg+CRGTFhpjvp5V+7wd8/TkuZ6fSuztLVV3bwoQ= -github.com/RomiChan/protobuf v0.0.0-20220213164748-44b69c8bdec0/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= +github.com/Mrs4s/MiraiGo v0.0.0-20220227135520-9884d9b0de20 h1:ZbJOWQRQB64npjqGMc031/Ry3bKhtMvx7Rf4bx0t9xI= +github.com/Mrs4s/MiraiGo v0.0.0-20220227135520-9884d9b0de20/go.mod h1:23f5g1I7XT7mB3zq02B3rfuiDnE7PJYSfvb/skzDVhI= +github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 h1:1jRB6xuBKwfgZrg0bA7XJin0VeNwG9iJKx9RXwDobt4= +github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -27,7 +27,6 @@ github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrU github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= -github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM= github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -90,7 +89,6 @@ github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5Cc github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= -github.com/tidwall/gjson v1.11.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= github.com/tidwall/gjson v1.14.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA= @@ -123,7 +121,6 @@ golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= -golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -146,10 +143,8 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20211110154304-99a53858aa08/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220111092808-5a964db01320 h1:0jf+tOCoZ3LyutmCOWpVni1chK4VfFLhRsDK7MhqGRY= golang.org/x/sys v0.0.0-20220111092808-5a964db01320/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= @@ -175,8 +170,6 @@ google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQ google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= -google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= From c00e07dec9663c378cc989314eaa0d37ff7ac992 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Tue, 1 Mar 2022 16:30:23 +0800 Subject: [PATCH 34/93] coolq: adapt generic event handle & update MiraiGo --- .github/workflows/ci.yml | 3 ++- cmd/gocq/main.go | 2 +- coolq/api.go | 2 +- coolq/bot.go | 53 ++++++++++++++++++++-------------------- go.mod | 4 +-- go.sum | 4 +-- 6 files changed, 35 insertions(+), 33 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 80139515..5b36780c 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -28,7 +28,8 @@ jobs: - name: Setup Go environment uses: actions/setup-go@v2.1.3 with: - go-version: 1.17 + stable: false + go-version: 1.18.0-rc1 - name: Cache downloaded module uses: actions/cache@v2 with: diff --git a/cmd/gocq/main.go b/cmd/gocq/main.go index 2b5952c9..863074bb 100644 --- a/cmd/gocq/main.go +++ b/cmd/gocq/main.go @@ -259,7 +259,7 @@ func Main() { } var times uint = 1 // 重试次数 var reLoginLock sync.Mutex - cli.OnDisconnected(func(q *client.QQClient, e *client.ClientDisconnectedEvent) { + cli.DisconnectedEvent.Subscribe(func(q *client.QQClient, e *client.ClientDisconnectedEvent) { reLoginLock.Lock() defer reLoginLock.Unlock() times = 1 diff --git a/coolq/api.go b/coolq/api.go index 6cbdde64..dba906f7 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -156,7 +156,7 @@ func (bot *CQBot) CQGetGuildMembers(guildID uint64, nextToken string) global.MSG if !exists { return Failed(100, "NEXT_TOKEN_NOT_EXISTS") } - token = i.(*guildMemberPageToken) + token = i if token.guildID != guildID { return Failed(100, "GUILD_NOT_MATCH") } diff --git a/coolq/bot.go b/coolq/bot.go index f3beca25..bd69f05d 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -32,7 +32,7 @@ type CQBot struct { friendReqCache sync.Map tempSessionCache sync.Map - nextTokenCache *utils.Cache + nextTokenCache *utils.Cache[*guildMemberPageToken] } // Event 事件 @@ -67,40 +67,40 @@ func (e *Event) JSONString() string { func NewQQBot(cli *client.QQClient) *CQBot { bot := &CQBot{ Client: cli, - nextTokenCache: utils.NewCache(time.Second * 10), + nextTokenCache: utils.NewCache[*guildMemberPageToken](time.Second * 10), } - bot.Client.OnPrivateMessage(bot.privateMessageEvent) - bot.Client.OnGroupMessage(bot.groupMessageEvent) + bot.Client.PrivateMessageEvent.Subscribe(bot.privateMessageEvent) + bot.Client.GroupMessageEvent.Subscribe(bot.groupMessageEvent) if base.ReportSelfMessage { - bot.Client.OnSelfPrivateMessage(bot.privateMessageEvent) - bot.Client.OnSelfGroupMessage(bot.groupMessageEvent) + bot.Client.SelfPrivateMessageEvent.Subscribe(bot.privateMessageEvent) + bot.Client.SelfGroupMessageEvent.Subscribe(bot.groupMessageEvent) } - bot.Client.OnTempMessage(bot.tempMessageEvent) + bot.Client.TempMessageEvent.Subscribe(bot.tempMessageEvent) bot.Client.GuildService.OnGuildChannelMessage(bot.guildChannelMessageEvent) bot.Client.GuildService.OnGuildMessageReactionsUpdated(bot.guildMessageReactionsUpdatedEvent) bot.Client.GuildService.OnGuildMessageRecalled(bot.guildChannelMessageRecalledEvent) bot.Client.GuildService.OnGuildChannelUpdated(bot.guildChannelUpdatedEvent) bot.Client.GuildService.OnGuildChannelCreated(bot.guildChannelCreatedEvent) bot.Client.GuildService.OnGuildChannelDestroyed(bot.guildChannelDestroyedEvent) - bot.Client.OnGroupMuted(bot.groupMutedEvent) - bot.Client.OnGroupMessageRecalled(bot.groupRecallEvent) - bot.Client.OnGroupNotify(bot.groupNotifyEvent) - bot.Client.OnFriendNotify(bot.friendNotifyEvent) - bot.Client.OnMemberSpecialTitleUpdated(bot.memberTitleUpdatedEvent) - bot.Client.OnFriendMessageRecalled(bot.friendRecallEvent) - bot.Client.OnReceivedOfflineFile(bot.offlineFileEvent) - bot.Client.OnJoinGroup(bot.joinGroupEvent) - bot.Client.OnLeaveGroup(bot.leaveGroupEvent) - bot.Client.OnGroupMemberJoined(bot.memberJoinEvent) - bot.Client.OnGroupMemberLeaved(bot.memberLeaveEvent) - bot.Client.OnGroupMemberPermissionChanged(bot.memberPermissionChangedEvent) - bot.Client.OnGroupMemberCardUpdated(bot.memberCardUpdatedEvent) - bot.Client.OnNewFriendRequest(bot.friendRequestEvent) - bot.Client.OnNewFriendAdded(bot.friendAddedEvent) - bot.Client.OnGroupInvited(bot.groupInvitedEvent) - bot.Client.OnUserWantJoinGroup(bot.groupJoinReqEvent) - bot.Client.OnOtherClientStatusChanged(bot.otherClientStatusChangedEvent) - bot.Client.OnGroupDigest(bot.groupEssenceMsg) + bot.Client.GroupMuteEvent.Subscribe(bot.groupMutedEvent) + bot.Client.GroupMessageRecalledEvent.Subscribe(bot.groupRecallEvent) + bot.Client.GroupNotifyEvent.Subscribe(bot.groupNotifyEvent) + bot.Client.FriendNotifyEvent.Subscribe(bot.friendNotifyEvent) + bot.Client.MemberSpecialTitleUpdatedEvent.Subscribe(bot.memberTitleUpdatedEvent) + bot.Client.FriendMessageRecalledEvent.Subscribe(bot.friendRecallEvent) + bot.Client.OfflineFileEvent.Subscribe(bot.offlineFileEvent) + bot.Client.GroupJoinEvent.Subscribe(bot.joinGroupEvent) + bot.Client.GroupLeaveEvent.Subscribe(bot.leaveGroupEvent) + bot.Client.GroupMemberJoinEvent.Subscribe(bot.memberJoinEvent) + bot.Client.GroupMemberLeaveEvent.Subscribe(bot.memberLeaveEvent) + bot.Client.GroupMemberPermissionChangedEvent.Subscribe(bot.memberPermissionChangedEvent) + bot.Client.MemberCardUpdatedEvent.Subscribe(bot.memberCardUpdatedEvent) + bot.Client.NewFriendRequestEvent.Subscribe(bot.friendRequestEvent) + bot.Client.NewFriendEvent.Subscribe(bot.friendAddedEvent) + bot.Client.GroupInvitedEvent.Subscribe(bot.groupInvitedEvent) + bot.Client.UserWantJoinGroupEvent.Subscribe(bot.groupJoinReqEvent) + bot.Client.OtherClientStatusChangedEvent.Subscribe(bot.otherClientStatusChangedEvent) + bot.Client.GroupDigestEvent.Subscribe(bot.groupEssenceMsg) go func() { if base.HeartbeatInterval == 0 { log.Warn("警告: 心跳功能已关闭,若非预期,请检查配置文件。") @@ -158,6 +158,7 @@ func (bot *CQBot) uploadLocalImage(target message.Source, img *LocalImageElement if lawful, mime := base.IsLawfulImage(img.Stream); !lawful { return nil, errors.New("image type error: " + mime) } + // todo: enable multi-thread upload, now got error code 81 i, err := bot.Client.UploadImage(target, img.Stream, 4) if err != nil { return nil, err diff --git a/go.mod b/go.mod index c22aa4e3..70f00527 100644 --- a/go.mod +++ b/go.mod @@ -1,10 +1,10 @@ module github.com/Mrs4s/go-cqhttp -go 1.17 +go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220227135520-9884d9b0de20 + github.com/Mrs4s/MiraiGo v0.0.0-20220301082018-d9f803837f49 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index a0e74b2d..ee3aa7d7 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220227135520-9884d9b0de20 h1:ZbJOWQRQB64npjqGMc031/Ry3bKhtMvx7Rf4bx0t9xI= -github.com/Mrs4s/MiraiGo v0.0.0-20220227135520-9884d9b0de20/go.mod h1:23f5g1I7XT7mB3zq02B3rfuiDnE7PJYSfvb/skzDVhI= +github.com/Mrs4s/MiraiGo v0.0.0-20220301082018-d9f803837f49 h1:IIEX0ue2VBA7kGOR1RpdQfPPKfeB4gWine47QXUyzTY= +github.com/Mrs4s/MiraiGo v0.0.0-20220301082018-d9f803837f49/go.mod h1:qJWkRO5vry/sUHthX5kh6go2llYIVAJ+Mq8p+N/FW+8= github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 h1:1jRB6xuBKwfgZrg0bA7XJin0VeNwG9iJKx9RXwDobt4= github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From a75f412b828ac26cb17a1e6d7522df7b6bb480a5 Mon Sep 17 00:00:00 2001 From: Sam <100737234+sam01102@users.noreply.github.com> Date: Wed, 2 Mar 2022 15:42:21 +0800 Subject: [PATCH 35/93] [update] Update 633 link (#1401) --- .github/ISSUE_TEMPLATE/bug-report.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/ISSUE_TEMPLATE/bug-report.yaml b/.github/ISSUE_TEMPLATE/bug-report.yaml index 1cee16c7..9849493c 100644 --- a/.github/ISSUE_TEMPLATE/bug-report.yaml +++ b/.github/ISSUE_TEMPLATE/bug-report.yaml @@ -11,7 +11,7 @@ body: ## 感谢您愿意填写错误回报! ## 以下是一些注意事项,请务必阅读让我们能够更容易处理 - ### ❗ | 确定没有相同问题的ISSUE已被提出. (教程: https://github.com/Mrs4s/go-cqhttp/issues/633) + ### ❗ | 确定没有相同问题的ISSUE已被提出. (教程: https://forums.go-cqhttp.org/t/topic/141) ### 🌎| 请准确填写环境信息 ### ❔ | 打开DEBUG模式复现,并提供出现问题前后至少 10 秒的完整日志内容。请自行删除日志内存在的个人信息及敏感内容。 ### ⚠ | 如果涉及内存泄漏/CPU占用异常请打开DEBUG模式并下载pprof性能分析. @@ -24,7 +24,7 @@ body: attributes: label: 请确保您已阅读以上注意事项,并勾选下方的确认框。 options: - - label: "我已经仔细阅读上述教程和 [\"提问前需知\"](https://github.com/Mrs4s/go-cqhttp/issues/633)" + - label: "我已经仔细阅读上述教程和 [\"提问前需知\"](https://forums.go-cqhttp.org/t/topic/141)" required: true - label: "我已经使用 [dev分支版本](https://github.com/Mrs4s/go-cqhttp/actions/workflows/ci.yml) 测试过,问题依旧存在。" required: true From 4d8c55aca1d561b80857557a6311f08671497a4c Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 2 Mar 2022 22:08:47 +0800 Subject: [PATCH 36/93] cmd/gocq: adapt MiraiGo Logger interface --- cmd/gocq/main.go | 49 ++++++++++++++++++++++++++++++------------------ go.mod | 2 +- go.sum | 4 ++-- 3 files changed, 34 insertions(+), 21 deletions(-) diff --git a/cmd/gocq/main.go b/cmd/gocq/main.go index 863074bb..cb52a0cb 100644 --- a/cmd/gocq/main.go +++ b/cmd/gocq/main.go @@ -130,7 +130,6 @@ func Main() { log.Info("当前版本:", base.Version) if base.Debug { log.SetLevel(log.DebugLevel) - log.SetReportCaller(true) log.Warnf("已开启Debug模式.") // log.Debugf("开发交流群: 192548878") } @@ -383,22 +382,36 @@ func newClient() *client.QQClient { } log.Infof("读取到 %v 个自定义地址.", len(addr)) } - c.OnLog(func(c *client.QQClient, e *client.LogEvent) { - switch e.Type { - case "INFO": - log.Info("Protocol -> " + e.Message) - case "ERROR": - log.Error("Protocol -> " + e.Message) - case "DEBUG": - log.Debug("Protocol -> " + e.Message) - case "DUMP": - if !global.PathExists(global.DumpsPath) { - _ = os.MkdirAll(global.DumpsPath, 0o755) - } - dumpFile := path.Join(global.DumpsPath, fmt.Sprintf("%v.dump", time.Now().Unix())) - log.Errorf("出现错误 %v. 详细信息已转储至文件 %v 请连同日志提交给开发者处理", e.Message, dumpFile) - _ = os.WriteFile(dumpFile, e.Dump, 0o644) - } - }) + c.SetLogger(protocolLogger{}) return c } + +type protocolLogger struct{} + +const fromProtocol = "Protocol -> " + +func (p protocolLogger) Info(format string, arg ...any) { + log.Infof(fromProtocol+format, arg...) +} + +func (p protocolLogger) Warning(format string, arg ...any) { + log.Warnf(fromProtocol+format, arg...) +} + +func (p protocolLogger) Debug(format string, arg ...any) { + log.Debugf(fromProtocol+format, arg...) +} + +func (p protocolLogger) Error(format string, arg ...any) { + log.Errorf(fromProtocol+format, arg...) +} + +func (p protocolLogger) Dump(data []byte, format string, arg ...any) { + if !global.PathExists(global.DumpsPath) { + _ = os.MkdirAll(global.DumpsPath, 0o755) + } + dumpFile := path.Join(global.DumpsPath, fmt.Sprintf("%v.dump", time.Now().Unix())) + message := fmt.Sprintf(format, arg...) + log.Errorf("出现错误 %v. 详细信息已转储至文件 %v 请连同日志提交给开发者处理", message, dumpFile) + _ = os.WriteFile(dumpFile, data, 0o644) +} diff --git a/go.mod b/go.mod index 70f00527..03ed722e 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220301082018-d9f803837f49 + github.com/Mrs4s/MiraiGo v0.0.0-20220302134146-348e317a3400 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index ee3aa7d7..e4a9bed4 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220301082018-d9f803837f49 h1:IIEX0ue2VBA7kGOR1RpdQfPPKfeB4gWine47QXUyzTY= -github.com/Mrs4s/MiraiGo v0.0.0-20220301082018-d9f803837f49/go.mod h1:qJWkRO5vry/sUHthX5kh6go2llYIVAJ+Mq8p+N/FW+8= +github.com/Mrs4s/MiraiGo v0.0.0-20220302134146-348e317a3400 h1:5e0KDN118/RKItDmUcJyCkyyK/EGItYYJ5TVX/jb6xM= +github.com/Mrs4s/MiraiGo v0.0.0-20220302134146-348e317a3400/go.mod h1:qJWkRO5vry/sUHthX5kh6go2llYIVAJ+Mq8p+N/FW+8= github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 h1:1jRB6xuBKwfgZrg0bA7XJin0VeNwG9iJKx9RXwDobt4= github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From 152521893d147895f2e768045798e11506d50746 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 4 Mar 2022 17:56:33 +0800 Subject: [PATCH 37/93] dep: update go-silk --- go.mod | 2 +- go.sum | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 03ed722e..8ba6cc29 100644 --- a/go.mod +++ b/go.mod @@ -16,7 +16,7 @@ require ( github.com/stretchr/testify v1.7.0 github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 github.com/tidwall/gjson v1.14.0 - github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60 + github.com/wdvxdr1123/go-silk v0.0.0-20220304095002-f67345df09ea go.mongodb.org/mongo-driver v1.8.3 golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3 golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 diff --git a/go.sum b/go.sum index e4a9bed4..d60cf463 100644 --- a/go.sum +++ b/go.sum @@ -96,8 +96,8 @@ github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JT github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= github.com/tidwall/pretty v1.2.0 h1:RWIZEg2iJ8/g6fDDYzMpobmaoGh5OLl4AXtGUGPcqCs= github.com/tidwall/pretty v1.2.0/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU= -github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60 h1:lRKf10iIOW0VsH5WDF621ihzR+R2wEBZVtNRHuLLCb4= -github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60/go.mod h1:ecFKZPX81BaB70I6ruUgEwYcDOtuNgJGnjdK+MIl5ko= +github.com/wdvxdr1123/go-silk v0.0.0-20220304095002-f67345df09ea h1:sl1pYm1kHtIndckTY8YDt+QFt77vI0JnKHP0U8rZtKc= +github.com/wdvxdr1123/go-silk v0.0.0-20220304095002-f67345df09ea/go.mod h1:ecFKZPX81BaB70I6ruUgEwYcDOtuNgJGnjdK+MIl5ko= github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c= github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI= github.com/xdg-go/scram v1.0.2 h1:akYIkZ28e6A96dkWNJQu3nmCzH3YfwMPQExUYDaRv7w= From d7fe481a8b05ee8337791ae3cd96ae62c5cdc6dd Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 13 Mar 2022 15:23:14 +0800 Subject: [PATCH 38/93] db,server: release config after init --- coolq/cqcode.go | 2 -- db/multidb.go | 1 + modules/servers/servers.go | 1 + 3 files changed, 2 insertions(+), 2 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 48c1cf13..f727a9d8 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -928,8 +928,6 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType message.So if !lawful { return nil, errors.New("audio type error: " + mt) } - } - if !global.IsAMRorSILK(data) { data, err = global.EncoderSilk(data) if err != nil { return nil, err diff --git a/db/multidb.go b/db/multidb.go index 6d3825ce..68d0ab30 100644 --- a/db/multidb.go +++ b/db/multidb.go @@ -45,6 +45,7 @@ func Open() error { return errors.Wrap(err, "open backend error") } } + base.Database = nil return nil } diff --git a/modules/servers/servers.go b/modules/servers/servers.go index 7a8ae289..e1c28c48 100644 --- a/modules/servers/servers.go +++ b/modules/servers/servers.go @@ -43,4 +43,5 @@ func Run(bot *coolq.CQBot) { for _, fn := range nocfgsvr { go fn(bot) } + base.Servers = nil } From 76295b0e89f84ce8448088b9fa39c09059ae2310 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Thu, 17 Mar 2022 16:59:47 +0800 Subject: [PATCH 39/93] dep: update MiraiGo --- db/mongodb/mongodb.go | 32 +++++++++++++++++++------------- go.mod | 2 +- go.sum | 4 ++-- modules/config/config.go | 15 +-------------- server/scf.go | 8 ++++---- 5 files changed, 27 insertions(+), 34 deletions(-) diff --git a/db/mongodb/mongodb.go b/db/mongodb/mongodb.go index 9c8449d7..35ea702c 100644 --- a/db/mongodb/mongodb.go +++ b/db/mongodb/mongodb.go @@ -10,15 +10,21 @@ import ( "gopkg.in/yaml.v3" "github.com/Mrs4s/go-cqhttp/db" - "github.com/Mrs4s/go-cqhttp/modules/config" ) -type MongoDBImpl struct { +type database struct { uri string db string mongo *mongo.Database } +// config mongodb 相关配置 +type config struct { + Enable bool `yaml:"enable"` + URI string `yaml:"uri"` + Database string `yaml:"database"` +} + const ( MongoGroupMessageCollection = "group-messages" MongoPrivateMessageCollection = "private-messages" @@ -26,8 +32,8 @@ const ( ) func init() { - db.Register("mongodb", func(node yaml.Node) db.Database { - conf := new(config.MongoDBConfig) + db.Register("database", func(node yaml.Node) db.Database { + conf := new(config) _ = node.Decode(conf) if conf.Database == "" { conf.Database = "gocq-database" @@ -35,11 +41,11 @@ func init() { if !conf.Enable { return nil } - return &MongoDBImpl{uri: conf.URI, db: conf.Database} + return &database{uri: conf.URI, db: conf.Database} }) } -func (m *MongoDBImpl) Open() error { +func (m *database) Open() error { cli, err := mongo.Connect(context.Background(), options.Client().ApplyURI(m.uri)) if err != nil { return errors.Wrap(err, "open mongo connection error") @@ -48,14 +54,14 @@ func (m *MongoDBImpl) Open() error { return nil } -func (m *MongoDBImpl) GetMessageByGlobalID(id int32) (db.StoredMessage, error) { +func (m *database) GetMessageByGlobalID(id int32) (db.StoredMessage, error) { if r, err := m.GetGroupMessageByGlobalID(id); err == nil { return r, nil } return m.GetPrivateMessageByGlobalID(id) } -func (m *MongoDBImpl) GetGroupMessageByGlobalID(id int32) (*db.StoredGroupMessage, error) { +func (m *database) GetGroupMessageByGlobalID(id int32) (*db.StoredGroupMessage, error) { coll := m.mongo.Collection(MongoGroupMessageCollection) var ret db.StoredGroupMessage if err := coll.FindOne(context.Background(), bson.D{{"globalId", id}}).Decode(&ret); err != nil { @@ -64,7 +70,7 @@ func (m *MongoDBImpl) GetGroupMessageByGlobalID(id int32) (*db.StoredGroupMessag return &ret, nil } -func (m *MongoDBImpl) GetPrivateMessageByGlobalID(id int32) (*db.StoredPrivateMessage, error) { +func (m *database) GetPrivateMessageByGlobalID(id int32) (*db.StoredPrivateMessage, error) { coll := m.mongo.Collection(MongoPrivateMessageCollection) var ret db.StoredPrivateMessage if err := coll.FindOne(context.Background(), bson.D{{"globalId", id}}).Decode(&ret); err != nil { @@ -73,7 +79,7 @@ func (m *MongoDBImpl) GetPrivateMessageByGlobalID(id int32) (*db.StoredPrivateMe return &ret, nil } -func (m *MongoDBImpl) GetGuildChannelMessageByID(id string) (*db.StoredGuildChannelMessage, error) { +func (m *database) GetGuildChannelMessageByID(id string) (*db.StoredGuildChannelMessage, error) { coll := m.mongo.Collection(MongoGuildChannelMessageCollection) var ret db.StoredGuildChannelMessage if err := coll.FindOne(context.Background(), bson.D{{"_id", id}}).Decode(&ret); err != nil { @@ -82,19 +88,19 @@ func (m *MongoDBImpl) GetGuildChannelMessageByID(id string) (*db.StoredGuildChan return &ret, nil } -func (m *MongoDBImpl) InsertGroupMessage(msg *db.StoredGroupMessage) error { +func (m *database) InsertGroupMessage(msg *db.StoredGroupMessage) error { coll := m.mongo.Collection(MongoGroupMessageCollection) _, err := coll.UpdateOne(context.Background(), bson.D{{"_id", msg.ID}}, bson.D{{"$set", msg}}, options.Update().SetUpsert(true)) return errors.Wrap(err, "insert error") } -func (m *MongoDBImpl) InsertPrivateMessage(msg *db.StoredPrivateMessage) error { +func (m *database) InsertPrivateMessage(msg *db.StoredPrivateMessage) error { coll := m.mongo.Collection(MongoPrivateMessageCollection) _, err := coll.UpdateOne(context.Background(), bson.D{{"_id", msg.ID}}, bson.D{{"$set", msg}}, options.Update().SetUpsert(true)) return errors.Wrap(err, "insert error") } -func (m *MongoDBImpl) InsertGuildChannelMessage(msg *db.StoredGuildChannelMessage) error { +func (m *database) InsertGuildChannelMessage(msg *db.StoredGuildChannelMessage) error { coll := m.mongo.Collection(MongoGuildChannelMessageCollection) _, err := coll.UpdateOne(context.Background(), bson.D{{"_id", msg.ID}}, bson.D{{"$set", msg}}, options.Update().SetUpsert(true)) return errors.Wrap(err, "insert error") diff --git a/go.mod b/go.mod index 8ba6cc29..28b155c8 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220302134146-348e317a3400 + github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/gabriel-vasile/mimetype v1.4.0 diff --git a/go.sum b/go.sum index d60cf463..1a7f972e 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220302134146-348e317a3400 h1:5e0KDN118/RKItDmUcJyCkyyK/EGItYYJ5TVX/jb6xM= -github.com/Mrs4s/MiraiGo v0.0.0-20220302134146-348e317a3400/go.mod h1:qJWkRO5vry/sUHthX5kh6go2llYIVAJ+Mq8p+N/FW+8= +github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3 h1:U3UumMt052Ii1gGrkKM1MbX1uxCzxKhlfuNQ42LtIRQ= +github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3/go.mod h1:qJWkRO5vry/sUHthX5kh6go2llYIVAJ+Mq8p+N/FW+8= github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 h1:1jRB6xuBKwfgZrg0bA7XJin0VeNwG9iJKx9RXwDobt4= github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= diff --git a/modules/config/config.go b/modules/config/config.go index 1386aa66..9c3c65ed 100644 --- a/modules/config/config.go +++ b/modules/config/config.go @@ -8,7 +8,6 @@ import ( "os" "regexp" "strings" - "sync" log "github.com/sirupsen/logrus" "gopkg.in/yaml.v3" @@ -75,13 +74,6 @@ type Server struct { Default string } -// MongoDBConfig mongodb 相关配置 -type MongoDBConfig struct { - Enable bool `yaml:"enable"` - URI string `yaml:"uri"` - Database string `yaml:"database"` -} - // Parse 从默认配置文件路径中获取 func Parse(path string) *Config { file, err := os.ReadFile(path) @@ -98,16 +90,11 @@ func Parse(path string) *Config { return config } -var ( - serverconfs []*Server - mu sync.Mutex -) +var serverconfs []*Server // AddServer 添加该服务的简介和默认配置 func AddServer(s *Server) { - mu.Lock() serverconfs = append(serverconfs, s) - mu.Unlock() } // generateConfig 生成配置文件 diff --git a/server/scf.go b/server/scf.go index 29546ae4..f41b3597 100644 --- a/server/scf.go +++ b/server/scf.go @@ -190,9 +190,9 @@ func (c *lambdaClient) next() *http.Request { if resp.StatusCode != http.StatusOK { return nil } - req := new(http.Request) - invoke := new(lambdaInvoke) - _ = json.NewDecoder(resp.Body).Decode(invoke) + var req http.Request + var invoke lambdaInvoke + _ = json.NewDecoder(resp.Body).Decode(&invoke) if invoke.HTTPMethod == "" { // 不是 api 网关 return nil } @@ -211,5 +211,5 @@ func (c *lambdaClient) next() *http.Request { query[k] = []string{v} } req.URL.RawQuery = query.Encode() - return req + return &req } From d48dc4fb3c73ea2b070d97dce941a04f526c4746 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Thu, 17 Mar 2022 17:58:07 +0800 Subject: [PATCH 40/93] ci: disable golangci-lint --- .github/workflows/ci.yml | 3 +-- .github/workflows/golint.yml | 3 ++- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 5b36780c..05bc69a2 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -28,8 +28,7 @@ jobs: - name: Setup Go environment uses: actions/setup-go@v2.1.3 with: - stable: false - go-version: 1.18.0-rc1 + go-version: 1.18 - name: Cache downloaded module uses: actions/cache@v2 with: diff --git a/.github/workflows/golint.yml b/.github/workflows/golint.yml index 5a9ef49c..e4f61e85 100644 --- a/.github/workflows/golint.yml +++ b/.github/workflows/golint.yml @@ -12,9 +12,10 @@ jobs: - name: Setup Go environment uses: actions/setup-go@v2.1.3 with: - go-version: 1.17 + go-version: 1.18 - name: golangci-lint + if: ${{ false }} uses: golangci/golangci-lint-action@v2 with: version: latest From 779fa207041eb86edc0ab26af1640b173fecbcfc Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Thu, 17 Mar 2022 21:20:34 +0800 Subject: [PATCH 41/93] Dockerfile: update to go1.18 Fixes #1427 --- Dockerfile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Dockerfile b/Dockerfile index d5ff7e56..2f2f1acd 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,4 +1,4 @@ -FROM golang:1.17-alpine AS builder +FROM golang:1.18-alpine AS builder RUN go env -w GO111MODULE=auto \ && go env -w CGO_ENABLED=0 \ From 34613306b311365f08b2cf2f8fd709d09c235c49 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 17:07:10 +0800 Subject: [PATCH 42/93] internal/mime: use stdlib to detect mimetype --- coolq/api.go | 4 +-- go.mod | 1 - go.sum | 6 ---- modules/config/config.go | 10 +----- modules/mime/mime.go | 71 +++++++++++++++------------------------- 5 files changed, 30 insertions(+), 62 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index dba906f7..9c26ec28 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -38,7 +38,7 @@ type guildMemberPageToken struct { nextQueryParam string } -var defaultPageToken = &guildMemberPageToken{ +var defaultPageToken = guildMemberPageToken{ guildID: 0, nextIndex: 0, nextRoleID: 2, @@ -150,7 +150,7 @@ func (bot *CQBot) CQGetGuildMembers(guildID uint64, nextToken string) global.MSG if guild == nil { return Failed(100, "GUILD_NOT_FOUND") } - token := defaultPageToken + token := &defaultPageToken if nextToken != "" { i, exists := bot.nextTokenCache.Get(nextToken) if !exists { diff --git a/go.mod b/go.mod index 28b155c8..68169dcc 100644 --- a/go.mod +++ b/go.mod @@ -7,7 +7,6 @@ require ( github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 - github.com/gabriel-vasile/mimetype v1.4.0 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible github.com/mattn/go-colorable v0.1.12 github.com/pkg/errors v0.9.1 diff --git a/go.sum b/go.sum index 1a7f972e..15d94b48 100644 --- a/go.sum +++ b/go.sum @@ -16,8 +16,6 @@ github.com/fumiama/go-hide-param v0.1.4 h1:y7TRTzZMdCH9GOXnIzU3B+1BSkcmvejVGmGsz github.com/fumiama/go-hide-param v0.1.4/go.mod h1:vJkQlJIEI56nIyp7tCQu1/2QOyKtZpudsnJkGk9U1aY= github.com/fumiama/imgsz v0.0.2 h1:fAkC0FnIscdKOXwAxlyw3EUba5NzxZdSxGaq3Uyfxak= github.com/fumiama/imgsz v0.0.2/go.mod h1:dR71mI3I2O5u6+PCpd47M9TZptzP+39tRBcbdIkoqM4= -github.com/gabriel-vasile/mimetype v1.4.0 h1:Cn9dkdYsMIu56tGho+fqzh7XmvY2YyGU0FnbhiOsEro= -github.com/gabriel-vasile/mimetype v1.4.0/go.mod h1:fA8fi6KUiG7MgQQ+mEWotXoEOvmxRtOJlERCzSmRvr8= github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= @@ -120,7 +118,6 @@ golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200813134508-3edf25e44fcc/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= -golang.org/x/net v0.0.0-20210505024714-0287a6fb4125/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 h1:0qxwC5n+ttVOINCBeRHO0nq9X7uy8SDsPoi5OaCdIEI= golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -139,16 +136,13 @@ golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200519105757-fe76b779f299/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200814200057-3d37ad5750ed/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201126233918-771906719818/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220111092808-5a964db01320 h1:0jf+tOCoZ3LyutmCOWpVni1chK4VfFLhRsDK7MhqGRY= golang.org/x/sys v0.0.0-20220111092808-5a964db01320/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= -golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 h1:JGgROgKl9N8DuW20oFS5gxc+lE67/N3FcwmBPMe7ArY= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= diff --git a/modules/config/config.go b/modules/config/config.go index 9c3c65ed..158bd623 100644 --- a/modules/config/config.go +++ b/modules/config/config.go @@ -137,8 +137,7 @@ func expand(s string, mapping func(string) string) string { r := regexp.MustCompile(`\${([a-zA-Z_]+[a-zA-Z0-9_:/.]*)}`) return r.ReplaceAllStringFunc(s, func(s string) string { s = strings.Trim(s, "${}") - // todo: use strings.Cut once go1.18 is released - before, after, ok := cut(s, ":") + before, after, ok := strings.Cut(s, ":") m := mapping(before) if ok && m == "" { return after @@ -146,10 +145,3 @@ func expand(s string, mapping func(string) string) string { return m }) } - -func cut(s, sep string) (before, after string, found bool) { - if i := strings.Index(s, sep); i >= 0 { - return s[:i], s[i+len(sep):], true - } - return s, "", false -} diff --git a/modules/mime/mime.go b/modules/mime/mime.go index 50d762db..dbaa831a 100644 --- a/modules/mime/mime.go +++ b/modules/mime/mime.go @@ -3,68 +3,51 @@ package mime import ( "io" - - "github.com/gabriel-vasile/mimetype" - "github.com/sirupsen/logrus" + "net/http" + "strings" "github.com/Mrs4s/go-cqhttp/internal/base" ) func init() { - base.IsLawfulAudio = checkImage + base.IsLawfulImage = checkImage base.IsLawfulAudio = checkAudio } -// keep sync with /docs/file.md#MINE -var lawfulImage = [...]string{ - "image/bmp", - "image/gif", - "image/jpeg", - "image/png", - "image/webp", -} +const limit = 4 * 1024 -var lawfulAudio = [...]string{ - "audio/aac", - "audio/aiff", - "audio/amr", - "audio/ape", - "audio/flac", - "audio/midi", - "audio/mp4", - "audio/mpeg", - "audio/ogg", - "audio/wav", - "audio/x-m4a", -} - -func check(r io.ReadSeeker, list []string) (bool, string) { - if base.SkipMimeScan { - return true, "" - } +func scan(r io.ReadSeeker) string { _, _ = r.Seek(0, io.SeekStart) defer r.Seek(0, io.SeekStart) - t, err := mimetype.DetectReader(r) - if err != nil { - logrus.Debugf("扫描 Mime 时出现问题: %v", err) - return false, "" - } - for _, lt := range list { - if t.Is(lt) { - return true, t.String() - } - } - return false, t.String() + in := make([]byte, limit) + _, _ = r.Read(in) + return http.DetectContentType(in) } // checkImage 判断给定流是否为合法图片 // 返回 是否合法, 实际Mime // 判断后会自动将 Stream Seek 至 0 -func checkImage(r io.ReadSeeker) (bool, string) { - return check(r, lawfulImage[:]) +func checkImage(r io.ReadSeeker) (ok bool, t string) { + if base.SkipMimeScan { + return true, "" + } + t = scan(r) + switch t { + case "image/bmp", "image/gif", "image/jpeg", "image/png", "image/webp": + ok = true + } + return } // checkImage 判断给定流是否为合法音频 func checkAudio(r io.ReadSeeker) (bool, string) { - return check(r, lawfulAudio[:]) + if base.SkipMimeScan { + return true, "" + } + t := scan(r) + // std mime type detection is not full supported for audio + if strings.Contains(t, "text") || strings.Contains(t, "image") { + return false, t + } + return true, t } From 0a603dee92f75e4f3b7b0d9df3aa1daa07c4b54c Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 18:49:08 +0800 Subject: [PATCH 43/93] dep: revert go-silk version --- cmd/gocq/main.go | 5 ++--- go.mod | 2 +- go.sum | 4 ++-- 3 files changed, 5 insertions(+), 6 deletions(-) diff --git a/cmd/gocq/main.go b/cmd/gocq/main.go index cb52a0cb..c6200803 100644 --- a/cmd/gocq/main.go +++ b/cmd/gocq/main.go @@ -324,10 +324,9 @@ func Main() { log.Info("资源初始化完成, 开始处理信息.") log.Info("アトリは、高性能ですから!") - go selfupdate.CheckUpdate() go func() { - time.Sleep(5 * time.Second) - go selfdiagnosis.NetworkDiagnosis(cli) + selfupdate.CheckUpdate() + selfdiagnosis.NetworkDiagnosis(cli) }() <-global.SetupMainSignalHandler() diff --git a/go.mod b/go.mod index 68169dcc..caa6d463 100644 --- a/go.mod +++ b/go.mod @@ -15,7 +15,7 @@ require ( github.com/stretchr/testify v1.7.0 github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 github.com/tidwall/gjson v1.14.0 - github.com/wdvxdr1123/go-silk v0.0.0-20220304095002-f67345df09ea + github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60 go.mongodb.org/mongo-driver v1.8.3 golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3 golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 diff --git a/go.sum b/go.sum index 15d94b48..41fea276 100644 --- a/go.sum +++ b/go.sum @@ -94,8 +94,8 @@ github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JT github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk= github.com/tidwall/pretty v1.2.0 h1:RWIZEg2iJ8/g6fDDYzMpobmaoGh5OLl4AXtGUGPcqCs= github.com/tidwall/pretty v1.2.0/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU= -github.com/wdvxdr1123/go-silk v0.0.0-20220304095002-f67345df09ea h1:sl1pYm1kHtIndckTY8YDt+QFt77vI0JnKHP0U8rZtKc= -github.com/wdvxdr1123/go-silk v0.0.0-20220304095002-f67345df09ea/go.mod h1:ecFKZPX81BaB70I6ruUgEwYcDOtuNgJGnjdK+MIl5ko= +github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60 h1:lRKf10iIOW0VsH5WDF621ihzR+R2wEBZVtNRHuLLCb4= +github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60/go.mod h1:ecFKZPX81BaB70I6ruUgEwYcDOtuNgJGnjdK+MIl5ko= github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c= github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI= github.com/xdg-go/scram v1.0.2 h1:akYIkZ28e6A96dkWNJQu3nmCzH3YfwMPQExUYDaRv7w= From afbf42b7094ed457c27614af57eeafb815f04818 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 19:36:06 +0800 Subject: [PATCH 44/93] dep: update MiraiGo --- go.mod | 4 ++-- go.sum | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/go.mod b/go.mod index caa6d463..2075be34 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3 + github.com/Mrs4s/MiraiGo v0.0.0-20220318113435-f5950d72fa77 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible @@ -24,7 +24,7 @@ require ( ) require ( - github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 // indirect + github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect diff --git a/go.sum b/go.sum index 41fea276..abe4bf4e 100644 --- a/go.sum +++ b/go.sum @@ -1,9 +1,9 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3 h1:U3UumMt052Ii1gGrkKM1MbX1uxCzxKhlfuNQ42LtIRQ= -github.com/Mrs4s/MiraiGo v0.0.0-20220317085721-6d84141b8dd3/go.mod h1:qJWkRO5vry/sUHthX5kh6go2llYIVAJ+Mq8p+N/FW+8= -github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 h1:1jRB6xuBKwfgZrg0bA7XJin0VeNwG9iJKx9RXwDobt4= -github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= +github.com/Mrs4s/MiraiGo v0.0.0-20220318113435-f5950d72fa77 h1:SmyVuRtew04EETyL24+IxzQ+Tr8YhhPpAFmgx20V2nI= +github.com/Mrs4s/MiraiGo v0.0.0-20220318113435-f5950d72fa77/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= +github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= +github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= From 937538a7cbb6b3c689b23b8e54aa66b782513304 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 19:49:32 +0800 Subject: [PATCH 45/93] coolq: remove support for old cache path --- coolq/cqcode.go | 7 ------- global/fs.go | 17 ++++------------- 2 files changed, 4 insertions(+), 20 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index f727a9d8..39e0de03 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -917,9 +917,6 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType message.So case "record": f := d["file"] data, err := global.FindFile(f, d["cache"], global.VoicePath) - if err == global.ErrSyntax { - data, err = global.FindFile(f, d["cache"], global.VoicePathOld) - } if err != nil { return nil, err } @@ -1241,10 +1238,6 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy } } exist := global.PathExists(rawPath) - if !exist && global.PathExists(path.Join(global.ImagePathOld, f)) { - exist = true - rawPath = path.Join(global.ImagePathOld, f) - } if !exist { if d["url"] != "" { return bot.makeImageOrVideoElem(map[string]string{"file": d["url"]}, false, sourceType) diff --git a/global/fs.go b/global/fs.go index f4693444..be15a589 100644 --- a/global/fs.go +++ b/global/fs.go @@ -22,27 +22,18 @@ import ( const ( // ImagePath go-cqhttp使用的图片缓存目录 ImagePath = "data/images" - // ImagePathOld 兼容旧版go-cqhttp使用的图片缓存目录 - ImagePathOld = "data/image" // VoicePath go-cqhttp使用的语音缓存目录 VoicePath = "data/voices" - // VoicePathOld 兼容旧版go-cqhttp使用的语音缓存目录 - VoicePathOld = "data/record" // VideoPath go-cqhttp使用的视频缓存目录 VideoPath = "data/videos" // CachePath go-cqhttp使用的缓存目录 CachePath = "data/cache" // DumpsPath go-cqhttp使用错误转储目录 DumpsPath = "dumps" -) - -var ( - // ErrSyntax Path语法错误时返回的错误 - ErrSyntax = errors.New("syntax error") // HeaderAmr AMR文件头 - HeaderAmr = []byte("#!AMR") + HeaderAmr = "#!AMR" // HeaderSilk Silkv3文件头 - HeaderSilk = []byte("\x02#!SILK_V3") + HeaderSilk = "\x02#!SILK_V3" ) // PathExists 判断给定path是否存在 @@ -78,13 +69,13 @@ func Check(err error, deleteSession bool) { // IsAMRorSILK 判断给定文件是否为Amr或Silk格式 func IsAMRorSILK(b []byte) bool { - return bytes.HasPrefix(b, HeaderAmr) || bytes.HasPrefix(b, HeaderSilk) + return bytes.HasPrefix(b, []byte(HeaderAmr)) || bytes.HasPrefix(b, []byte(HeaderSilk)) } // FindFile 从给定的File寻找文件,并返回文件byte数组。File是一个合法的URL。p为文件寻找位置。 // 对于HTTP/HTTPS形式的URL,Cache为"1"或空时表示启用缓存 func FindFile(file, cache, p string) (data []byte, err error) { - data, err = nil, ErrSyntax + data, err = nil, os.ErrNotExist switch { case strings.HasPrefix(file, "http"): // https also has prefix http hash := md5.Sum([]byte(file)) From cbcfee9f69ca2102ceda069245af2fde5d16fca6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8D=83=E6=A9=98=20=E9=9B=AB=E9=9C=9E?= Date: Fri, 18 Mar 2022 21:15:53 +0800 Subject: [PATCH 46/93] feat: support get group notice #493 (#1418) * feat: support get group notice #493 * feat: update `go.mod` * fix --- coolq/api.go | 11 +++++++++++ go.mod | 2 +- go.sum | 4 ++-- modules/api/api.go | 3 +++ 4 files changed, 17 insertions(+), 3 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 9c26ec28..cdb7677d 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -995,6 +995,17 @@ func (bot *CQBot) CQSetGroupName(groupID int64, name string) global.MSG { return Failed(100, "GROUP_NOT_FOUND", "群聊不存在") } +// CQGetGroupMemo 扩展API-获取群公告 +// @route(_get_group_notice) +func (bot *CQBot) CQGetGroupMemo(groupID int64) global.MSG { + r, err := bot.Client.GetGroupNotice(groupID) + if err != nil { + return Failed(100, "获取群公告失败", err.Error()) + } + + return OK(r) +} + // CQSetGroupMemo 扩展API-发送群公告 // // https://docs.go-cqhttp.org/api/#%E5%8F%91%E9%80%81%E7%BE%A4%E5%85%AC%E5%91%8A diff --git a/go.mod b/go.mod index 2075be34..80e124ca 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220318113435-f5950d72fa77 + github.com/Mrs4s/MiraiGo v0.0.0-20220318123613-8fa49fedb994 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible diff --git a/go.sum b/go.sum index abe4bf4e..d36375bb 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220318113435-f5950d72fa77 h1:SmyVuRtew04EETyL24+IxzQ+Tr8YhhPpAFmgx20V2nI= -github.com/Mrs4s/MiraiGo v0.0.0-20220318113435-f5950d72fa77/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= +github.com/Mrs4s/MiraiGo v0.0.0-20220318123613-8fa49fedb994 h1:wqsMt+ob6KMNEl0EWzn9nPoCEQx886UlFRPU9YdRpBQ= +github.com/Mrs4s/MiraiGo v0.0.0-20220318123613-8fa49fedb994/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= diff --git a/modules/api/api.go b/modules/api/api.go index e936269a..fc40e266 100644 --- a/modules/api/api.go +++ b/modules/api/api.go @@ -21,6 +21,9 @@ func (c *Caller) call(action string, p Getter) global.MSG { case ".ocr_image", "ocr_image": p0 := p.Get("image").String() return c.bot.CQOcrImage(p0) + case "_get_group_notice": + p0 := p.Get("group_id").Int() + return c.bot.CQGetGroupMemo(p0) case "_get_model_show": p0 := p.Get("model").String() return c.bot.CQGetModelShow(p0) From 429ff80cf0643e02f5e8b0574813e2f60d882da7 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 21:38:50 +0800 Subject: [PATCH 47/93] update MiraiGo & remove `_get_vip_info` Fixes #1429 --- coolq/api.go | 21 --------------------- go.mod | 2 +- go.sum | 4 ++-- modules/api/api.go | 3 --- 4 files changed, 3 insertions(+), 27 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index cdb7677d..4cc15265 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1235,27 +1235,6 @@ func (bot *CQBot) CQSetGroupAdmin(groupID, userID int64, enable bool) global.MSG return OK(nil) } -// CQGetVipInfo 扩展API-获取VIP信息 -// -// https://docs.go-cqhttp.org/api/#%E8%8E%B7%E5%8F%96vip%E4%BF%A1%E6%81%AF -// @route(_get_vip_info) -func (bot *CQBot) CQGetVipInfo(userID int64) global.MSG { - vip, err := bot.Client.GetVipInfo(userID) - if err != nil { - return Failed(100, "VIP_API_ERROR", err.Error()) - } - msg := global.MSG{ - "user_id": vip.Uin, - "nickname": vip.Name, - "level": vip.Level, - "level_speed": vip.LevelSpeed, - "vip_level": vip.VipLevel, - "vip_growth_speed": vip.VipGrowthSpeed, - "vip_growth_total": vip.VipGrowthTotal, - } - return OK(msg) -} - // CQGetGroupHonorInfo 获取群荣誉信息 // // https://git.io/Jtz1H diff --git a/go.mod b/go.mod index 80e124ca..922e213b 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220318123613-8fa49fedb994 + github.com/Mrs4s/MiraiGo v0.0.0-20220318133222-87e53dd6e2f2 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible diff --git a/go.sum b/go.sum index d36375bb..a415ab09 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220318123613-8fa49fedb994 h1:wqsMt+ob6KMNEl0EWzn9nPoCEQx886UlFRPU9YdRpBQ= -github.com/Mrs4s/MiraiGo v0.0.0-20220318123613-8fa49fedb994/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= +github.com/Mrs4s/MiraiGo v0.0.0-20220318133222-87e53dd6e2f2 h1:8Q2eZyYxpd8En9JTe79tx0dekENJ5OTto8fQiLS9tQA= +github.com/Mrs4s/MiraiGo v0.0.0-20220318133222-87e53dd6e2f2/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= diff --git a/modules/api/api.go b/modules/api/api.go index fc40e266..b57c2500 100644 --- a/modules/api/api.go +++ b/modules/api/api.go @@ -27,9 +27,6 @@ func (c *Caller) call(action string, p Getter) global.MSG { case "_get_model_show": p0 := p.Get("model").String() return c.bot.CQGetModelShow(p0) - case "_get_vip_info": - p0 := p.Get("user_id").Int() - return c.bot.CQGetVipInfo(p0) case "_send_group_notice": p0 := p.Get("group_id").Int() p1 := p.Get("content").String() From de4cfe073395428249c78725069ee34ec4dd2867 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 22:58:14 +0800 Subject: [PATCH 48/93] dep: update MiraiGo Fix wrong self message event dispatch --- go.mod | 2 +- go.sum | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 922e213b..1c246b02 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220318133222-87e53dd6e2f2 + github.com/Mrs4s/MiraiGo v0.0.0-20220318145114-35f774b86afa github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible diff --git a/go.sum b/go.sum index a415ab09..17c27fd1 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220318133222-87e53dd6e2f2 h1:8Q2eZyYxpd8En9JTe79tx0dekENJ5OTto8fQiLS9tQA= -github.com/Mrs4s/MiraiGo v0.0.0-20220318133222-87e53dd6e2f2/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= +github.com/Mrs4s/MiraiGo v0.0.0-20220318145114-35f774b86afa h1:UgOs+GImN0IYAZ/P/OH9nCOkEbidauK40F5axm11TcM= +github.com/Mrs4s/MiraiGo v0.0.0-20220318145114-35f774b86afa/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From d34531790ca5005d8c27d30fbf0d09d887329bda Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Fri, 18 Mar 2022 23:50:21 +0800 Subject: [PATCH 49/93] coolq: handle extract cover error For #1426 --- coolq/cqcode.go | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 39e0de03..1e97f4b8 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -1103,21 +1103,18 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType message.So if cover, ok := d["cover"]; ok { data, _ = global.FindFile(cover, d["cache"], global.ImagePath) } else { - _ = global.ExtractCover(v.File, v.File+".jpg") + err = global.ExtractCover(v.File, v.File+".jpg") + if err != nil { + return nil, err + } data, _ = os.ReadFile(v.File + ".jpg") } v.thumb = bytes.NewReader(data) video, _ := os.Open(v.File) defer video.Close() - _, err = video.Seek(4, io.SeekStart) - if err != nil { - return nil, err - } + _, _ = video.Seek(4, io.SeekStart) header := make([]byte, 4) - _, err = video.Read(header) - if err != nil { - return nil, err - } + _, _ = video.Read(header) if !bytes.Equal(header, []byte{0x66, 0x74, 0x79, 0x70}) { // check file header ftyp _, _ = video.Seek(0, io.SeekStart) hash, _ := utils.ComputeMd5AndLength(video) From 70da0ce6e4dfa0aa318fef6809425fe8e4ef3246 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 19 Mar 2022 10:11:15 +0800 Subject: [PATCH 50/93] ci: enable golangci-lint latest version support go1.18 --- .github/workflows/golint.yml | 1 - go.mod | 2 +- go.sum | 4 ++-- 3 files changed, 3 insertions(+), 4 deletions(-) diff --git a/.github/workflows/golint.yml b/.github/workflows/golint.yml index e4f61e85..6ab8830a 100644 --- a/.github/workflows/golint.yml +++ b/.github/workflows/golint.yml @@ -15,7 +15,6 @@ jobs: go-version: 1.18 - name: golangci-lint - if: ${{ false }} uses: golangci/golangci-lint-action@v2 with: version: latest diff --git a/go.mod b/go.mod index 1c246b02..6cb3f648 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220318145114-35f774b86afa + github.com/Mrs4s/MiraiGo v0.0.0-20220319020337-5903226f2534 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible diff --git a/go.sum b/go.sum index 17c27fd1..cfae5fad 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220318145114-35f774b86afa h1:UgOs+GImN0IYAZ/P/OH9nCOkEbidauK40F5axm11TcM= -github.com/Mrs4s/MiraiGo v0.0.0-20220318145114-35f774b86afa/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= +github.com/Mrs4s/MiraiGo v0.0.0-20220319020337-5903226f2534 h1:Ah5fmskBIYruUGBIH1mLoeXmmGDO92N8JPDPW0Fd7f4= +github.com/Mrs4s/MiraiGo v0.0.0-20220319020337-5903226f2534/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From 5b148d6c5e4f395d959f8337a8ca6819d8048124 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 19 Mar 2022 10:53:58 +0800 Subject: [PATCH 51/93] ci: disable some lint some lint work failed with generic --- .golangci.yml | 33 +++++++++++++-------------------- 1 file changed, 13 insertions(+), 20 deletions(-) diff --git a/.golangci.yml b/.golangci.yml index 4ff3d91c..0a87b864 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -21,35 +21,28 @@ linters: disable-all: true fast: false enable: - - bodyclose - - deadcode - - depguard - - dogsled + #- bodyclose + #- deadcode + #- depguard + #- dogsled + - gofmt + - goimports - errcheck - exportloopref - exhaustive - bidichk - #- funlen - #- goconst - gocritic - #- gocyclo - - gofmt - - goimports - - goprintffuncname - #- gosec - - gosimple + #- gosimple - govet - ineffassign - #- misspell - - nolintlint - - rowserrcheck - - staticcheck + #- nolintlint + #- rowserrcheck + #- staticcheck - structcheck - - stylecheck - - typecheck + #- stylecheck - unconvert - - unparam - - unused + #- unparam + #- unused - varcheck - whitespace - prealloc From 062eea62abfe2338f21218fce16fa11aeeeacafc Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 20 Mar 2022 15:19:47 +0800 Subject: [PATCH 52/93] coolq: use generic sync.Map --- coolq/api.go | 4 ++-- coolq/bot.go | 7 ++++--- go.mod | 3 ++- go.sum | 6 ++++-- 4 files changed, 12 insertions(+), 8 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 4cc15265..020f2115 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1126,9 +1126,9 @@ func (bot *CQBot) CQProcessFriendRequest(flag string, approve bool) global.MSG { return Failed(100, "FLAG_NOT_FOUND", "FLAG不存在") } if approve { - req.(*client.NewFriendRequest).Accept() + req.Accept() } else { - req.(*client.NewFriendRequest).Reject() + req.Reject() } return OK(nil) } diff --git a/coolq/bot.go b/coolq/bot.go index bd69f05d..407800f6 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -14,6 +14,7 @@ import ( "github.com/Mrs4s/MiraiGo/client" "github.com/Mrs4s/MiraiGo/message" "github.com/Mrs4s/MiraiGo/utils" + "github.com/RomiChan/syncx" "github.com/pkg/errors" "github.com/segmentio/asm/base64" log "github.com/sirupsen/logrus" @@ -30,8 +31,8 @@ type CQBot struct { lock sync.RWMutex events []func(*Event) - friendReqCache sync.Map - tempSessionCache sync.Map + friendReqCache syncx.Map[string, *client.NewFriendRequest] + tempSessionCache syncx.Map[int64, *client.TempSessionInfo] nextTokenCache *utils.Cache[*guildMemberPageToken] } @@ -366,7 +367,7 @@ func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.Sen } break } - msg, err := session.(*client.TempSessionInfo).SendMessage(m) + msg, err := session.SendMessage(m) if err != nil { log.Errorf("发送临时会话消息失败: %v", err) break diff --git a/go.mod b/go.mod index 6cb3f648..43649e2b 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,8 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220319020337-5903226f2534 + github.com/Mrs4s/MiraiGo v0.0.0-20220320070754-38990f6e1cf9 + github.com/RomiChan/syncx v0.0.0-20220320065321-8d448f958257 github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible diff --git a/go.sum b/go.sum index cfae5fad..2442768e 100644 --- a/go.sum +++ b/go.sum @@ -1,9 +1,11 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220319020337-5903226f2534 h1:Ah5fmskBIYruUGBIH1mLoeXmmGDO92N8JPDPW0Fd7f4= -github.com/Mrs4s/MiraiGo v0.0.0-20220319020337-5903226f2534/go.mod h1:kkUjOuOj2FMfqEEtnan/mxxKBZopYRBVIR4gSAdt7Hs= +github.com/Mrs4s/MiraiGo v0.0.0-20220320070754-38990f6e1cf9 h1:YJeHJRNVfpbuC7wSQD3WOcysC7AcILgQf5d8kFPL12Y= +github.com/Mrs4s/MiraiGo v0.0.0-20220320070754-38990f6e1cf9/go.mod h1:qseuVVwl5wxdhphaS29F6CN0gV2J0ojT880Ql5g2MBo= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= +github.com/RomiChan/syncx v0.0.0-20220320065321-8d448f958257 h1:fdMod+DEoiICoTtS1Wij/wl1d57FPvKVmretLi2sGD8= +github.com/RomiChan/syncx v0.0.0-20220320065321-8d448f958257/go.mod h1:KqZzu7slNKROh3TSYEH/IUMG6f4M+1qubZ5e52QypsE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= From 112441d76e9e66ed5b6b369d440a4eb85baa2c7c Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 21 Mar 2022 21:41:29 +0800 Subject: [PATCH 53/93] coolq: refactor send forward message --- coolq/api.go | 204 ++++++++++++++++++++++++++------------------------- go.mod | 4 +- go.sum | 8 +- 3 files changed, 110 insertions(+), 106 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 020f2115..486b543b 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -789,116 +789,120 @@ func (bot *CQBot) CQSendGuildChannelMessage(guildID, channelID uint64, m gjson.R func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.ForwardElement { ts := time.Now().Add(-time.Minute * 5) - fm := message.NewForwardMessage() source := message.Source{SourceType: message.SourceGroup, PrimaryID: groupID} - - var w worker - resolveElement := func(elems []message.IMessageElement) []message.IMessageElement { - for i, elem := range elems { - p := &elems[i] - switch o := elem.(type) { - case *LocalVideoElement: - w.do(func() { - gm, err := bot.uploadLocalVideo(source, o) - if err != nil { - log.Warnf(uploadFailedTemplate, "群", groupID, "视频", err) - } else { - *p = gm - } - }) - case *LocalImageElement: - w.do(func() { - gm, err := bot.uploadLocalImage(source, o) - if err != nil { - log.Warnf(uploadFailedTemplate, "群", groupID, "图片", err) - } else { - *p = gm - } - }) + builder := bot.Client.NewForwardMessageBuilder(groupID) + + var convertMessage func(m gjson.Result) *message.ForwardMessage + convertMessage = func(m gjson.Result) *message.ForwardMessage { + fm := message.NewForwardMessage() + var w worker + resolveElement := func(elems []message.IMessageElement) []message.IMessageElement { + for i, elem := range elems { + p := &elems[i] + switch o := elem.(type) { + case *LocalVideoElement: + w.do(func() { + gm, err := bot.uploadLocalVideo(source, o) + if err != nil { + log.Warnf(uploadFailedTemplate, "群", groupID, "视频", err) + } else { + *p = gm + } + }) + case *LocalImageElement: + w.do(func() { + gm, err := bot.uploadLocalImage(source, o) + if err != nil { + log.Warnf(uploadFailedTemplate, "群", groupID, "图片", err) + } else { + *p = gm + } + }) + } } + return elems } - return elems - } - convert := func(e gjson.Result) *message.ForwardNode { - if e.Get("type").Str != "node" { - return nil - } - ts.Add(time.Second) - if e.Get("data.id").Exists() { - i := e.Get("data.id").Int() - m, _ := db.GetGroupMessageByGlobalID(int32(i)) - if m != nil { - return &message.ForwardNode{ - SenderId: m.Attribute.SenderUin, - SenderName: m.Attribute.SenderName, - Time: func() int32 { - msgTime := m.Attribute.Timestamp - if msgTime == 0 { - return int32(ts.Unix()) - } - return int32(msgTime) - }(), - Message: resolveElement(bot.ConvertContentMessage(m.Content, message.SourceGroup)), + convert := func(e gjson.Result) *message.ForwardNode { + if e.Get("type").Str != "node" { + return nil + } + if e.Get("data.id").Exists() { + i := e.Get("data.id").Int() + m, _ := db.GetGroupMessageByGlobalID(int32(i)) + if m != nil { + msgTime := m.Attribute.Timestamp + if msgTime == 0 { + msgTime = ts.Unix() + } + return &message.ForwardNode{ + SenderId: m.Attribute.SenderUin, + SenderName: m.Attribute.SenderName, + Time: int32(msgTime), + Message: resolveElement(bot.ConvertContentMessage(m.Content, message.SourceGroup)), + } } + log.Warnf("警告: 引用消息 %v 错误或数据库未开启.", e.Get("data.id").Str) + return nil } - log.Warnf("警告: 引用消息 %v 错误或数据库未开启.", e.Get("data.id").Str) - return nil - } - uin := e.Get("data.[user_id,uin].0").Int() - msgTime := e.Get("data.time").Int() - if msgTime == 0 { - msgTime = ts.Unix() - } - name := e.Get("data.name").Str - c := e.Get("data.content") - if c.IsArray() { - nested := false - c.ForEach(func(_, value gjson.Result) bool { - if value.Get("type").Str == "node" { - nested = true - return false + uin := e.Get("data.[user_id,uin].0").Int() + msgTime := e.Get("data.time").Int() + if msgTime == 0 { + msgTime = ts.Unix() + } + name := e.Get("data.name").Str + c := e.Get("data.content") + if c.IsArray() { + nested := false + c.ForEach(func(_, value gjson.Result) bool { + if value.Get("type").Str == "node" { + nested = true + return false + } + return true + }) + if nested { // 处理嵌套 + nestedNode := builder.NestedNode() + builder.Link(nestedNode, convertMessage(c)) + return &message.ForwardNode{ + SenderId: uin, + SenderName: name, + Time: int32(msgTime), + Message: []message.IMessageElement{nestedNode}, + } } - return true - }) - if nested { // 处理嵌套 - fe := bot.uploadForwardElement(c, groupID) + } + content := bot.ConvertObjectMessage(c, message.SourceGroup) + if uin != 0 && name != "" && len(content) > 0 { return &message.ForwardNode{ SenderId: uin, SenderName: name, Time: int32(msgTime), - Message: []message.IMessageElement{fe}, + Message: resolveElement(content), } } + log.Warnf("警告: 非法 Forward node 将跳过. uin: %v name: %v content count: %v", uin, name, len(content)) + return nil } - content := bot.ConvertObjectMessage(c, message.SourceGroup) - if uin != 0 && name != "" && len(content) > 0 { - return &message.ForwardNode{ - SenderId: uin, - SenderName: name, - Time: int32(msgTime), - Message: resolveElement(content), - } - } - log.Warnf("警告: 非法 Forward node 将跳过. uin: %v name: %v content count: %v", uin, name, len(content)) - return nil - } - if m.IsArray() { - for _, item := range m.Array() { - node := convert(item) + if m.IsArray() { + for _, item := range m.Array() { + node := convert(item) + if node != nil { + fm.AddNode(node) + } + } + } else { + node := convert(m) if node != nil { fm.AddNode(node) } } - } else { - node := convert(m) - if node != nil { - fm.AddNode(node) - } + + w.wait() + return fm } - w.wait() - return bot.Client.UploadGroupForwardMessage(groupID, fm) + return builder.Main(convertMessage(m)) } // CQSendGroupForwardMessage 扩展API-发送合并转发(群) @@ -912,17 +916,17 @@ func (bot *CQBot) CQSendGroupForwardMessage(groupID int64, m gjson.Result) globa } fe := bot.uploadForwardElement(m, groupID) - if fe != nil { - ret := bot.Client.SendGroupForwardMessage(groupID, fe) - if ret == nil || ret.Id == -1 { - log.Warnf("合并转发(群)消息发送失败: 账号可能被风控.") - return Failed(100, "SEND_MSG_API_ERROR", "请参考 go-cqhttp 端输出") - } - return OK(global.MSG{ - "message_id": bot.InsertGroupMessage(ret), - }) + if fe == nil { + return Failed(100, "EMPTY_NODES", "未找到任何可发送的合并转发信息") + } + ret := bot.Client.SendGroupForwardMessage(groupID, fe) + if ret == nil || ret.Id == -1 { + log.Warnf("合并转发(群)消息发送失败: 账号可能被风控.") + return Failed(100, "SEND_MSG_API_ERROR", "请参考 go-cqhttp 端输出") } - return Failed(100, "EMPTY_NODES", "未找到任何可发送的合并转发信息") + return OK(global.MSG{ + "message_id": bot.InsertGroupMessage(ret), + }) } // CQSendPrivateMessage 发送私聊消息 diff --git a/go.mod b/go.mod index 43649e2b..abf9dc24 100644 --- a/go.mod +++ b/go.mod @@ -4,8 +4,8 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220320070754-38990f6e1cf9 - github.com/RomiChan/syncx v0.0.0-20220320065321-8d448f958257 + github.com/Mrs4s/MiraiGo v0.0.0-20220321133915-aa657c0f09d0 + github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible diff --git a/go.sum b/go.sum index 2442768e..95564b9e 100644 --- a/go.sum +++ b/go.sum @@ -1,11 +1,11 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220320070754-38990f6e1cf9 h1:YJeHJRNVfpbuC7wSQD3WOcysC7AcILgQf5d8kFPL12Y= -github.com/Mrs4s/MiraiGo v0.0.0-20220320070754-38990f6e1cf9/go.mod h1:qseuVVwl5wxdhphaS29F6CN0gV2J0ojT880Ql5g2MBo= +github.com/Mrs4s/MiraiGo v0.0.0-20220321133915-aa657c0f09d0 h1:RsFAUylRh9T4zIx4iVe8KTbG/XtI/uHw2qhhQfoCetE= +github.com/Mrs4s/MiraiGo v0.0.0-20220321133915-aa657c0f09d0/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= -github.com/RomiChan/syncx v0.0.0-20220320065321-8d448f958257 h1:fdMod+DEoiICoTtS1Wij/wl1d57FPvKVmretLi2sGD8= -github.com/RomiChan/syncx v0.0.0-20220320065321-8d448f958257/go.mod h1:KqZzu7slNKROh3TSYEH/IUMG6f4M+1qubZ5e52QypsE= +github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= +github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c/go.mod h1:KqZzu7slNKROh3TSYEH/IUMG6f4M+1qubZ5e52QypsE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= From e4d10eb2ae37ff07c93f571214efbbbacb70c1ff Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Tue, 22 Mar 2022 22:56:06 +0800 Subject: [PATCH 54/93] global: use net/netip --- global/fs.go | 14 ++++++-------- go.mod | 2 +- go.sum | 4 ++-- 3 files changed, 9 insertions(+), 11 deletions(-) diff --git a/global/fs.go b/global/fs.go index be15a589..3c197712 100644 --- a/global/fs.go +++ b/global/fs.go @@ -5,12 +5,11 @@ import ( "crypto/md5" "encoding/hex" "errors" - "net" + "net/netip" "net/url" "os" "path" "runtime" - "strconv" "strings" "github.com/Mrs4s/MiraiGo/utils" @@ -129,19 +128,18 @@ func DelFile(path string) bool { } // ReadAddrFile 从给定path中读取合法的IP地址与端口,每个IP地址以换行符"\n"作为分隔 -func ReadAddrFile(path string) []*net.TCPAddr { +func ReadAddrFile(path string) []netip.AddrPort { d, err := os.ReadFile(path) if err != nil { return nil } str := string(d) lines := strings.Split(str, "\n") - var ret []*net.TCPAddr + var ret []netip.AddrPort for _, l := range lines { - ip := strings.Split(strings.TrimSpace(l), ":") - if len(ip) == 2 { - port, _ := strconv.Atoi(ip[1]) - ret = append(ret, &net.TCPAddr{IP: net.ParseIP(ip[0]), Port: port}) + addr, err := netip.ParseAddrPort(l) + if err == nil { + ret = append(ret, addr) } } return ret diff --git a/go.mod b/go.mod index abf9dc24..38ab2a0d 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220321133915-aa657c0f09d0 + github.com/Mrs4s/MiraiGo v0.0.0-20220322144437-665c6acf024a github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index 95564b9e..0b7e4b44 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220321133915-aa657c0f09d0 h1:RsFAUylRh9T4zIx4iVe8KTbG/XtI/uHw2qhhQfoCetE= -github.com/Mrs4s/MiraiGo v0.0.0-20220321133915-aa657c0f09d0/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= +github.com/Mrs4s/MiraiGo v0.0.0-20220322144437-665c6acf024a h1:rG0RcLo/kWRAXnVLgMkudktVO2yg3kVgdV1/Zc9fwh4= +github.com/Mrs4s/MiraiGo v0.0.0-20220322144437-665c6acf024a/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= From f63c59f1a40a4210bea6a59b10a658257722a2e0 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 23 Mar 2022 19:32:32 +0800 Subject: [PATCH 55/93] server: new config format for HTTP server and Websocket server For #1415 Fixes #1438 --- go.mod | 2 +- go.sum | 4 ++-- server/http.go | 30 ++++++++++++++++++------------ server/websocket.go | 23 ++++++++++++++++++++--- 4 files changed, 41 insertions(+), 18 deletions(-) diff --git a/go.mod b/go.mod index 38ab2a0d..645550d1 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220322144437-665c6acf024a + github.com/Mrs4s/MiraiGo v0.0.0-20220323044857-868828f3da83 github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index 0b7e4b44..cedc9579 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220322144437-665c6acf024a h1:rG0RcLo/kWRAXnVLgMkudktVO2yg3kVgdV1/Zc9fwh4= -github.com/Mrs4s/MiraiGo v0.0.0-20220322144437-665c6acf024a/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= +github.com/Mrs4s/MiraiGo v0.0.0-20220323044857-868828f3da83 h1:2OA6ciqUytCaV7LQr/IvwCqRXJpc8bfvta63bn2XkHc= +github.com/Mrs4s/MiraiGo v0.0.0-20220323044857-868828f3da83/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= diff --git a/server/http.go b/server/http.go index b289eef8..a43a2408 100644 --- a/server/http.go +++ b/server/http.go @@ -8,6 +8,7 @@ import ( "encoding/json" "fmt" "io" + "net" "net/http" "net/url" "os" @@ -31,6 +32,7 @@ import ( // HTTPServer HTTP通信相关配置 type HTTPServer struct { Disabled bool `yaml:"disabled"` + Address string `yaml:"address"` Host string `yaml:"host"` Port int `yaml:"port"` Timeout int32 `yaml:"timeout"` @@ -242,12 +244,20 @@ func runHTTP(bot *coolq.CQBot, node yaml.Node) { return } - var addr string + network, addr := "tcp", "" s := &httpServer{accessToken: conf.AccessToken} - if conf.Host == "" || conf.Port == 0 { + if conf.Address != "" { + uri, err := url.Parse(conf.Address) + if err == nil && uri.Scheme != "" { + network = uri.Scheme + addr = uri.Host + } + } else if conf.Host != "" || conf.Port != 0 { + addr = fmt.Sprintf("%s:%d", conf.Host, conf.Port) + log.Warnln("HTTP 服务器使用了过时的配置格式,请更新配置文件!") + } else { goto client } - addr = fmt.Sprintf("%s:%d", conf.Host, conf.Port) s.api = api.NewCaller(bot) if conf.RateLimit.Enabled { s.api.Use(rateLimit(conf.RateLimit.Frequency, conf.RateLimit.Bucket)) @@ -255,20 +265,16 @@ func runHTTP(bot *coolq.CQBot, node yaml.Node) { if conf.LongPolling.Enabled { s.api.Use(longPolling(bot, conf.LongPolling.MaxQueueSize)) } - go func() { - log.Infof("CQ HTTP 服务器已启动: %v", addr) - server := &http.Server{ - Addr: addr, - Handler: s, - } - if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed { - log.Error(err) - log.Infof("HTTP 服务启动失败, 请检查端口是否被占用.") + listener, err := net.Listen(network, addr) + if err != nil { + log.Infof("HTTP 服务启动失败, 请检查端口是否被占用: %v", err) log.Warnf("将在五秒后退出.") time.Sleep(time.Second * 5) os.Exit(1) } + log.Infof("CQ HTTP 服务器已启动: %v", listener.Addr()) + log.Fatal(http.Serve(listener, s)) }() client: for _, c := range conf.Post { diff --git a/server/websocket.go b/server/websocket.go index 20d3a73b..888cd49c 100644 --- a/server/websocket.go +++ b/server/websocket.go @@ -4,7 +4,9 @@ import ( "bytes" "encoding/json" "fmt" + "net" "net/http" + "net/url" "runtime/debug" "strconv" "strings" @@ -100,6 +102,7 @@ const wsReverseDefault = ` # 反向WS设置 // WebsocketServer 正向WS相关配置 type WebsocketServer struct { Disabled bool `yaml:"disabled"` + Address string `yaml:"address"` Host string `yaml:"host"` Port int `yaml:"port"` @@ -139,6 +142,17 @@ func runWSServer(b *coolq.CQBot, node yaml.Node) { return } + network, address := "tcp", conf.Address + if conf.Address == "" && (conf.Host != "" || conf.Port != 0) { + log.Warn("正向 Websocket 使用了过时的配置格式,请更新配置文件") + address = fmt.Sprintf("%s:%d", conf.Host, conf.Port) + } else { + addr, err := url.Parse(conf.Address) + if err == nil && addr.Scheme != "" { + network = addr.Scheme + address = addr.Host + } + } s := &webSocketServer{ bot: b, conf: &conf, @@ -146,7 +160,6 @@ func runWSServer(b *coolq.CQBot, node yaml.Node) { filter: conf.Filter, } filter.Add(s.filter) - addr := fmt.Sprintf("%s:%d", conf.Host, conf.Port) s.handshake = fmt.Sprintf(`{"_post_method":2,"meta_event_type":"lifecycle","post_type":"meta_event","self_id":%d,"sub_type":"connect","time":%d}`, b.Client.Uin, time.Now().Unix()) b.OnEventPush(s.onBotPushEvent) @@ -154,8 +167,12 @@ func runWSServer(b *coolq.CQBot, node yaml.Node) { mux.HandleFunc("/event", s.event) mux.HandleFunc("/api", s.api) mux.HandleFunc("/", s.any) - log.Infof("CQ WebSocket 服务器已启动: %v", addr) - log.Fatal(http.ListenAndServe(addr, &mux)) + listener, err := net.Listen(network, address) + if err != nil { + log.Fatal(err) + } + log.Infof("CQ WebSocket 服务器已启动: %v", listener.Addr()) + log.Fatal(http.Serve(listener, &mux)) } // runWSClient 运行一个反向向WS client From d42d8dd3951545d38b92c571eed614986abd1e65 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 23 Mar 2022 19:55:21 +0800 Subject: [PATCH 56/93] server: add uri Path to address For #1415 --- server/http.go | 11 ++++++----- server/websocket.go | 8 ++++---- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/server/http.go b/server/http.go index a43a2408..8bc362c9 100644 --- a/server/http.go +++ b/server/http.go @@ -244,18 +244,19 @@ func runHTTP(bot *coolq.CQBot, node yaml.Node) { return } - network, addr := "tcp", "" + network, addr := "tcp", conf.Address s := &httpServer{accessToken: conf.AccessToken} - if conf.Address != "" { + switch { + case conf.Address != "": uri, err := url.Parse(conf.Address) if err == nil && uri.Scheme != "" { network = uri.Scheme - addr = uri.Host + addr = uri.Host + uri.Path } - } else if conf.Host != "" || conf.Port != 0 { + case conf.Host != "" || conf.Port != 0: addr = fmt.Sprintf("%s:%d", conf.Host, conf.Port) log.Warnln("HTTP 服务器使用了过时的配置格式,请更新配置文件!") - } else { + default: goto client } s.api = api.NewCaller(bot) diff --git a/server/websocket.go b/server/websocket.go index 888cd49c..df8c9a22 100644 --- a/server/websocket.go +++ b/server/websocket.go @@ -147,10 +147,10 @@ func runWSServer(b *coolq.CQBot, node yaml.Node) { log.Warn("正向 Websocket 使用了过时的配置格式,请更新配置文件") address = fmt.Sprintf("%s:%d", conf.Host, conf.Port) } else { - addr, err := url.Parse(conf.Address) - if err == nil && addr.Scheme != "" { - network = addr.Scheme - address = addr.Host + uri, err := url.Parse(conf.Address) + if err == nil && uri.Scheme != "" { + network = uri.Scheme + address = uri.Host + uri.Path } } s := &webSocketServer{ From 40a765b1171e432e2e21c55cb926c23326762eb2 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 23 Mar 2022 21:06:32 +0800 Subject: [PATCH 57/93] server: support unix socket Fixes #1415 --- server/http.go | 33 ++++++++++++++++++++++----- server/websocket.go | 54 ++++++++++++++++++++++++++++++++++++--------- 2 files changed, 72 insertions(+), 15 deletions(-) diff --git a/server/http.go b/server/http.go index 8bc362c9..32163431 100644 --- a/server/http.go +++ b/server/http.go @@ -2,8 +2,10 @@ package server import ( "bytes" + "context" "crypto/hmac" "crypto/sha1" + "encoding/base64" "encoding/hex" "encoding/json" "fmt" @@ -65,6 +67,7 @@ type HTTPClient struct { filter string apiPort int timeout int32 + client *http.Client MaxRetries uint64 RetriesInterval uint64 } @@ -77,8 +80,7 @@ type httpCtx struct { const httpDefault = ` - http: # HTTP 通信设置 - host: 127.0.0.1 # 服务端监听地址 - port: 5700 # 服务端监听端口 + address: 0.0.0.0:5700 # HTTP监听地址 timeout: 5 # 反向 HTTP 超时时间, 单位秒,<5 时将被忽略 long-polling: # 长轮询拓展 enabled: false # 是否开启 @@ -300,8 +302,30 @@ func (c HTTPClient) Run() { if c.timeout < 5 { c.timeout = 5 } + rawAddress := c.addr + network, address := resolveURI(c.addr) + client := &http.Client{ + Timeout: time.Second * time.Duration(c.timeout), + Transport: &http.Transport{ + DialContext: func(_ context.Context, _, addr string) (net.Conn, error) { + if network == "unix" { + host, _, err := net.SplitHostPort(addr) + if err != nil { + host = addr + } + filepath, err := base64.RawURLEncoding.DecodeString(host) + if err == nil { + addr = string(filepath) + } + } + return net.Dial(network, addr) + }, + }, + } + c.addr = address // clean path + c.client = client + log.Infof("HTTP POST上报器已启动: %v", rawAddress) c.bot.OnEventPush(c.onBotPushEvent) - log.Infof("HTTP POST上报器已启动: %v", c.addr) } func (c *HTTPClient) onBotPushEvent(e *coolq.Event) { @@ -313,7 +337,6 @@ func (c *HTTPClient) onBotPushEvent(e *coolq.Event) { } } - client := http.Client{Timeout: time.Second * time.Duration(c.timeout)} header := make(http.Header) header.Set("X-Self-ID", strconv.FormatInt(c.bot.Client.Uin, 10)) header.Set("User-Agent", "CQHttp/4.15.0") @@ -338,7 +361,7 @@ func (c *HTTPClient) onBotPushEvent(e *coolq.Event) { } req.Header = header - res, err = client.Do(req) + res, err = c.client.Do(req) if res != nil { //goland:noinspection GoDeferInLoop defer res.Body.Close() diff --git a/server/websocket.go b/server/websocket.go index df8c9a22..0c09c12a 100644 --- a/server/websocket.go +++ b/server/websocket.go @@ -2,6 +2,7 @@ package server import ( "bytes" + "encoding/base64" "encoding/json" "fmt" "net" @@ -77,9 +78,7 @@ var upgrader = websocket.Upgrader{ const wsDefault = ` # 正向WS设置 - ws: # 正向WS服务器监听地址 - host: 127.0.0.1 - # 正向WS服务器监听端口 - port: 6700 + address: 0.0.0.0:8080 middlewares: <<: *default # 引用默认中间件 ` @@ -213,8 +212,25 @@ func runWSClient(b *coolq.CQBot, node yaml.Node) { } } -func (c *websocketClient) connect(typ, url string, conptr **wsConn) { - log.Infof("开始尝试连接到反向WebSocket %s服务器: %v", typ, url) +func resolveURI(addr string) (network, address string) { + network, address = "tcp", addr + uri, err := url.Parse(addr) + if err == nil && uri.Scheme != "" { + scheme, ext, _ := strings.Cut(uri.Scheme, "+") + if ext != "" { + network = ext + uri.Scheme = scheme // remove `+unix`/`+tcp4` + if ext == "unix" { + uri.Host = base64.StdEncoding.EncodeToString([]byte(uri.Host + uri.Path)) + } + address = uri.String() + } + } + return +} + +func (c *websocketClient) connect(typ, addr string, conptr **wsConn) { + log.Infof("开始尝试连接到反向WebSocket %s服务器: %v", typ, addr) header := http.Header{ "X-Client-Role": []string{typ}, "X-Self-ID": []string{strconv.FormatInt(c.bot.Client.Uin, 10)}, @@ -223,12 +239,30 @@ func (c *websocketClient) connect(typ, url string, conptr **wsConn) { if c.token != "" { header["Authorization"] = []string{"Token " + c.token} } - conn, _, err := websocket.DefaultDialer.Dial(url, header) // nolint + + network, address := resolveURI(addr) + dialer := websocket.Dialer{ + NetDial: func(_, addr string) (net.Conn, error) { + if network == "unix" { + host, _, err := net.SplitHostPort(addr) + if err != nil { + host = addr + } + filepath, err := base64.RawURLEncoding.DecodeString(host) + if err == nil { + addr = string(filepath) + } + } + return net.Dial(network, addr) // support unix socket transport + }, + } + + conn, _, err := dialer.Dial(address, header) // nolint if err != nil { - log.Warnf("连接到反向WebSocket %s服务器 %v 时出现错误: %v", typ, url, err) + log.Warnf("连接到反向WebSocket %s服务器 %v 时出现错误: %v", typ, addr, err) if c.reconnectInterval != 0 { time.Sleep(c.reconnectInterval) - c.connect(typ, url, conptr) + c.connect(typ, addr, conptr) } return } @@ -242,7 +276,7 @@ func (c *websocketClient) connect(typ, url string, conptr **wsConn) { } } - log.Infof("已连接到反向WebSocket %s服务器 %v", typ, url) + log.Infof("已连接到反向WebSocket %s服务器 %v", typ, addr) var wrappedConn *wsConn if conptr != nil && *conptr != nil { @@ -261,7 +295,7 @@ func (c *websocketClient) connect(typ, url string, conptr **wsConn) { } if typ != "Event" { - go c.listenAPI(typ, url, wrappedConn) + go c.listenAPI(typ, addr, wrappedConn) } } From d161f35c69d8c61779d755fa070e4870083c2b69 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 23 Mar 2022 21:25:31 +0800 Subject: [PATCH 58/93] server: fix unix socket path For #1415 --- server/websocket.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/server/websocket.go b/server/websocket.go index 0c09c12a..f6000172 100644 --- a/server/websocket.go +++ b/server/websocket.go @@ -221,7 +221,8 @@ func resolveURI(addr string) (network, address string) { network = ext uri.Scheme = scheme // remove `+unix`/`+tcp4` if ext == "unix" { - uri.Host = base64.StdEncoding.EncodeToString([]byte(uri.Host + uri.Path)) + uri.Host, uri.Path, _ = strings.Cut(uri.Path, ":") + uri.Host = base64.StdEncoding.EncodeToString([]byte(uri.Host)) } address = uri.String() } From ee9af5fa69c5e7b9f8d95492cc824eb4e45ae0d1 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sat, 26 Mar 2022 14:39:28 +0800 Subject: [PATCH 59/93] server: refactor http post retry --- server/http.go | 28 ++++++++++++---------------- 1 file changed, 12 insertions(+), 16 deletions(-) diff --git a/server/http.go b/server/http.go index 32163431..a4710115 100644 --- a/server/http.go +++ b/server/http.go @@ -350,36 +350,32 @@ func (c *HTTPClient) onBotPushEvent(e *coolq.Event) { header.Set("X-API-Port", strconv.FormatInt(int64(c.apiPort), 10)) } + var req *http.Request var res *http.Response + var err error for i := uint64(0); i <= c.MaxRetries; i++ { // see https://stackoverflow.com/questions/31337891/net-http-http-contentlength-222-with-body-length-0 // we should create a new request for every single post trial - req, err := http.NewRequest("POST", c.addr, bytes.NewReader(e.JSONBytes())) + req, err = http.NewRequest("POST", c.addr, bytes.NewReader(e.JSONBytes())) if err != nil { log.Warnf("上报 Event 数据到 %v 时创建请求失败: %v", c.addr, err) return } req.Header = header - res, err = c.client.Do(req) - if res != nil { - //goland:noinspection GoDeferInLoop - defer res.Body.Close() - } - if err == nil { - break - } - if i < c.MaxRetries { - log.Warnf("上报 Event 数据到 %v 失败: %v 将进行第 %d 次重试", c.addr, err, i+1) - } else { - log.Warnf("上报 Event 数据 %s 到 %v 失败: %v 停止上报:已达重试上线", e.JSONBytes(), c.addr, err) - return + if err != nil { + if i < c.MaxRetries { + log.Warnf("上报 Event 数据到 %v 失败: %v 将进行第 %d 次重试", c.addr, err, i+1) + } else { + log.Warnf("上报 Event 数据 %s 到 %v 失败: %v 停止上报:已达重试上限", e.JSONBytes(), c.addr, err) + return + } + time.Sleep(time.Millisecond * time.Duration(c.RetriesInterval)) } - time.Sleep(time.Millisecond * time.Duration(c.RetriesInterval)) } + defer res.Body.Close() log.Debugf("上报Event数据 %s 到 %v", e.JSONBytes(), c.addr) - r, err := io.ReadAll(res.Body) if err != nil { return From d52237831544dcc9a4a84181b78bf16d259478bc Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 27 Mar 2022 22:53:00 +0800 Subject: [PATCH 60/93] all: optimize detected by go-perfguard --- coolq/api.go | 4 ++-- coolq/cqcode.go | 4 ++-- db/leveldb/writer.go | 5 ++--- global/log_hook.go | 3 ++- global/net.go | 4 ++-- internal/selfupdate/update.go | 2 +- server/daemon.go | 4 ++-- server/scf.go | 2 +- 8 files changed, 14 insertions(+), 14 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 486b543b..44a52e87 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1342,7 +1342,7 @@ func (bot *CQBot) CQHandleQuickOperation(context, operation gjson.Result) global if reply.Exists() { autoEscape := param.EnsureBool(operation.Get("auto_escape"), false) - at := operation.Get("at_sender").Bool() && !isAnonymous && msgType == "group" + at := !isAnonymous && operation.Get("at_sender").Bool() && msgType == "group" if at && reply.IsArray() { // 在 reply 数组头部插入CQ码 replySegments := make([]global.MSG, 0) @@ -1388,7 +1388,7 @@ func (bot *CQBot) CQHandleQuickOperation(context, operation gjson.Result) global if operation.Get("delete").Bool() { bot.CQDeleteMessage(int32(context.Get("message_id").Int())) } - if operation.Get("kick").Bool() && !isAnonymous { + if !isAnonymous && operation.Get("kick").Bool() { bot.CQSetGroupKick(context.Get("group_id").Int(), context.Get("user_id").Int(), "", operation.Get("reject_add_request").Bool()) } if operation.Get("ban").Bool() { diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 1e97f4b8..6b9edac1 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -209,7 +209,7 @@ func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []glo case *message.DiceElement: m = global.MSG{ "type": "dice", - "data": map[string]string{"value": fmt.Sprint(o.Value)}, + "data": map[string]string{"value": strconv.FormatInt(int64(o.Value), 10)}, } case *message.MarketFaceElement: m = global.MSG{ @@ -1192,7 +1192,7 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy } return &LocalImageElement{File: fu.Path, URL: f}, nil } - if strings.HasPrefix(f, "base64") && !video { + if !video && strings.HasPrefix(f, "base64") { b, err := param.Base64DecodeString(strings.TrimPrefix(f, "base64://")) if err != nil { return nil, err diff --git a/db/leveldb/writer.go b/db/leveldb/writer.go index a8fe7075..baed92a2 100644 --- a/db/leveldb/writer.go +++ b/db/leveldb/writer.go @@ -2,7 +2,6 @@ package leveldb import ( "bytes" - "io" "github.com/Mrs4s/go-cqhttp/global" ) @@ -125,7 +124,7 @@ func (w *writer) bytes() []byte { out.uvarint(dataVersion) out.uvarint(uint64(w.strings.Len())) out.uvarint(uint64(w.data.Len())) - _, _ = io.Copy(&out, &w.strings) - _, _ = io.Copy(&out, &w.data) + _, _ = w.strings.WriteTo(&out) + _, _ = w.data.WriteTo(&out) return out.Bytes() } diff --git a/global/log_hook.go b/global/log_hook.go index b93f1307..44f4f1d8 100644 --- a/global/log_hook.go +++ b/global/log_hook.go @@ -195,7 +195,8 @@ func (f LogFormat) Format(entry *logrus.Entry) ([]byte, error) { buf.WriteString(colorReset) } - ret := append([]byte(nil), buf.Bytes()...) // copy buffer + ret := make([]byte, len(buf.Bytes())) + copy(ret, buf.Bytes()) // copy buffer return ret, nil } diff --git a/global/net.go b/global/net.go index ce74edbe..c72000a2 100644 --- a/global/net.go +++ b/global/net.go @@ -79,7 +79,7 @@ func DownloadFile(url, path string, limit int64, headers map[string]string) erro if limit > 0 && resp.ContentLength > limit { return ErrOverSize } - _, err = io.Copy(file, resp.Body) + _, err = file.ReadFrom(resp.Body) if err != nil { return err } @@ -107,7 +107,7 @@ func DownloadFileMultiThreading(url, path string, limit int64, threadCount int, return err } defer file.Close() - if _, err = io.Copy(file, s); err != nil { + if _, err = file.ReadFrom(s); err != nil { return err } return errUnsupportedMultiThreading diff --git a/internal/selfupdate/update.go b/internal/selfupdate/update.go index 5aa52a3a..8771502b 100644 --- a/internal/selfupdate/update.go +++ b/internal/selfupdate/update.go @@ -188,7 +188,7 @@ func fromStream(updateWith io.Reader) (err error, errRecover error) { } // We won't log this error, because it's always going to happen. defer func() { _ = fp.Close() }() - if _, err = io.Copy(fp, bufio.NewReader(updateWith)); err != nil { + if _, err = bufio.NewReader(updateWith).WriteTo(fp); err != nil { logrus.Errorf("Unable to copy data: %v\n", err) } diff --git a/server/daemon.go b/server/daemon.go index f2746d01..0a570b62 100644 --- a/server/daemon.go +++ b/server/daemon.go @@ -3,9 +3,9 @@ package server // daemon 功能写在这,目前仅支持了-d 作为后台运行参数,stop,start,restart这些功能目前看起来并不需要,可以通过api控制,后续需要的话再补全。 import ( - "fmt" "os" "os/exec" + "strconv" "strings" "github.com/Mrs4s/go-cqhttp/global" @@ -36,7 +36,7 @@ func Daemon() { log.Info("[PID] ", proc.Process.Pid) // pid写入到pid文件中,方便后续stop的时候kill - pidErr := savePid("go-cqhttp.pid", fmt.Sprintf("%d", proc.Process.Pid)) + pidErr := savePid("go-cqhttp.pid", strconv.FormatInt(int64(proc.Process.Pid), 10)) if pidErr != nil { log.Errorf("save pid file error: %v", pidErr) } diff --git a/server/scf.go b/server/scf.go index f41b3597..7d95e7f0 100644 --- a/server/scf.go +++ b/server/scf.go @@ -54,7 +54,7 @@ func (l *lambdaResponseWriter) flush() error { buffer := global.NewBuffer() defer global.PutBuffer(buffer) body := utils.B2S(l.buf.Bytes()) - header := make(map[string]string) + header := make(map[string]string, len(l.header)) for k, v := range l.header { header[k] = v[0] } From fb33d93b311557d4115e22c216109fcb656d6873 Mon Sep 17 00:00:00 2001 From: ishkong <19740260+ishkong@users.noreply.github.com> Date: Mon, 28 Mar 2022 13:00:29 +0800 Subject: [PATCH 61/93] =?UTF-8?q?=F0=9F=91=BD=EF=B8=8F=20Update=20ffrmpeg?= =?UTF-8?q?=20screenshot=20command?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Ref: https://trac.ffmpeg.org/wiki/Create%20a%20thumbnail%20image%20every%20X%20seconds%20of%20the%20video Force a screenshot of the 0th second of the video --- global/codec.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/global/codec.go b/global/codec.go index 223c5337..6a5f088c 100644 --- a/global/codec.go +++ b/global/codec.go @@ -43,6 +43,6 @@ func EncodeMP4(src string, dst string) error { // -y 覆盖文件 // ExtractCover 获取给定视频文件的Cover func ExtractCover(src string, target string) error { - cmd := exec.Command("ffmpeg", "-i", src, "-y", "-r", "1", "-f", "image2", target) + cmd := exec.Command("ffmpeg", "-i", src, "-y", "-ss", "0", "-frames:v", "1", target) return errors.Wrap(cmd.Run(), "extract video cover failed") } From b4c3f2340e0d288d46633b006f90b94840364f86 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 28 Mar 2022 13:43:39 +0800 Subject: [PATCH 62/93] dep: update MiraiGo --- coolq/cqcode.go | 12 +++++------- go.mod | 2 +- go.sum | 4 ++-- 3 files changed, 8 insertions(+), 10 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 6b9edac1..c9d3c541 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -1119,14 +1119,12 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType message.So _, _ = video.Seek(0, io.SeekStart) hash, _ := utils.ComputeMd5AndLength(video) cacheFile := path.Join(global.CachePath, hex.EncodeToString(hash)+".mp4") - if global.PathExists(cacheFile) && (d["cache"] == "" || d["cache"] == "1") { - goto ok - } - err = global.EncodeMP4(v.File, cacheFile) - if err != nil { - return nil, err + if !(d["cache"] == "" || d["cache"] == "1") || !global.PathExists(cacheFile) { + err = global.EncodeMP4(v.File, cacheFile) + if err != nil { + return nil, err + } } - ok: v.File = cacheFile } return v, nil diff --git a/go.mod b/go.mod index 645550d1..574f3a38 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220323044857-868828f3da83 + github.com/Mrs4s/MiraiGo v0.0.0-20220328053558-4f05838b6c18 github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index cedc9579..1c8a29a0 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220323044857-868828f3da83 h1:2OA6ciqUytCaV7LQr/IvwCqRXJpc8bfvta63bn2XkHc= -github.com/Mrs4s/MiraiGo v0.0.0-20220323044857-868828f3da83/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= +github.com/Mrs4s/MiraiGo v0.0.0-20220328053558-4f05838b6c18 h1:v8nim0qO+OvtaQPD0tMxUAEUH1ktfV7hmo6o4k+9aw8= +github.com/Mrs4s/MiraiGo v0.0.0-20220328053558-4f05838b6c18/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= From 550c17c1844ce9b47700c1e9fb704402572b1f20 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 28 Mar 2022 15:30:10 +0800 Subject: [PATCH 63/93] dep: update MiraiGo --- go.mod | 2 +- go.sum | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 574f3a38..94f0fee7 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220328053558-4f05838b6c18 + github.com/Mrs4s/MiraiGo v0.0.0-20220328072759-e2a42e542581 github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index 1c8a29a0..59d720fe 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220328053558-4f05838b6c18 h1:v8nim0qO+OvtaQPD0tMxUAEUH1ktfV7hmo6o4k+9aw8= -github.com/Mrs4s/MiraiGo v0.0.0-20220328053558-4f05838b6c18/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= +github.com/Mrs4s/MiraiGo v0.0.0-20220328072759-e2a42e542581 h1:6RRK4cG73LD9VUDMgNAVu7cOJ5KjZ3R57gbAbbXy930= +github.com/Mrs4s/MiraiGo v0.0.0-20220328072759-e2a42e542581/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= From 0d291f79faaf65a24b38e634745433d4b2985150 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 4 Apr 2022 21:40:58 +0800 Subject: [PATCH 64/93] ci: add static check golangci-lint didn't release yet --- .github/workflows/golint.yml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/.github/workflows/golint.yml b/.github/workflows/golint.yml index 6ab8830a..fb9cc4d5 100644 --- a/.github/workflows/golint.yml +++ b/.github/workflows/golint.yml @@ -19,6 +19,12 @@ jobs: with: version: latest + - name: Static Check + uses: dominikh/staticcheck-action@v1.2.0 + with: + install-go: false + version: "2022.1" + - name: Tests run: | go test $(go list ./...) From 4a27a60456cb808964502390c9b88dfeabb2527e Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 4 Apr 2022 21:56:18 +0800 Subject: [PATCH 65/93] coolq: fix static check --- coolq/bot.go | 2 ++ coolq/cqcode.go | 35 +++++++++++++++-------------------- 2 files changed, 17 insertions(+), 20 deletions(-) diff --git a/coolq/bot.go b/coolq/bot.go index 407800f6..1d6a2615 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -361,6 +361,7 @@ func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.Sen default: if session == nil && groupID != 0 { msg := bot.Client.SendGroupTempMessage(groupID, target, m) + //lint:ignore SA9003 if msg != nil { // nolint // todo(Mrs4s) // id = bot.InsertTempMessage(target, msg) @@ -372,6 +373,7 @@ func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.Sen log.Errorf("发送临时会话消息失败: %v", err) break } + //lint:ignore SA9003 if msg != nil { // nolint // todo(Mrs4s) // id = bot.InsertTempMessage(target, msg) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index c9d3c541..96e1b922 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -142,16 +142,13 @@ func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []glo "data": map[string]string{"data": o.Content}, } case *message.AtElement: - if o.Target == 0 { - m = global.MSG{ - "type": "at", - "data": map[string]string{"qq": "all"}, - } - } else { - m = global.MSG{ - "type": "at", - "data": map[string]string{"qq": strconv.FormatUint(uint64(o.Target), 10)}, - } + target := "all" + if o.Target != 0 { + target = strconv.FormatUint(uint64(o.Target), 10) + } + m = global.MSG{ + "type": "at", + "data": map[string]string{"qq": target}, } case *message.RedBagElement: m = global.MSG{ @@ -236,9 +233,7 @@ func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []glo default: continue } - if m != nil { - r = append(r, m) - } + r = append(r, m) } return } @@ -315,9 +310,9 @@ func ToStringMessage(e []message.IMessageElement, source message.Source, isRaw . } arg += ",subType=" + strconv.FormatInt(int64(o.ImageBizType), 10) if ur { - write("[CQ:image,file=%s%s]", hex.EncodeToString(o.Md5)+".image", arg) + write("[CQ:image,file=%x.image%s]", o.Md5, arg) } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url), arg) + write("[CQ:image,file=%x.image,url=%s%s]", o.Md5, cqcode.EscapeValue(o.Url), arg) } case *message.FriendImageElement: var arg string @@ -325,9 +320,9 @@ func ToStringMessage(e []message.IMessageElement, source message.Source, isRaw . arg = ",type=flash" } if ur { - write("[CQ:image,file=%s%s]", hex.EncodeToString(o.Md5)+".image", arg) + write("[CQ:image,file=%x.image%s]", o.Md5, arg) } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url), arg) + write("[CQ:image,file=%x.image,url=%s%s]", cqcode.EscapeValue(o.Url), arg) } case *LocalImageElement: var arg string @@ -338,13 +333,13 @@ func ToStringMessage(e []message.IMessageElement, source message.Source, isRaw . if err == nil { m := md5.Sum(data) if ur { - write("[CQ:image,file=%s%s]", hex.EncodeToString(m[:])+".image", arg) + write("[CQ:image,file=%x.image%s]", m[:], arg) } else { - write("[CQ:image,file=%s,url=%s%s]", hex.EncodeToString(m[:])+".image", cqcode.EscapeValue(o.URL), arg) + write("[CQ:image,file=%x.image,url=%s%s]", m[:], cqcode.EscapeValue(o.URL), arg) } } case *message.GuildImageElement: - write("[CQ:image,file=%s,url=%s]", hex.EncodeToString(o.Md5)+".image", cqcode.EscapeValue(o.Url)) + write("[CQ:image,file=%x.image,url=%s]", o.Md5, cqcode.EscapeValue(o.Url)) case *message.DiceElement: write("[CQ:dice,value=%v]", o.Value) case *message.MarketFaceElement: From b22ff34cb7b04221d7c4fd916f8747d5ae881537 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 4 Apr 2022 22:02:10 +0800 Subject: [PATCH 66/93] coolq: fix static check --- coolq/bot.go | 4 ++-- coolq/cqcode.go | 5 ++--- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/coolq/bot.go b/coolq/bot.go index 1d6a2615..00ec19cc 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -361,7 +361,7 @@ func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.Sen default: if session == nil && groupID != 0 { msg := bot.Client.SendGroupTempMessage(groupID, target, m) - //lint:ignore SA9003 + //lint:ignore SA9003 there is a todo if msg != nil { // nolint // todo(Mrs4s) // id = bot.InsertTempMessage(target, msg) @@ -373,7 +373,7 @@ func (bot *CQBot) SendPrivateMessage(target int64, groupID int64, m *message.Sen log.Errorf("发送临时会话消息失败: %v", err) break } - //lint:ignore SA9003 + //lint:ignore SA9003 there is a todo if msg != nil { // nolint // todo(Mrs4s) // id = bot.InsertTempMessage(target, msg) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 96e1b922..8ea7aac0 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -131,6 +131,7 @@ func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []glo e[i+1] = nil } } + continue case *message.TextElement: m = global.MSG{ "type": "text", @@ -472,9 +473,7 @@ func ToMessageContent(e []message.IMessageElement) (r []global.MSG) { default: continue } - if m != nil { - r = append(r, m) - } + r = append(r, m) } return } From eaf34288de725ba4e01e93f078d94fd5509ef012 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Tue, 5 Apr 2022 21:49:03 +0800 Subject: [PATCH 67/93] fix forward --- go.mod | 2 +- go.sum | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 94f0fee7..c23a9481 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220328072759-e2a42e542581 + github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8 github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 diff --git a/go.sum b/go.sum index 59d720fe..425fad23 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220328072759-e2a42e542581 h1:6RRK4cG73LD9VUDMgNAVu7cOJ5KjZ3R57gbAbbXy930= -github.com/Mrs4s/MiraiGo v0.0.0-20220328072759-e2a42e542581/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= +github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8 h1:qkv7t94MNxwObbl1flZEZD5O0E8+R42XiZxOrppQNXc= +github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= From 18a091145af358687f653af1ed3b5322f7eba3d4 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Thu, 14 Apr 2022 21:53:00 +0800 Subject: [PATCH 68/93] style: go fmt ./... also delete mkrw.go, we can maintain this file by hand. --- coolq/cqcode/escape.go | 62 ++++------ db/leveldb/mkrw.go | 129 --------------------- db/leveldb/{database_gen.go => structs.go} | 2 - db/leveldb/writer.go | 21 +++- modules/config/config.go | 1 + 5 files changed, 40 insertions(+), 175 deletions(-) delete mode 100644 db/leveldb/mkrw.go rename db/leveldb/{database_gen.go => structs.go} (98%) diff --git a/coolq/cqcode/escape.go b/coolq/cqcode/escape.go index a9f0cdf4..cee90330 100644 --- a/coolq/cqcode/escape.go +++ b/coolq/cqcode/escape.go @@ -3,15 +3,11 @@ package cqcode import "strings" -/*EscapeText 将字符串raw中部分字符转义 - -& -> & - -[ -> [ - -] -> ] - -*/ +// EscapeText 将字符串raw中部分字符转义 +// +// - & -> & +// - [ -> [ +// - ] -> ] func EscapeText(s string) string { count := strings.Count(s, "&") count += strings.Count(s, "[") @@ -47,31 +43,22 @@ func EscapeText(s string) string { return b.String() } -/*EscapeValue 将字符串value中部分字符转义 - -, -> , - -& -> & - -[ -> [ - -] -> ] - -*/ +// EscapeValue 将字符串value中部分字符转义 +// +// - , -> , +// - & -> & +// - [ -> [ +// - ] -> ] func EscapeValue(value string) string { ret := EscapeText(value) return strings.ReplaceAll(ret, ",", ",") } -/*UnescapeText 将字符串content中部分字符反转义 - -& -> & - -[ -> [ - -] -> ] - -*/ +// UnescapeText 将字符串content中部分字符反转义 +// +// - & -> & +// - [ -> [ +// - ] -> ] func UnescapeText(content string) string { ret := content ret = strings.ReplaceAll(ret, "[", "[") @@ -80,17 +67,12 @@ func UnescapeText(content string) string { return ret } -/*UnescapeValue 将字符串content中部分字符反转义 - -, -> , - -& -> & - -[ -> [ - -] -> ] - -*/ +// UnescapeValue 将字符串content中部分字符反转义 +// +// - , -> , +// - & -> & +// - [ -> [ +// - ] -> ] func UnescapeValue(content string) string { ret := strings.ReplaceAll(content, ",", ",") return UnescapeText(ret) diff --git a/db/leveldb/mkrw.go b/db/leveldb/mkrw.go deleted file mode 100644 index d7a7489c..00000000 --- a/db/leveldb/mkrw.go +++ /dev/null @@ -1,129 +0,0 @@ -//go:build ignore - -package main - -import ( - "bytes" - "fmt" - "go/ast" - "go/format" - "go/parser" - "go/token" - "os" -) - -var output bytes.Buffer - -func fprintf(format string, args ...interface{}) { - _, _ = fmt.Fprintf(&output, format, args...) -} - -func main() { - f, _ := parser.ParseFile(token.NewFileSet(), "./../database.go", nil, 0) - fprintf("// Code generated by mkrw.go; DO NOT EDIT.\n\n") - fprintf("package leveldb\n\n") - fprintf("import \"github.com/Mrs4s/go-cqhttp/db\"\n\n") - ast.Inspect(f, func(node ast.Node) bool { - switch node := node.(type) { - case *ast.FuncDecl: - return false - case *ast.TypeSpec: - if !node.Name.IsExported() { - return false - } - x, ok := node.Type.(*ast.StructType) - if !ok { - return false - } - if x.Fields != nil && x.Fields.List != nil { - mkWrite(node) - mkRead(node) - } - } - return true - }) - out, err := format.Source(output.Bytes()) - if err != nil { - fmt.Println(string(output.Bytes())) - panic(err) - } - os.WriteFile("database_gen.go", out, 0o644) -} - -func typeName(typ ast.Expr) string { - switch typ := typ.(type) { - case *ast.Ident: - return typ.Name - case *ast.ArrayType: - if typ.Len != nil { - panic("unexpected array type") - } - return "[]" + typeName(typ.Elt) - case *ast.SelectorExpr: - return typeName(typ.X) + "." + typ.Sel.Name - } - panic("unexpected type") -} - -func mkWrite(node *ast.TypeSpec) { - typename := node.Name.String() - structType := node.Type.(*ast.StructType) - fprintf("func (w *writer) write%s(x *db.%s) {\n", typename, typename) - fprintf("if x == nil {\n") - fprintf("w.nil()\n") - fprintf("return\n") - fprintf("}\n") - fprintf("w.coder(coderStruct)\n") - for _, field := range structType.Fields.List { - switch typ := field.Type.(type) { - case *ast.Ident: - for _, name := range field.Names { - fprintf("w.%s(x.%s)\n", typ.Name, name.Name) - } - case *ast.ArrayType: - if typeName(typ) != "[]global.MSG" { - panic("unexpected array type") - } - for _, name := range field.Names { - fprintf("w.arrayMsg(x.%s)\n", name.Name) - } - case *ast.StarExpr: - for _, name := range field.Names { - fprintf("w.write%s(x.%s)\n", typeName(typ.X), name.Name) - } - } - } - fprintf("}\n\n") -} - -func mkRead(node *ast.TypeSpec) { - typename := node.Name.String() - structType := node.Type.(*ast.StructType) - fprintf(`func (r *reader) read%s() *db.%s { - coder := r.coder() - if coder == coderNil { - return nil - }`+"\n", typename, typename) - fprintf("x := &db.%s{}\n", typename) - for _, field := range structType.Fields.List { - switch typ := field.Type.(type) { - case *ast.Ident: - for _, name := range field.Names { - fprintf("x.%s = r.%s()\n", name.Name, typ.Name) - } - case *ast.ArrayType: - if typeName(typ) != "[]global.MSG" { - panic("unexpected array type") - } - for _, name := range field.Names { - fprintf("x.%s = r.arrayMsg()\n", name.Name) - } - case *ast.StarExpr: - for _, name := range field.Names { - fprintf("x.%s = r.read%s()\n", name.Name, typeName(typ.X)) - } - } - } - fprintf("return x\n") - fprintf("}\n\n") -} diff --git a/db/leveldb/database_gen.go b/db/leveldb/structs.go similarity index 98% rename from db/leveldb/database_gen.go rename to db/leveldb/structs.go index 929aeac1..dfb7caad 100644 --- a/db/leveldb/database_gen.go +++ b/db/leveldb/structs.go @@ -1,5 +1,3 @@ -// Code generated by mkrw.go; DO NOT EDIT. - package leveldb import "github.com/Mrs4s/go-cqhttp/db" diff --git a/db/leveldb/writer.go b/db/leveldb/writer.go index baed92a2..6067ca10 100644 --- a/db/leveldb/writer.go +++ b/db/leveldb/writer.go @@ -23,12 +23,25 @@ func (w *intWriter) uvarint(x uint64) { } // writer implements the index write. +// // data format(use uvarint to encode integers): -// | version | string data length | index data length | string data | index data | +// +// - version +// - string data length +// - index data length +// - string data +// - index data +// // for string data part, each string is encoded as: -// | string length | string | -// for index data part, each value is encoded as: -// | coder | value | +// +// - string length +// - string +// +// for index data part, each object value is encoded as: +// +// - coder +// - value +// // * coder is the identifier of value's type. // * specially for string, it's value is the offset in string data part. type writer struct { diff --git a/modules/config/config.go b/modules/config/config.go index 158bd623..23329d7f 100644 --- a/modules/config/config.go +++ b/modules/config/config.go @@ -14,6 +14,7 @@ import ( ) // defaultConfig 默认配置文件 +// //go:embed default_config.yml var defaultConfig string From 859f40db837bc0ec60deb31458976a730a277b01 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=BA=90=E6=96=87=E9=9B=A8?= <41315874+fumiama@users.noreply.github.com> Date: Tue, 10 May 2022 16:50:38 +0800 Subject: [PATCH 69/93] feat: support binary encoding method base16384 --- coolq/cqcode.go | 8 ++++++++ global/fs.go | 7 +++++++ go.mod | 5 +++-- go.sum | 9 ++++++--- 4 files changed, 24 insertions(+), 5 deletions(-) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 8ea7aac0..870b0e66 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -19,6 +19,7 @@ import ( "github.com/Mrs4s/MiraiGo/binary" "github.com/Mrs4s/MiraiGo/message" "github.com/Mrs4s/MiraiGo/utils" + b14 "github.com/fumiama/go-base16384" log "github.com/sirupsen/logrus" "github.com/tidwall/gjson" @@ -1191,6 +1192,13 @@ func (bot *CQBot) makeImageOrVideoElem(d map[string]string, video bool, sourceTy } return &LocalImageElement{Stream: bytes.NewReader(b), URL: f}, nil } + if !video && strings.HasPrefix(f, "base16384") { + b, err := b14.UTF82UTF16BE(utils.S2B(strings.TrimPrefix(f, "base16384://"))) + if err != nil { + return nil, err + } + return &LocalImageElement{Stream: bytes.NewReader(b14.Decode(b)), URL: f}, nil + } rawPath := path.Join(global.ImagePath, f) if video { if strings.HasSuffix(f, ".video") { diff --git a/global/fs.go b/global/fs.go index 3c197712..ccfac88d 100644 --- a/global/fs.go +++ b/global/fs.go @@ -13,6 +13,7 @@ import ( "strings" "github.com/Mrs4s/MiraiGo/utils" + b14 "github.com/fumiama/go-base16384" log "github.com/sirupsen/logrus" "github.com/Mrs4s/go-cqhttp/internal/param" @@ -92,6 +93,12 @@ func FindFile(file, cache, p string) (data []byte, err error) { if err != nil { return nil, err } + case strings.HasPrefix(file, "base16384"): + data, err = b14.UTF82UTF16BE(utils.S2B(strings.TrimPrefix(file, "base16384://"))) + if err != nil { + return nil, err + } + data = b14.Decode(data) case strings.HasPrefix(file, "file"): var fu *url.URL fu, err = url.Parse(file) diff --git a/go.mod b/go.mod index c23a9481..a27206b3 100644 --- a/go.mod +++ b/go.mod @@ -7,13 +7,14 @@ require ( github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8 github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc + github.com/fumiama/go-base16384 v1.5.2 github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible github.com/mattn/go-colorable v0.1.12 github.com/pkg/errors v0.9.1 github.com/segmentio/asm v1.1.3 github.com/sirupsen/logrus v1.8.1 - github.com/stretchr/testify v1.7.0 + github.com/stretchr/testify v1.7.1 github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 github.com/tidwall/gjson v1.14.0 github.com/wdvxdr1123/go-silk v0.0.0-20210316130616-d47b553def60 @@ -48,7 +49,7 @@ require ( golang.org/x/net v0.0.0-20211123203042-d83791d6bcd9 // indirect golang.org/x/sync v0.0.0-20210220032951-036812b2e83c // indirect golang.org/x/sys v0.0.0-20220111092808-5a964db01320 // indirect - golang.org/x/text v0.3.6 // indirect + golang.org/x/text v0.3.7 // indirect modernc.org/libc v1.8.1 // indirect modernc.org/mathutil v1.2.2 // indirect modernc.org/memory v1.0.4 // indirect diff --git a/go.sum b/go.sum index 425fad23..5b57b6dd 100644 --- a/go.sum +++ b/go.sum @@ -14,6 +14,8 @@ github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSs github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= +github.com/fumiama/go-base16384 v1.5.2 h1:cbxXTcDH92PNgG7bEBwiCEoWb5O+nwZKxKOG94ilFo8= +github.com/fumiama/go-base16384 v1.5.2/go.mod h1:OEn+947GV5gsbTAnyuUW/SrfxJYUdYupSIQXOuGOcXM= github.com/fumiama/go-hide-param v0.1.4 h1:y7TRTzZMdCH9GOXnIzU3B+1BSkcmvejVGmGsz4t0DGU= github.com/fumiama/go-hide-param v0.1.4/go.mod h1:vJkQlJIEI56nIyp7tCQu1/2QOyKtZpudsnJkGk9U1aY= github.com/fumiama/imgsz v0.0.2 h1:fAkC0FnIscdKOXwAxlyw3EUba5NzxZdSxGaq3Uyfxak= @@ -85,8 +87,9 @@ github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+ github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.1 h1:5TQK59W5E3v0r2duFAb7P95B6hEeOyEnHRa8MjYSMTY= +github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7 h1:epCh84lMvA70Z7CTTCmYQn2CKbY8j86K7/FAIr141uY= github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7/go.mod h1:q4W45IWZaF22tdD+VEXcAWRA037jwmWEB5VWYORlTpc= github.com/tidwall/gjson v1.14.0 h1:6aeJ0bzojgWLa82gDQHcx3S0Lr/O51I9bJ5nv6JFx5w= @@ -151,8 +154,8 @@ golang.org/x/text v0.3.0/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.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M= -golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk= +golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= golang.org/x/time v0.0.0-20211116232009-f0f3c7e86c11 h1:GZokNIeuVkl3aZHJchRrr13WCsols02MLUcz1U9is6M= golang.org/x/time v0.0.0-20211116232009-f0f3c7e86c11/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= From df3168ffd3df488d16872c3ca110517213f58e2b Mon Sep 17 00:00:00 2001 From: RTAkland <79452994+MarkusJoe@users.noreply.github.com> Date: Wed, 18 May 2022 22:05:02 +0800 Subject: [PATCH 70/93] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E4=BA=86=E9=94=99?= =?UTF-8?q?=E5=88=AB=E5=AD=97=20(#1471)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 第346行的文字: `线` => `限` --- server/http.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/http.go b/server/http.go index 7d696c52..6971f05c 100644 --- a/server/http.go +++ b/server/http.go @@ -343,7 +343,7 @@ func (c *HTTPClient) onBotPushEvent(e *coolq.Event) { if i < c.MaxRetries { log.Warnf("上报 Event 数据到 %v 失败: %v 将进行第 %d 次重试", c.addr, err, i+1) } else { - log.Warnf("上报 Event 数据 %s 到 %v 失败: %v 停止上报:已达重试上线", e.JSONBytes(), c.addr, err) + log.Warnf("上报 Event 数据 %s 到 %v 失败: %v 停止上报:已达重试上限", e.JSONBytes(), c.addr, err) return } time.Sleep(time.Millisecond * time.Duration(c.RetriesInterval)) From c141501ae5a14bd600c70d6c86ffc9760dcd8dc5 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 23 May 2022 11:13:44 +0800 Subject: [PATCH 71/93] all: update MiraiGo and some minor changes --- cmd/gocq/main.go | 1 + coolq/api.go | 18 ++++++++---------- coolq/bot.go | 2 +- go.mod | 2 +- server/http.go | 6 +++--- 5 files changed, 14 insertions(+), 15 deletions(-) diff --git a/cmd/gocq/main.go b/cmd/gocq/main.go index c6200803..1cb85cae 100644 --- a/cmd/gocq/main.go +++ b/cmd/gocq/main.go @@ -365,6 +365,7 @@ func PasswordHashDecrypt(encryptedPasswordHash string, key []byte) ([]byte, erro func newClient() *client.QQClient { c := client.NewClientEmpty() + c.UseFragmentMessage = base.ForceFragmented c.OnServerUpdated(func(bot *client.QQClient, e *client.ServerUpdatedEvent) bool { if !base.UseSSOAddress { log.Infof("收到服务器地址更新通知, 根据配置文件已忽略.") diff --git a/coolq/api.go b/coolq/api.go index 44a52e87..ece70765 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1470,18 +1470,18 @@ func (bot *CQBot) CQDownloadFile(url string, headers gjson.Result, threadCount i h := map[string]string{} if headers.IsArray() { for _, sub := range headers.Array() { - str := strings.SplitN(sub.String(), "=", 2) - if len(str) == 2 { - h[str[0]] = str[1] + first, second, ok := strings.Cut(sub.String(), "=") + if ok { + h[first] = second } } } if headers.Type == gjson.String { lines := strings.Split(headers.String(), "\r\n") for _, sub := range lines { - str := strings.SplitN(sub, "=", 2) - if len(str) == 2 { - h[str[0]] = str[1] + first, second, ok := strings.Cut(sub, "=") + if ok { + h[first] = second } } } @@ -1772,12 +1772,10 @@ func (bot *CQBot) CQSetGroupAnonymousBan(groupID int64, flag string, duration in return Failed(100, "INVALID_FLAG", "无效的flag") } if g := bot.Client.FindGroup(groupID); g != nil { - s := strings.SplitN(flag, "|", 2) - if len(s) != 2 { + id, nick, ok := strings.Cut(flag, "|") + if !ok { return Failed(100, "INVALID_FLAG", "无效的flag") } - id := s[0] - nick := s[1] if err := g.MuteAnonymous(id, nick, duration); err != nil { log.Warnf("anonymous ban error: %v", err) return Failed(100, "CALL_API_ERROR", err.Error()) diff --git a/coolq/bot.go b/coolq/bot.go index 00ec19cc..aea4845b 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -289,7 +289,7 @@ func (bot *CQBot) SendGroupMessage(groupID int64, m *message.SendingMessage) int } m.Elements = newElem bot.checkMedia(newElem, groupID) - ret := bot.Client.SendGroupMessage(groupID, m, base.ForceFragmented) + ret := bot.Client.SendGroupMessage(groupID, m) if ret == nil || ret.Id == -1 { log.Warnf("群消息发送失败: 账号可能被风控.") return -1 diff --git a/go.mod b/go.mod index c23a9481..58c17493 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8 + github.com/Mrs4s/MiraiGo v0.0.0-20220523030651-b28ec81f546e github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 diff --git a/server/http.go b/server/http.go index a4710115..710610de 100644 --- a/server/http.go +++ b/server/http.go @@ -212,9 +212,9 @@ func checkAuth(req *http.Request, token string) int { if auth == "" { auth = req.URL.Query().Get("access_token") } else { - authN := strings.SplitN(auth, " ", 2) - if len(authN) == 2 { - auth = authN[1] + _, after, ok := strings.Cut(auth, " ") + if ok { + auth = after } } From cfa35b6b0a3441786e967b58db0db4b6a66184a5 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Mon, 23 May 2022 11:15:51 +0800 Subject: [PATCH 72/93] dep: update go.sum --- go.sum | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/go.sum b/go.sum index 425fad23..d1ce9531 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8 h1:qkv7t94MNxwObbl1flZEZD5O0E8+R42XiZxOrppQNXc= -github.com/Mrs4s/MiraiGo v0.0.0-20220405134734-9cb9e80d99d8/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= +github.com/Mrs4s/MiraiGo v0.0.0-20220523030651-b28ec81f546e h1:OJu+7G+U9dRjE0VDvZI0YVbbPRspuOeOmUiYR9jOo5A= +github.com/Mrs4s/MiraiGo v0.0.0-20220523030651-b28ec81f546e/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= From 111a5506b9de0a1b7fbb28ee812133ae868cf200 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Tue, 24 May 2022 15:07:24 +0800 Subject: [PATCH 73/93] dep: update MiraiGo --- coolq/api.go | 2 -- coolq/converter.go | 2 +- go.mod | 6 +++--- go.sum | 12 ++++++------ 4 files changed, 10 insertions(+), 12 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index ece70765..23b3285d 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -407,7 +407,6 @@ func (bot *CQBot) CQGetGroupList(noCache bool) global.MSG { gs = append(gs, global.MSG{ "group_id": g.Code, "group_name": g.Name, - "group_memo": g.Memo, "group_create_time": g.GroupCreateTime, "group_level": g.GroupLevel, "max_member_count": g.MaxMemberCount, @@ -449,7 +448,6 @@ func (bot *CQBot) CQGetGroupInfo(groupID int64, noCache bool) global.MSG { return OK(global.MSG{ "group_id": group.Code, "group_name": group.Name, - "group_memo": group.Memo, "group_create_time": group.GroupCreateTime, "group_level": group.GroupLevel, "max_member_count": group.MaxMemberCount, diff --git a/coolq/converter.go b/coolq/converter.go index fbe3d4c5..43be08ee 100644 --- a/coolq/converter.go +++ b/coolq/converter.go @@ -41,7 +41,7 @@ func convertGroupMemberInfo(groupID int64, m *client.GroupMemberInfo) global.MSG "role": role, "unfriendly": false, "title": m.SpecialTitle, - "title_expire_time": m.SpecialTitleExpireTime, + "title_expire_time": 0, "card_changeable": false, } } diff --git a/go.mod b/go.mod index 58c17493..5b70bf7b 100644 --- a/go.mod +++ b/go.mod @@ -4,8 +4,8 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220523030651-b28ec81f546e - github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c + github.com/Mrs4s/MiraiGo v0.0.0-20220524053130-007f228e1092 + github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible @@ -25,7 +25,7 @@ require ( ) require ( - github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 // indirect + github.com/RomiChan/protobuf v0.1.1-0.20220524030518-4f349493f9da // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect diff --git a/go.sum b/go.sum index d1ce9531..1be6fb9b 100644 --- a/go.sum +++ b/go.sum @@ -1,11 +1,11 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220523030651-b28ec81f546e h1:OJu+7G+U9dRjE0VDvZI0YVbbPRspuOeOmUiYR9jOo5A= -github.com/Mrs4s/MiraiGo v0.0.0-20220523030651-b28ec81f546e/go.mod h1:APw03y3A3Qp5In9gI/S9m7DBJkWsd6FQMV+fB636bmU= -github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896 h1:UFAqSbH6VqW5mEzQV2HVB7+p3k9JfTbidWJ/9F15yz0= -github.com/RomiChan/protobuf v0.0.0-20220318113238-d8a99598f896/go.mod h1:CKKOWC7mBxd36zxsCB1V8DTrwlTNRQvkSVbYqyUiGEE= -github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c h1:zHWyqx7A71A/+mlzthPVcVrNGuTPyTpCW3meUPtaULU= -github.com/RomiChan/syncx v0.0.0-20220320130821-c88644afda9c/go.mod h1:KqZzu7slNKROh3TSYEH/IUMG6f4M+1qubZ5e52QypsE= +github.com/Mrs4s/MiraiGo v0.0.0-20220524053130-007f228e1092 h1:8TDeBGcywkNWXAmAVVL7u3xIXdlSD0IfXCs/8qf2G0I= +github.com/Mrs4s/MiraiGo v0.0.0-20220524053130-007f228e1092/go.mod h1:7jCgifOheeioTGhQnNUNlinEx7XfBszCEueyZCkTc2A= +github.com/RomiChan/protobuf v0.1.1-0.20220524030518-4f349493f9da h1:T+Sc+QtOfpIRnfnOXaToyLvxmUmFwF2iaqxpJddI4Cc= +github.com/RomiChan/protobuf v0.1.1-0.20220524030518-4f349493f9da/go.mod h1:2Ie+hdBFQpQFDHfeklgxoFmQRCE7O+KwFpISeXq7OwA= +github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c h1:cNPOdTNiVwxLpROLjXCgbIPvdkE+BwvxDvgmdYmWx6Q= +github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c/go.mod h1:KqZzu7slNKROh3TSYEH/IUMG6f4M+1qubZ5e52QypsE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc/go.mod h1:OMmITAib6POA37xCichWM0aRnoVpSMZO1rB/G01wrr0= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= From 810c781c25aed4e7de2361307994be1c99bb8555 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 25 May 2022 14:19:59 +0800 Subject: [PATCH 74/93] server: simplify long poll implementation --- server/middlewares.go | 34 +++++++++++++++++++--------------- 1 file changed, 19 insertions(+), 15 deletions(-) diff --git a/server/middlewares.go b/server/middlewares.go index d7835a42..301efbd2 100644 --- a/server/middlewares.go +++ b/server/middlewares.go @@ -50,33 +50,37 @@ func longPolling(bot *coolq.CQBot, maxSize int) api.Handler { return nil } var ( - once sync.Once - ch = make(chan []interface{}, 1) + ch = make(chan []interface{}) timeout = time.Duration(p.Get("timeout").Int()) * time.Second ) - defer close(ch) go func() { mutex.Lock() defer mutex.Unlock() - if queue.Len() == 0 { + for queue.Len() == 0 { cond.Wait() } - once.Do(func() { - limit := int(p.Get("limit").Int()) - if limit <= 0 || queue.Len() < limit { - limit = queue.Len() - } - ret := make([]interface{}, limit) - for i := 0; i < limit; i++ { - ret[i] = queue.Remove(queue.Front()) + limit := int(p.Get("limit").Int()) + if limit <= 0 || queue.Len() < limit { + limit = queue.Len() + } + ret := make([]interface{}, limit) + elem := queue.Front() + for i := 0; i < limit; i++ { + ret[i] = elem.Value + elem = elem.Next() + } + select { + case ch <- ret: + for i := 0; i < limit; i++ { // remove sent msg + queue.Remove(queue.Front()) } - ch <- ret - }) + default: + // don't block if parent already return due to timeout + } }() if timeout != 0 { select { case <-time.After(timeout): - once.Do(func() {}) return coolq.OK([]interface{}{}) case ret := <-ch: return coolq.OK(ret) From 296668441f3eeaa084164a6eb130c8a7bcfa6ea3 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Wed, 25 May 2022 15:24:48 +0800 Subject: [PATCH 75/93] coolq: unify converting IMessage to string&array message --- coolq/api.go | 6 +- coolq/bot.go | 4 +- coolq/converter.go | 12 +- coolq/cqcode.go | 322 +++++++++++++++------------------------- coolq/cqcode/element.go | 51 +++++++ coolq/event.go | 14 +- 6 files changed, 194 insertions(+), 215 deletions(-) create mode 100644 coolq/cqcode/element.go diff --git a/coolq/api.go b/coolq/api.go index 23b3285d..190484d6 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1577,7 +1577,7 @@ func (bot *CQBot) CQGetMessage(messageID int32) global.MSG { // @route(get_guild_msg) func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { source, seq := decodeGuildMessageID(messageID) - if source == nil { + if source.SourceType == 0 { log.Warnf("获取消息时出现错误: 无效消息ID") return Failed(100, "INVALID_MESSAGE_ID", "无效消息ID") } @@ -1613,7 +1613,7 @@ func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { "tiny_id": fU64(pull[0].Sender.TinyId), "nickname": pull[0].Sender.Nickname, } - m["message"] = ToFormattedMessage(pull[0].Elements, *source, false) + m["message"] = ToFormattedMessage(pull[0].Elements, source, false) m["reactions"] = convertReactions(pull[0].Reactions) bot.InsertGuildChannelMessage(pull[0]) } else { @@ -1628,7 +1628,7 @@ func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { "tiny_id": fU64(channelMsgByDB.Attribute.SenderTinyID), "nickname": channelMsgByDB.Attribute.SenderName, } - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(channelMsgByDB.Content, message.SourceGuildChannel), *source) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(channelMsgByDB.Content, message.SourceGuildChannel), source, false) } case message.SourceGuildDirect: // todo(mrs4s): 支持 direct 消息 diff --git a/coolq/bot.go b/coolq/bot.go index aea4845b..e6507cd5 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -630,13 +630,13 @@ func encodeGuildMessageID(primaryID, subID, seq uint64, source message.SourceTyp })) } -func decodeGuildMessageID(id string) (source *message.Source, seq uint64) { +func decodeGuildMessageID(id string) (source message.Source, seq uint64) { b, _ := base64.StdEncoding.DecodeString(id) if len(b) < 25 { return } r := binary.NewReader(b) - source = &message.Source{ + source = message.Source{ SourceType: message.SourceType(r.ReadByte()), PrimaryID: r.ReadInt64(), SecondaryID: r.ReadInt64(), diff --git a/coolq/converter.go b/coolq/converter.go index 43be08ee..65f26c4f 100644 --- a/coolq/converter.go +++ b/coolq/converter.go @@ -2,6 +2,7 @@ package coolq import ( "strconv" + "strings" "github.com/Mrs4s/MiraiGo/topic" @@ -64,7 +65,7 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { SourceType: message.SourceGroup, PrimaryID: m.GroupCode, } - cqm := ToStringMessage(m.Elements, source, true) + cqm := toStringMessage(m.Elements, source, true) postType := "message" if m.Sender.Uin == bot.Client.Uin { postType = "message_sent" @@ -211,6 +212,15 @@ func convertReactions(reactions []*message.GuildMessageEmojiReaction) (r []globa return } +func toStringMessage(m []message.IMessageElement, source message.Source, raw bool) string { + elems := toElements(m, source, raw) + var sb strings.Builder + for _, elem := range elems { + sb.WriteString(elem.CQCode()) + } + return sb.String() +} + func fU64(v uint64) string { return strconv.FormatUint(v, 10) } diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 8ea7aac0..d97c63d8 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -92,9 +92,12 @@ func replyID(r *message.ReplyElement, source message.Source) int32 { return db.ToGlobalID(id, seq) } -// ToArrayMessage 将消息元素数组转为MSG数组以用于消息上报 -func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []global.MSG) { - r = make([]global.MSG, 0, len(e)) +// toElements 将消息元素数组转为MSG数组以用于消息上报 +func toElements(e []message.IMessageElement, source message.Source, raw bool) (r []cqcode.Element) { + type pair = cqcode.Pair // simplify code + type pairs = []pair + + r = make([]cqcode.Element, 0, len(e)) m := &message.SendingMessage{Elements: e} reply := m.FirstOrNil(func(e message.IMessageElement) bool { _, ok := e.(*message.ReplyElement) @@ -103,26 +106,24 @@ func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []glo if reply != nil && source.SourceType&(message.SourceGroup|message.SourcePrivate) != 0 { replyElem := reply.(*message.ReplyElement) id := replyID(replyElem, source) - if base.ExtraReplyData { - r = append(r, global.MSG{ - "type": "reply", - "data": map[string]string{ - "id": strconv.FormatInt(int64(id), 10), - "seq": strconv.FormatInt(int64(replyElem.ReplySeq), 10), - "qq": strconv.FormatInt(replyElem.Sender, 10), - "time": strconv.FormatInt(int64(replyElem.Time), 10), - "text": ToStringMessage(replyElem.Elements, source), - }, - }) - } else { - r = append(r, global.MSG{ - "type": "reply", - "data": map[string]string{"id": strconv.FormatInt(int64(id), 10)}, - }) + elem := cqcode.Element{ + Type: "reply", + Data: pairs{ + {"id", strconv.FormatInt(int64(id), 10)}, + }, } + if base.ExtraReplyData { + elem.Data = append(elem.Data, + pair{K: "seq", V: strconv.FormatInt(int64(replyElem.ReplySeq), 10)}, + pair{K: "qq", V: strconv.FormatInt(replyElem.Sender, 10)}, + pair{K: "time", V: strconv.FormatInt(int64(replyElem.Time), 10)}, + pair{K: "text", V: toStringMessage(replyElem.Elements, source, true)}, + ) + } + r = append(r, elem) } for i, elem := range e { - var m global.MSG + var m cqcode.Element switch o := elem.(type) { case *message.ReplyElement: if base.RemoveReplyAt && i+1 < len(e) { @@ -133,103 +134,143 @@ func ToArrayMessage(e []message.IMessageElement, source message.Source) (r []glo } continue case *message.TextElement: - m = global.MSG{ - "type": "text", - "data": map[string]string{"text": o.Content}, + m = cqcode.Element{ + Type: "text", + Data: pairs{ + {"text", o.Content}, + }, } case *message.LightAppElement: - m = global.MSG{ - "type": "json", - "data": map[string]string{"data": o.Content}, + m = cqcode.Element{ + Type: "json", + Data: pairs{ + {"data", o.Content}, + }, } case *message.AtElement: target := "all" if o.Target != 0 { target = strconv.FormatUint(uint64(o.Target), 10) } - m = global.MSG{ - "type": "at", - "data": map[string]string{"qq": target}, + m = cqcode.Element{ + Type: "at", + Data: pairs{ + {"qq", target}, + }, } case *message.RedBagElement: - m = global.MSG{ - "type": "redbag", - "data": map[string]string{"title": o.Title}, + m = cqcode.Element{ + Type: "redbag", + Data: pairs{ + {"title", o.Title}, + }, } case *message.ForwardElement: - m = global.MSG{ - "type": "forward", - "data": map[string]string{"id": o.ResId}, + m = cqcode.Element{ + Type: "forward", + Data: pairs{ + {"id", o.ResId}, + }, } case *message.FaceElement: - m = global.MSG{ - "type": "face", - "data": map[string]string{"id": strconv.FormatInt(int64(o.Index), 10)}, + m = cqcode.Element{ + Type: "face", + Data: pairs{ + {"id", strconv.FormatInt(int64(o.Index), 10)}, + }, } case *message.VoiceElement: - m = global.MSG{ - "type": "record", - "data": map[string]string{"file": o.Name, "url": o.Url}, + m = cqcode.Element{ + Type: "record", + Data: pairs{ + {"file", o.Name}, + {"url", o.Url}, + }, } case *message.ShortVideoElement: - m = global.MSG{ - "type": "video", - "data": map[string]string{"file": o.Name, "url": o.Url}, + m = cqcode.Element{ + Type: "video", + Data: pairs{ + {"file", o.Name}, + {"url", o.Url}, + }, } case *message.GroupImageElement: - data := map[string]string{"file": hex.EncodeToString(o.Md5) + ".image", "url": o.Url, "subType": strconv.FormatInt(int64(o.ImageBizType), 10)} + data := pairs{ + {"file", hex.EncodeToString(o.Md5) + ".image"}, + {"subType", strconv.FormatInt(int64(o.ImageBizType), 10)}, + } + if raw { + data = append(data, pair{K: "url", V: o.Url}) + } switch { case o.Flash: - data["type"] = "flash" + data = append(data, pair{K: "type", V: "flash"}) case o.EffectID != 0: - data["type"] = "show" - data["id"] = strconv.FormatInt(int64(o.EffectID), 10) + data = append(data, pair{K: "type", V: "show"}) + data = append(data, pair{K: "id", V: strconv.FormatInt(int64(o.EffectID), 10)}) } - m = global.MSG{ - "type": "image", - "data": data, + m = cqcode.Element{ + Type: "image", + Data: data, } case *message.GuildImageElement: - data := map[string]string{"file": hex.EncodeToString(o.Md5) + ".image", "url": o.Url} - m = global.MSG{ - "type": "image", - "data": data, + data := pairs{ + {"file", hex.EncodeToString(o.Md5) + ".image"}, + } + if raw { + data = append(data, pair{K: "url", V: o.Url}) + } + m = cqcode.Element{ + Type: "image", + Data: data, } case *message.FriendImageElement: - data := map[string]string{"file": hex.EncodeToString(o.Md5) + ".image", "url": o.Url} + data := pairs{ + {"file", hex.EncodeToString(o.Md5) + ".image"}, + } + if raw { + data = append(data, pair{K: "url", V: o.Url}) + } if o.Flash { - data["type"] = "flash" + data = append(data, pair{K: "type", V: "flash"}) } - m = global.MSG{ - "type": "image", - "data": data, + m = cqcode.Element{ + Type: "image", + Data: data, } case *message.DiceElement: - m = global.MSG{ - "type": "dice", - "data": map[string]string{"value": strconv.FormatInt(int64(o.Value), 10)}, + m = cqcode.Element{ + Type: "dice", + Data: pairs{ + {"value", strconv.FormatInt(int64(o.Value), 10)}, + }, } case *message.MarketFaceElement: - m = global.MSG{ - "type": "text", - "data": map[string]string{"text": o.Name}, + m = cqcode.Element{ + Type: "text", + Data: pairs{ + {"text", o.Name}, + }, } case *message.ServiceElement: - if isOk := strings.Contains(o.Content, " i+1 { - elem, ok := e[i+1].(*message.AtElement) - if ok && elem.Target == o.Sender { - e[i+1] = nil - } - } - case *message.TextElement: - sb.WriteString(cqcode.EscapeText(o.Content)) - case *message.AtElement: - if o.Target == 0 { - write("[CQ:at,qq=all]") - continue - } - write("[CQ:at,qq=%d]", uint64(o.Target)) - case *message.RedBagElement: - write("[CQ:redbag,title=%s]", o.Title) - case *message.ForwardElement: - write("[CQ:forward,id=%s]", o.ResId) - case *message.FaceElement: - write(`[CQ:face,id=%d]`, o.Index) - case *message.VoiceElement: - if ur { - write(`[CQ:record,file=%s]`, o.Name) - } else { - write(`[CQ:record,file=%s,url=%s]`, o.Name, cqcode.EscapeValue(o.Url)) - } - case *message.ShortVideoElement: - if ur { - write(`[CQ:video,file=%s]`, o.Name) - } else { - write(`[CQ:video,file=%s,url=%s]`, o.Name, cqcode.EscapeValue(o.Url)) - } - case *message.GroupImageElement: - var arg string - if o.Flash { - arg = ",type=flash" - } else if o.EffectID != 0 { - arg = ",type=show,id=" + strconv.FormatInt(int64(o.EffectID), 10) - } - arg += ",subType=" + strconv.FormatInt(int64(o.ImageBizType), 10) - if ur { - write("[CQ:image,file=%x.image%s]", o.Md5, arg) - } else { - write("[CQ:image,file=%x.image,url=%s%s]", o.Md5, cqcode.EscapeValue(o.Url), arg) - } - case *message.FriendImageElement: - var arg string - if o.Flash { - arg = ",type=flash" - } - if ur { - write("[CQ:image,file=%x.image%s]", o.Md5, arg) - } else { - write("[CQ:image,file=%x.image,url=%s%s]", cqcode.EscapeValue(o.Url), arg) - } - case *LocalImageElement: - var arg string - if o.Flash { - arg = ",type=flash" - } - data, err := os.ReadFile(o.File) - if err == nil { - m := md5.Sum(data) - if ur { - write("[CQ:image,file=%x.image%s]", m[:], arg) - } else { - write("[CQ:image,file=%x.image,url=%s%s]", m[:], cqcode.EscapeValue(o.URL), arg) - } - } - case *message.GuildImageElement: - write("[CQ:image,file=%x.image,url=%s]", o.Md5, cqcode.EscapeValue(o.Url)) - case *message.DiceElement: - write("[CQ:dice,value=%v]", o.Value) - case *message.MarketFaceElement: - sb.WriteString(o.Name) - case *message.ServiceElement: - if isOk := strings.Contains(o.Content, " Date: Wed, 25 May 2022 15:31:26 +0800 Subject: [PATCH 76/93] coolq: make linter happy --- coolq/cqcode.go | 2 ++ coolq/cqcode/element.go | 4 ++++ 2 files changed, 6 insertions(+) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index d97c63d8..8d9de1d1 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -93,6 +93,8 @@ func replyID(r *message.ReplyElement, source message.Source) int32 { } // toElements 将消息元素数组转为MSG数组以用于消息上报 +// +// nolint:govet func toElements(e []message.IMessageElement, source message.Source, raw bool) (r []cqcode.Element) { type pair = cqcode.Pair // simplify code type pairs = []pair diff --git a/coolq/cqcode/element.go b/coolq/cqcode/element.go index b7469f92..83559258 100644 --- a/coolq/cqcode/element.go +++ b/coolq/cqcode/element.go @@ -7,16 +7,19 @@ import ( "github.com/Mrs4s/go-cqhttp/global" ) +// Element single message type Element struct { Type string Data []Pair } +// Pair key value pair type Pair struct { K string V string } +// CQCode convert to cqcode func (e *Element) CQCode() string { if e.Type == "text" { return EscapeText(e.Data[0].V) // must be {"text": value} @@ -34,6 +37,7 @@ func (e *Element) CQCode() string { return sb.String() } +// MarshalJSON see encoding/json.Marshaler func (e *Element) MarshalJSON() ([]byte, error) { buf := global.NewBuffer() defer global.PutBuffer(buf) From 9e136b21fa2ecf9d7ef97bce38cca06d35e7f37e Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Thu, 26 May 2022 20:45:05 +0800 Subject: [PATCH 77/93] coolq: refactor event msg --- coolq/api.go | 4 +- coolq/bot.go | 42 +++-- coolq/converter.go | 16 +- coolq/event.go | 422 +++++++++++++++++------------------------- server/middlewares.go | 2 +- 5 files changed, 205 insertions(+), 281 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 190484d6..df7285ed 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1671,12 +1671,12 @@ func (bot *CQBot) CQGetGroupMessageHistory(groupID int64, seq int64) global.MSG log.Warnf("获取群历史消息失败: %v", err) return Failed(100, "MESSAGES_API_ERROR", err.Error()) } - ms := make([]global.MSG, 0, len(msg)) + ms := make([]*event, 0, len(msg)) for _, m := range msg { bot.checkMedia(m.Elements, groupID) id := bot.InsertGroupMessage(m) t := bot.formatGroupMessage(m) - t["message_id"] = id + t.Others["message_id"] = id ms = append(ms, t) } return OK(global.MSG{ diff --git a/coolq/bot.go b/coolq/bot.go index e6507cd5..7723ea1e 100644 --- a/coolq/bot.go +++ b/coolq/bot.go @@ -7,6 +7,7 @@ import ( "fmt" "os" "runtime/debug" + "strings" "sync" "time" @@ -38,9 +39,8 @@ type CQBot struct { // Event 事件 type Event struct { - RawMsg global.MSG - once sync.Once + Raw *event buffer *bytes.Buffer } @@ -48,7 +48,7 @@ func (e *Event) marshal() { if e.buffer == nil { e.buffer = global.NewBuffer() } - _ = json.NewEncoder(e.buffer).Encode(e.RawMsg) + _ = json.NewEncoder(e.buffer).Encode(e.Raw) } // JSONBytes return byes of json by lazy marshalling. @@ -110,13 +110,9 @@ func NewQQBot(cli *client.QQClient) *CQBot { t := time.NewTicker(base.HeartbeatInterval) for { <-t.C - bot.dispatchEventMessage(global.MSG{ - "time": time.Now().Unix(), - "self_id": bot.Client.Uin, - "post_type": "meta_event", - "meta_event_type": "heartbeat", - "status": bot.CQGetStatus()["data"], - "interval": base.HeartbeatInterval.Milliseconds(), + bot.dispatchEvent("meta_event/heartbeat", global.MSG{ + "status": bot.CQGetStatus()["data"], + "interval": base.HeartbeatInterval.Milliseconds(), }) } }() @@ -569,11 +565,31 @@ func (bot *CQBot) InsertGuildChannelMessage(m *message.GuildChannelMessage) stri return msg.ID } -func (bot *CQBot) dispatchEventMessage(m global.MSG) { +func (bot *CQBot) event(typ string, others global.MSG) *event { + ev := new(event) + post, detail, ok := strings.Cut(typ, "/") + ev.PostType = post + ev.DetailType = detail + if ok { + detail, sub, _ := strings.Cut(detail, "/") + ev.DetailType = detail + ev.SubType = sub + } + ev.Time = time.Now().Unix() + ev.SelfID = bot.Client.Uin + ev.Others = others + return ev +} + +func (bot *CQBot) dispatchEvent(typ string, others global.MSG) { + bot.dispatch(bot.event(typ, others)) +} + +func (bot *CQBot) dispatch(ev *event) { bot.lock.RLock() defer bot.lock.RUnlock() - event := &Event{RawMsg: m} + event := &Event{Raw: ev} wg := sync.WaitGroup{} wg.Add(len(bot.events)) for _, f := range bot.events { @@ -581,7 +597,7 @@ func (bot *CQBot) dispatchEventMessage(m global.MSG) { defer func() { wg.Done() if pan := recover(); pan != nil { - log.Warnf("处理事件 %v 时出现错误: %v \n%s", m, pan, debug.Stack()) + log.Warnf("处理事件 %v 时出现错误: %v \n%s", event.JSONString(), pan, debug.Stack()) } }() diff --git a/coolq/converter.go b/coolq/converter.go index 65f26c4f..2116c7ac 100644 --- a/coolq/converter.go +++ b/coolq/converter.go @@ -60,15 +60,15 @@ func convertGuildMemberInfo(m []*client.GuildMemberInfo) (r []global.MSG) { return } -func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { +func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) *event { source := message.Source{ SourceType: message.SourceGroup, PrimaryID: m.GroupCode, } cqm := toStringMessage(m.Elements, source, true) - postType := "message" + typ := "message/group/normal" if m.Sender.Uin == bot.Client.Uin { - postType = "message_sent" + typ = "message_sent/group/normal" } gm := global.MSG{ "anonymous": nil, @@ -77,9 +77,7 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { "message": ToFormattedMessage(m.Elements, source, false), "message_type": "group", "message_seq": m.Id, - "post_type": postType, "raw_message": cqm, - "self_id": bot.Client.Uin, "sender": global.MSG{ "age": 0, "area": "", @@ -87,9 +85,7 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { "sex": "unknown", "user_id": m.Sender.Uin, }, - "sub_type": "normal", - "time": m.Time, - "user_id": m.Sender.Uin, + "user_id": m.Sender.Uin, } if m.Sender.IsAnonymous() { gm["anonymous"] = global.MSG{ @@ -128,7 +124,9 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) global.MSG { ms["card"] = mem.CardName ms["title"] = mem.SpecialTitle } - return gm + ev := bot.event(typ, gm) + ev.Time = int64(m.Time) + return ev } func convertChannelInfo(c *client.ChannelInfo) global.MSG { diff --git a/coolq/event.go b/coolq/event.go index 6f8d35f1..cef496c5 100644 --- a/coolq/event.go +++ b/coolq/event.go @@ -2,12 +2,12 @@ package coolq import ( "encoding/hex" + "encoding/json" "fmt" "os" "path" "strconv" "strings" - "time" "github.com/Mrs4s/MiraiGo/binary" "github.com/Mrs4s/MiraiGo/client" @@ -30,7 +30,45 @@ func ToFormattedMessage(e []message.IMessageElement, source message.Source, raw return } -func (bot *CQBot) privateMessageEvent(c *client.QQClient, m *message.PrivateMessage) { +type event struct { + PostType string + DetailType string + SubType string + Time int64 + SelfID int64 + Others global.MSG +} + +func (ev *event) MarshalJSON() ([]byte, error) { + buf := global.NewBuffer() + defer global.PutBuffer(buf) + + detail := "" + switch ev.PostType { + case "message", "message_sent": + detail = "message_type" + case "notice": + detail = "notice_type" + case "request": + detail = "request_type" + case "meta_event": + detail = "meta_event_type" + default: + panic("unknown post type: " + ev.PostType) + } + fmt.Fprintf(buf, `{"post_type":"%s","%s":"%s","time":%d,"self_id":%d`, ev.PostType, detail, ev.DetailType, ev.Time, ev.SelfID) + if ev.SubType != "" { + fmt.Fprintf(buf, `,"sub_type":"%s"`, ev.SubType) + } + for k, v := range ev.Others { + v, _ := json.Marshal(v) + fmt.Fprintf(buf, `,"%s":%s`, k, v) + } + buf.WriteByte('}') + return append([]byte(nil), buf.Bytes()...), nil +} + +func (bot *CQBot) privateMessageEvent(_ *client.QQClient, m *message.PrivateMessage) { bot.checkMedia(m.Elements, m.Sender.Uin) source := message.Source{ SourceType: message.SourcePrivate, @@ -39,23 +77,17 @@ func (bot *CQBot) privateMessageEvent(c *client.QQClient, m *message.PrivateMess cqm := toStringMessage(m.Elements, source, true) id := bot.InsertPrivateMessage(m) log.Infof("收到好友 %v(%v) 的消息: %v (%v)", m.Sender.DisplayName(), m.Sender.Uin, cqm, id) + typ := "message/private/friend" + if m.Sender.Uin == bot.Client.Uin { + typ = "message_sent/private/friend" + } fm := global.MSG{ - "post_type": func() string { - if m.Sender.Uin == bot.Client.Uin { - return "message_sent" - } - return "message" - }(), - "message_type": "private", - "sub_type": "friend", - "message_id": id, - "user_id": m.Sender.Uin, - "target_id": m.Target, - "message": ToFormattedMessage(m.Elements, source, false), - "raw_message": cqm, - "font": 0, - "self_id": c.Uin, - "time": time.Now().Unix(), + "message_id": id, + "user_id": m.Sender.Uin, + "target_id": m.Target, + "message": ToFormattedMessage(m.Elements, source, false), + "raw_message": cqm, + "font": 0, "sender": global.MSG{ "user_id": m.Sender.Uin, "nickname": m.Sender.Nickname, @@ -63,7 +95,7 @@ func (bot *CQBot) privateMessageEvent(c *client.QQClient, m *message.PrivateMess "age": 0, }, } - bot.dispatchEventMessage(fm) + bot.dispatchEvent(typ, fm) } func (bot *CQBot) groupMessageEvent(c *client.QQClient, m *message.GroupMessage) { @@ -71,11 +103,9 @@ func (bot *CQBot) groupMessageEvent(c *client.QQClient, m *message.GroupMessage) for _, elem := range m.Elements { if file, ok := elem.(*message.GroupFileElement); ok { log.Infof("群 %v(%v) 内 %v(%v) 上传了文件: %v", m.GroupName, m.GroupCode, m.Sender.DisplayName(), m.Sender.Uin, file.Name) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "group_upload", - "group_id": m.GroupCode, - "user_id": m.Sender.Uin, + bot.dispatchEvent("notice/group_upload", global.MSG{ + "group_id": m.GroupCode, + "user_id": m.Sender.Uin, "file": global.MSG{ "id": file.Path, "name": file.Name, @@ -83,8 +113,6 @@ func (bot *CQBot) groupMessageEvent(c *client.QQClient, m *message.GroupMessage) "busid": file.Busid, "url": c.GetGroupFileUrl(m.GroupCode, file.Path, file.Busid), }, - "self_id": c.Uin, - "time": time.Now().Unix(), }) return } @@ -100,8 +128,8 @@ func (bot *CQBot) groupMessageEvent(c *client.QQClient, m *message.GroupMessage) if gm == nil { return } - gm["message_id"] = id - bot.dispatchEventMessage(gm) + gm.Others["message_id"] = id + bot.dispatch(gm) } func (bot *CQBot) tempMessageEvent(c *client.QQClient, e *client.TempMessageEvent) { @@ -120,17 +148,12 @@ func (bot *CQBot) tempMessageEvent(c *client.QQClient, e *client.TempMessageEven // } log.Infof("收到来自群 %v(%v) 内 %v(%v) 的临时会话消息: %v", m.GroupName, m.GroupCode, m.Sender.DisplayName(), m.Sender.Uin, cqm) tm := global.MSG{ - "post_type": "message", - "message_type": "private", - "sub_type": "group", - "temp_source": e.Session.Source, - "message_id": id, - "user_id": m.Sender.Uin, - "message": ToFormattedMessage(m.Elements, source, false), - "raw_message": cqm, - "font": 0, - "self_id": c.Uin, - "time": time.Now().Unix(), + "temp_source": e.Session.Source, + "message_id": id, + "user_id": m.Sender.Uin, + "message": ToFormattedMessage(m.Elements, source, false), + "raw_message": cqm, + "font": 0, "sender": global.MSG{ "user_id": m.Sender.Uin, "group_id": m.GroupCode, @@ -139,7 +162,7 @@ func (bot *CQBot) tempMessageEvent(c *client.QQClient, e *client.TempMessageEven "age": 0, }, } - bot.dispatchEventMessage(tm) + bot.dispatchEvent("message/private/group", tm) } func (bot *CQBot) guildChannelMessageEvent(c *client.QQClient, m *message.GuildChannelMessage) { @@ -156,24 +179,21 @@ func (bot *CQBot) guildChannelMessageEvent(c *client.QQClient, m *message.GuildC } log.Infof("收到来自频道 %v(%v) 子频道 %v(%v) 内 %v(%v) 的消息: %v", guild.GuildName, guild.GuildId, channel.ChannelName, m.ChannelId, m.Sender.Nickname, m.Sender.TinyId, toStringMessage(m.Elements, source, true)) id := bot.InsertGuildChannelMessage(m) - bot.dispatchEventMessage(global.MSG{ - "post_type": "message", - "message_type": "guild", - "sub_type": "channel", + ev := bot.event("message/guild/channel", global.MSG{ "guild_id": fU64(m.GuildId), "channel_id": fU64(m.ChannelId), "message_id": id, "user_id": fU64(m.Sender.TinyId), "message": ToFormattedMessage(m.Elements, source, false), // todo: 增加对频道消息 Reply 的支持 - "self_id": bot.Client.Uin, "self_tiny_id": fU64(bot.Client.GuildService.TinyId), - "time": m.Time, "sender": global.MSG{ "user_id": m.Sender.TinyId, "tiny_id": fU64(m.Sender.TinyId), "nickname": m.Sender.Nickname, }, }) + ev.Time = m.Time + bot.dispatch(ev) } func (bot *CQBot) guildMessageReactionsUpdatedEvent(c *client.QQClient, e *client.GuildMessageReactionsUpdatedEvent) { @@ -199,16 +219,12 @@ func (bot *CQBot) guildMessageReactionsUpdatedEvent(c *client.QQClient, e *clien str += "无任何表情" } log.Infof(str) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "message_reactions_updated", + bot.dispatchEvent("notice/message_reactions_updated", global.MSG{ "guild_id": fU64(e.GuildId), "channel_id": fU64(e.ChannelId), "message_id": msgID, "operator_id": fU64(e.OperatorId), "current_reactions": currentReactions, - "time": time.Now().Unix(), - "self_id": bot.Client.Uin, "self_tiny_id": fU64(bot.Client.GuildService.TinyId), "user_id": e.OperatorId, }) @@ -230,15 +246,11 @@ func (bot *CQBot) guildChannelMessageRecalledEvent(c *client.QQClient, e *client } msgID := encodeGuildMessageID(e.GuildId, e.ChannelId, e.MessageId, message.SourceGuildChannel) log.Infof("用户 %v(%v) 撤回了频道 %v(%v) 子频道 %v(%v) 的消息 %v", operator.Nickname, operator.TinyId, guild.GuildName, guild.GuildId, channel.ChannelName, channel.ChannelId, msgID) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "guild_channel_recall", + bot.dispatchEvent("notice/guild_channel_recall", global.MSG{ "guild_id": fU64(e.GuildId), "channel_id": fU64(e.ChannelId), "operator_id": fU64(e.OperatorId), "message_id": msgID, - "time": time.Now().Unix(), - "self_id": bot.Client.Uin, "self_tiny_id": fU64(bot.Client.GuildService.TinyId), "user_id": e.OperatorId, }) @@ -250,14 +262,10 @@ func (bot *CQBot) guildChannelUpdatedEvent(c *client.QQClient, e *client.GuildCh return } log.Infof("频道 %v(%v) 子频道 %v(%v) 信息已更新", guild.GuildName, guild.GuildId, e.NewChannelInfo.ChannelName, e.NewChannelInfo.ChannelId) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "channel_updated", + bot.dispatchEvent("notice/channel_updated", global.MSG{ "guild_id": fU64(e.GuildId), "channel_id": fU64(e.ChannelId), "operator_id": fU64(e.OperatorId), - "time": time.Now().Unix(), - "self_id": bot.Client.Uin, "self_tiny_id": fU64(bot.Client.GuildService.TinyId), "user_id": e.OperatorId, "old_info": convertChannelInfo(e.OldChannelInfo), @@ -275,16 +283,12 @@ func (bot *CQBot) guildChannelCreatedEvent(c *client.QQClient, e *client.GuildCh member = &client.GuildUserProfile{Nickname: "未知"} } log.Infof("频道 %v(%v) 内用户 %v(%v) 创建了子频道 %v(%v)", guild.GuildName, guild.GuildId, member.Nickname, member.TinyId, e.ChannelInfo.ChannelName, e.ChannelInfo.ChannelId) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "channel_created", + bot.dispatchEvent("notice/channel_created", global.MSG{ "guild_id": fU64(e.GuildId), "channel_id": fU64(e.ChannelInfo.ChannelId), "operator_id": fU64(e.OperatorId), - "self_id": bot.Client.Uin, "self_tiny_id": fU64(bot.Client.GuildService.TinyId), "user_id": e.OperatorId, - "time": time.Now().Unix(), "channel_info": convertChannelInfo(e.ChannelInfo), }) } @@ -299,16 +303,12 @@ func (bot *CQBot) guildChannelDestroyedEvent(c *client.QQClient, e *client.Guild member = &client.GuildUserProfile{Nickname: "未知"} } log.Infof("频道 %v(%v) 内用户 %v(%v) 删除了子频道 %v(%v)", guild.GuildName, guild.GuildId, member.Nickname, member.TinyId, e.ChannelInfo.ChannelName, e.ChannelInfo.ChannelId) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "channel_destroyed", + bot.dispatchEvent("notice/channel_destroyed", global.MSG{ "guild_id": fU64(e.GuildId), "channel_id": fU64(e.ChannelInfo.ChannelId), "operator_id": fU64(e.OperatorId), - "self_id": bot.Client.Uin, "self_tiny_id": fU64(bot.Client.GuildService.TinyId), "user_id": e.OperatorId, - "time": time.Now().Unix(), "channel_info": convertChannelInfo(e.ChannelInfo), }) } @@ -332,22 +332,15 @@ func (bot *CQBot) groupMutedEvent(c *client.QQClient, e *client.GroupMuteEvent) formatGroupName(g), formatMemberName(g.FindMember(e.TargetUin)), formatMemberName(g.FindMember(e.OperatorUin))) } } - - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", + typ := "notice/group_ban/ban" + if e.Time == 0 { + typ = "notice/group_ban/lift_ban" + } + bot.dispatchEvent(typ, global.MSG{ "duration": e.Time, "group_id": e.GroupCode, - "notice_type": "group_ban", "operator_id": e.OperatorUin, - "self_id": c.Uin, "user_id": e.TargetUin, - "time": time.Now().Unix(), - "sub_type": func() string { - if e.Time == 0 { - return "lift_ban" - } - return "ban" - }(), }) } @@ -356,16 +349,15 @@ func (bot *CQBot) groupRecallEvent(c *client.QQClient, e *client.GroupMessageRec gid := db.ToGlobalID(e.GroupCode, e.MessageId) log.Infof("群 %v 内 %v 撤回了 %v 的消息: %v.", formatGroupName(g), formatMemberName(g.FindMember(e.OperatorUin)), formatMemberName(g.FindMember(e.AuthorUin)), gid) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", + + ev := bot.event("notice/group_recall", global.MSG{ "group_id": e.GroupCode, - "notice_type": "group_recall", - "self_id": c.Uin, "user_id": e.AuthorUin, "operator_id": e.OperatorUin, - "time": e.Time, "message_id": gid, }) + ev.Time = int64(e.Time) + bot.dispatch(ev) } func (bot *CQBot) groupNotifyEvent(c *client.QQClient, e client.INotifyEvent) { @@ -375,42 +367,27 @@ func (bot *CQBot) groupNotifyEvent(c *client.QQClient, e client.INotifyEvent) { sender := group.FindMember(notify.Sender) receiver := group.FindMember(notify.Receiver) log.Infof("群 %v 内 %v 戳了戳 %v", formatGroupName(group), formatMemberName(sender), formatMemberName(receiver)) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "group_id": group.Code, - "notice_type": "notify", - "sub_type": "poke", - "self_id": c.Uin, - "user_id": notify.Sender, - "sender_id": notify.Sender, - "target_id": notify.Receiver, - "time": time.Now().Unix(), + bot.dispatchEvent("notice/notify/poke", global.MSG{ + "group_id": group.Code, + "user_id": notify.Sender, + "sender_id": notify.Sender, + "target_id": notify.Receiver, }) case *client.GroupRedBagLuckyKingNotifyEvent: sender := group.FindMember(notify.Sender) luckyKing := group.FindMember(notify.LuckyKing) log.Infof("群 %v 内 %v 的红包被抢完, %v 是运气王", formatGroupName(group), formatMemberName(sender), formatMemberName(luckyKing)) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "group_id": group.Code, - "notice_type": "notify", - "sub_type": "lucky_king", - "self_id": c.Uin, - "user_id": notify.Sender, - "sender_id": notify.Sender, - "target_id": notify.LuckyKing, - "time": time.Now().Unix(), + bot.dispatchEvent("notice/notify/lucky_king", global.MSG{ + "group_id": group.Code, + "user_id": notify.Sender, + "sender_id": notify.Sender, + "target_id": notify.LuckyKing, }) case *client.MemberHonorChangedNotifyEvent: log.Info(notify.Content()) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "group_id": group.Code, - "notice_type": "notify", - "sub_type": "honor", - "self_id": c.Uin, - "user_id": notify.Uin, - "time": time.Now().Unix(), + bot.dispatchEvent("notice/notify/honor", global.MSG{ + "group_id": group.Code, + "user_id": notify.Uin, "honor_type": func() string { switch notify.Honor { case client.Talkative: @@ -439,15 +416,10 @@ func (bot *CQBot) friendNotifyEvent(c *client.QQClient, e client.INotifyEvent) { } else { log.Infof("好友 %v 戳了戳你.", friend.Nickname) } - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "notify", - "sub_type": "poke", - "self_id": c.Uin, - "user_id": notify.Sender, - "sender_id": notify.Sender, - "target_id": notify.Receiver, - "time": time.Now().Unix(), + bot.dispatchEvent("notice/notify/poke", global.MSG{ + "user_id": notify.Sender, + "sender_id": notify.Sender, + "target_id": notify.Receiver, }) } } @@ -456,15 +428,10 @@ func (bot *CQBot) memberTitleUpdatedEvent(c *client.QQClient, e *client.MemberSp group := c.FindGroup(e.GroupCode) mem := group.FindMember(e.Uin) log.Infof("群 %v(%v) 内成员 %v(%v) 获得了新的头衔: %v", group.Name, group.Code, mem.DisplayName(), mem.Uin, e.NewTitle) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "notify", - "sub_type": "title", - "group_id": group.Code, - "self_id": c.Uin, - "user_id": e.Uin, - "time": time.Now().Unix(), - "title": e.NewTitle, + bot.dispatchEvent("notice/notify/title", global.MSG{ + "group_id": group.Code, + "user_id": e.Uin, + "title": e.NewTitle, }) } @@ -476,14 +443,12 @@ func (bot *CQBot) friendRecallEvent(c *client.QQClient, e *client.FriendMessageR } else { log.Infof("好友 %v 撤回了消息: %v", e.FriendUin, gid) } - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "friend_recall", - "self_id": c.Uin, - "user_id": e.FriendUin, - "time": e.Time, - "message_id": gid, + ev := bot.event("notice/friend_recall", global.MSG{ + "user_id": e.FriendUin, + "message_id": gid, }) + ev.Time = e.Time + bot.dispatch(ev) } func (bot *CQBot) offlineFileEvent(c *client.QQClient, e *client.OfflineFileEvent) { @@ -492,23 +457,19 @@ func (bot *CQBot) offlineFileEvent(c *client.QQClient, e *client.OfflineFileEven return } log.Infof("好友 %v(%v) 发送了离线文件 %v", f.Nickname, f.Uin, e.FileName) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "offline_file", - "user_id": e.Sender, + bot.dispatchEvent("notice/offline_file", global.MSG{ + "user_id": e.Sender, "file": global.MSG{ "name": e.FileName, "size": e.FileSize, "url": e.DownloadUrl, }, - "self_id": c.Uin, - "time": time.Now().Unix(), }) } func (bot *CQBot) joinGroupEvent(c *client.QQClient, group *client.GroupInfo) { log.Infof("Bot进入了群 %v.", formatGroupName(group)) - bot.dispatchEventMessage(bot.groupIncrease(group.Code, 0, c.Uin)) + bot.dispatch(bot.groupIncrease(group.Code, 0, c.Uin)) } func (bot *CQBot) leaveGroupEvent(c *client.QQClient, e *client.GroupLeaveEvent) { @@ -517,44 +478,33 @@ func (bot *CQBot) leaveGroupEvent(c *client.QQClient, e *client.GroupLeaveEvent) } else { log.Infof("Bot退出了群 %v.", formatGroupName(e.Group)) } - bot.dispatchEventMessage(bot.groupDecrease(e.Group.Code, c.Uin, e.Operator)) + bot.dispatch(bot.groupDecrease(e.Group.Code, c.Uin, e.Operator)) } func (bot *CQBot) memberPermissionChangedEvent(c *client.QQClient, e *client.MemberPermissionChangedEvent) { - st := func() string { - if e.NewPermission == client.Administrator { - return "set" - } - return "unset" - }() - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "group_admin", - "sub_type": st, - "group_id": e.Group.Code, - "user_id": e.Member.Uin, - "time": time.Now().Unix(), - "self_id": c.Uin, + st := "unset" + if e.NewPermission == client.Administrator { + st = "set" + } + bot.dispatchEvent("notice/group_admin/"+st, global.MSG{ + "group_id": e.Group.Code, + "user_id": e.Member.Uin, }) } func (bot *CQBot) memberCardUpdatedEvent(c *client.QQClient, e *client.MemberCardUpdatedEvent) { log.Infof("群 %v 的 %v 更新了名片 %v -> %v", formatGroupName(e.Group), formatMemberName(e.Member), e.OldCard, e.Member.CardName) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "group_card", - "group_id": e.Group.Code, - "user_id": e.Member.Uin, - "card_new": e.Member.CardName, - "card_old": e.OldCard, - "time": time.Now().Unix(), - "self_id": c.Uin, + bot.dispatchEvent("notice/group_card", global.MSG{ + "group_id": e.Group.Code, + "user_id": e.Member.Uin, + "card_new": e.Member.CardName, + "card_old": e.OldCard, }) } func (bot *CQBot) memberJoinEvent(_ *client.QQClient, e *client.MemberJoinGroupEvent) { log.Infof("新成员 %v 进入了群 %v.", formatMemberName(e.Member), formatGroupName(e.Group)) - bot.dispatchEventMessage(bot.groupIncrease(e.Group.Code, 0, e.Member.Uin)) + bot.dispatch(bot.groupIncrease(e.Group.Code, 0, e.Member.Uin)) } func (bot *CQBot) memberLeaveEvent(_ *client.QQClient, e *client.MemberLeaveGroupEvent) { @@ -563,65 +513,47 @@ func (bot *CQBot) memberLeaveEvent(_ *client.QQClient, e *client.MemberLeaveGrou } else { log.Infof("成员 %v 离开了群 %v.", formatMemberName(e.Member), formatGroupName(e.Group)) } - bot.dispatchEventMessage(bot.groupDecrease(e.Group.Code, e.Member.Uin, e.Operator)) + bot.dispatch(bot.groupDecrease(e.Group.Code, e.Member.Uin, e.Operator)) } func (bot *CQBot) friendRequestEvent(c *client.QQClient, e *client.NewFriendRequest) { log.Infof("收到来自 %v(%v) 的好友请求: %v", e.RequesterNick, e.RequesterUin, e.Message) flag := strconv.FormatInt(e.RequestId, 10) bot.friendReqCache.Store(flag, e) - bot.dispatchEventMessage(global.MSG{ - "post_type": "request", - "request_type": "friend", - "user_id": e.RequesterUin, - "comment": e.Message, - "flag": flag, - "time": time.Now().Unix(), - "self_id": c.Uin, + bot.dispatchEvent("request/friend", global.MSG{ + "user_id": e.RequesterUin, + "comment": e.Message, + "flag": flag, }) } func (bot *CQBot) friendAddedEvent(c *client.QQClient, e *client.NewFriendEvent) { log.Infof("添加了新好友: %v(%v)", e.Friend.Nickname, e.Friend.Uin) bot.tempSessionCache.Delete(e.Friend.Uin) - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "friend_add", - "self_id": c.Uin, - "user_id": e.Friend.Uin, - "time": time.Now().Unix(), + bot.dispatchEvent("notice/friend_add", global.MSG{ + "user_id": e.Friend.Uin, }) } func (bot *CQBot) groupInvitedEvent(c *client.QQClient, e *client.GroupInvitedRequest) { log.Infof("收到来自群 %v(%v) 内用户 %v(%v) 的加群邀请.", e.GroupName, e.GroupCode, e.InvitorNick, e.InvitorUin) flag := strconv.FormatInt(e.RequestId, 10) - bot.dispatchEventMessage(global.MSG{ - "post_type": "request", - "request_type": "group", - "sub_type": "invite", - "group_id": e.GroupCode, - "user_id": e.InvitorUin, - "comment": "", - "flag": flag, - "time": time.Now().Unix(), - "self_id": c.Uin, + bot.dispatchEvent("request/group/invite", global.MSG{ + "group_id": e.GroupCode, + "user_id": e.InvitorUin, + "comment": "", + "flag": flag, }) } func (bot *CQBot) groupJoinReqEvent(c *client.QQClient, e *client.UserJoinGroupRequest) { log.Infof("群 %v(%v) 收到来自用户 %v(%v) 的加群请求.", e.GroupName, e.GroupCode, e.RequesterNick, e.RequesterUin) flag := strconv.FormatInt(e.RequestId, 10) - bot.dispatchEventMessage(global.MSG{ - "post_type": "request", - "request_type": "group", - "sub_type": "add", - "group_id": e.GroupCode, - "user_id": e.RequesterUin, - "comment": e.Message, - "flag": flag, - "time": time.Now().Unix(), - "self_id": c.Uin, + bot.dispatchEvent("request/group/add", global.MSG{ + "group_id": e.GroupCode, + "user_id": e.RequesterUin, + "comment": e.Message, + "flag": flag, }) } @@ -631,17 +563,13 @@ func (bot *CQBot) otherClientStatusChangedEvent(c *client.QQClient, e *client.Ot } else { log.Infof("Bot 账号在客户端 %v (%v) 登出.", e.Client.DeviceName, e.Client.DeviceKind) } - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", - "notice_type": "client_status", - "online": e.Online, + bot.dispatchEvent("notice/client_status", global.MSG{ + "online": e.Online, "client": global.MSG{ "app_id": e.Client.AppId, "device_name": e.Client.DeviceName, "device_kind": e.Client.DeviceKind, }, - "self_id": c.Uin, - "time": time.Now().Unix(), }) } @@ -668,61 +596,43 @@ func (bot *CQBot) groupEssenceMsg(c *client.QQClient, e *client.GroupDigestEvent if e.OperatorUin == bot.Client.Uin { return } - bot.dispatchEventMessage(global.MSG{ - "post_type": "notice", + subtype := "delete" + if e.OperationType == 1 { + subtype = "add" + } + bot.dispatchEvent("notice/essence/"+subtype, global.MSG{ "group_id": e.GroupCode, - "notice_type": "essence", - "sub_type": func() string { - if e.OperationType == 1 { - return "add" - } - return "delete" - }(), - "self_id": c.Uin, "sender_id": e.SenderUin, "operator_id": e.OperatorUin, - "time": time.Now().Unix(), "message_id": gid, }) } -func (bot *CQBot) groupIncrease(groupCode, operatorUin, userUin int64) global.MSG { - return global.MSG{ - "post_type": "notice", - "notice_type": "group_increase", +func (bot *CQBot) groupIncrease(groupCode, operatorUin, userUin int64) *event { + return bot.event("notice/group_increase/approve", global.MSG{ "group_id": groupCode, "operator_id": operatorUin, - "self_id": bot.Client.Uin, - "sub_type": "approve", - "time": time.Now().Unix(), "user_id": userUin, - } + }) } -func (bot *CQBot) groupDecrease(groupCode, userUin int64, operator *client.GroupMemberInfo) global.MSG { - return global.MSG{ - "post_type": "notice", - "notice_type": "group_decrease", - "group_id": groupCode, - "operator_id": func() int64 { - if operator != nil { - return operator.Uin - } - return userUin - }(), - "self_id": bot.Client.Uin, - "sub_type": func() string { - if operator != nil { - if userUin == bot.Client.Uin { - return "kick_me" - } - return "kick" - } - return "leave" - }(), - "time": time.Now().Unix(), - "user_id": userUin, +func (bot *CQBot) groupDecrease(groupCode, userUin int64, operator *client.GroupMemberInfo) *event { + op := userUin + if operator != nil { + op = operator.Uin + } + subtype := "leave" + if operator != nil { + if userUin == bot.Client.Uin { + subtype = "kick_me" + } + subtype = "kick" } + return bot.event("notice/group_decrease/"+subtype, global.MSG{ + "group_id": groupCode, + "operator_id": op, + "user_id": userUin, + }) } func (bot *CQBot) checkMedia(e []message.IMessageElement, sourceID int64) { diff --git a/server/middlewares.go b/server/middlewares.go index 301efbd2..7230248d 100644 --- a/server/middlewares.go +++ b/server/middlewares.go @@ -39,7 +39,7 @@ func longPolling(bot *coolq.CQBot, maxSize int) api.Handler { bot.OnEventPush(func(event *coolq.Event) { mutex.Lock() defer mutex.Unlock() - queue.PushBack(event.RawMsg) + queue.PushBack(event.Raw) for maxSize != 0 && queue.Len() > maxSize { queue.Remove(queue.Front()) } From 5daea94157de3f5e8ead4fa7e85b60c74ffba542 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Thu, 26 May 2022 20:48:11 +0800 Subject: [PATCH 78/93] fix golangci-lint error --- coolq/event.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/coolq/event.go b/coolq/event.go index cef496c5..74642b16 100644 --- a/coolq/event.go +++ b/coolq/event.go @@ -625,8 +625,9 @@ func (bot *CQBot) groupDecrease(groupCode, userUin int64, operator *client.Group if operator != nil { if userUin == bot.Client.Uin { subtype = "kick_me" + } else { + subtype = "kick" } - subtype = "kick" } return bot.event("notice/group_decrease/"+subtype, global.MSG{ "group_id": groupCode, From d313effb7965ce1cc9fed1ea6b90d65e86e9db2b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=A7=8B=E8=91=89=E6=9D=8F?= Date: Fri, 27 May 2022 14:24:48 +0800 Subject: [PATCH 79/93] feat: send forward msg to private (#1513) * feature(forward_msg): support send forward msg to private Added two apis: send_forward_msg & send_private_forward_msg * typo: messages * fix: message source target id --- coolq/api.go | 53 +++++++++++++++++++++++++++++++++++++++++----- modules/api/api.go | 10 +++++++++ 2 files changed, 58 insertions(+), 5 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index df7285ed..8332ac91 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -684,6 +684,24 @@ func (bot *CQBot) CQSendMessage(groupID, userID int64, m gjson.Result, messageTy return global.MSG{} } +// CQSendForwardMessage 发送合并转发消息 +// +// @route(send_forward_msg) +// @rename(m->messages) +func (bot *CQBot) CQSendForwardMessage(groupID, userID int64, m gjson.Result, messageType string) global.MSG { + switch { + case messageType == "group": + return bot.CQSendGroupForwardMessage(groupID, m) + case messageType == "private": + fallthrough + case userID != 0: + return bot.CQSendPrivateForwardMessage(userID, m) + case groupID != 0: + return bot.CQSendGroupForwardMessage(groupID, m) + } + return global.MSG{} +} + // CQSendGroupMessage 发送群消息 // // https://git.io/Jtz1c @@ -785,9 +803,13 @@ func (bot *CQBot) CQSendGuildChannelMessage(guildID, channelID uint64, m gjson.R return OK(global.MSG{"message_id": mid}) } -func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.ForwardElement { +func (bot *CQBot) uploadForwardElement(m gjson.Result, target int64, sourceType message.SourceType) *message.ForwardElement { ts := time.Now().Add(-time.Minute * 5) - source := message.Source{SourceType: message.SourceGroup, PrimaryID: groupID} + groupID := target + source := message.Source{SourceType: sourceType, PrimaryID: target} + if sourceType == message.SourcePrivate { + groupID = 0 + } builder := bot.Client.NewForwardMessageBuilder(groupID) var convertMessage func(m gjson.Result) *message.ForwardMessage @@ -802,7 +824,7 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F w.do(func() { gm, err := bot.uploadLocalVideo(source, o) if err != nil { - log.Warnf(uploadFailedTemplate, "群", groupID, "视频", err) + log.Warnf(uploadFailedTemplate, "合并转发", target, "视频", err) } else { *p = gm } @@ -811,7 +833,7 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, groupID int64) *message.F w.do(func() { gm, err := bot.uploadLocalImage(source, o) if err != nil { - log.Warnf(uploadFailedTemplate, "群", groupID, "图片", err) + log.Warnf(uploadFailedTemplate, "合并转发", target, "图片", err) } else { *p = gm } @@ -913,7 +935,7 @@ func (bot *CQBot) CQSendGroupForwardMessage(groupID int64, m gjson.Result) globa return Failed(100) } - fe := bot.uploadForwardElement(m, groupID) + fe := bot.uploadForwardElement(m, groupID, message.SourceGroup) if fe == nil { return Failed(100, "EMPTY_NODES", "未找到任何可发送的合并转发信息") } @@ -927,6 +949,27 @@ func (bot *CQBot) CQSendGroupForwardMessage(groupID int64, m gjson.Result) globa }) } +// CQSendPrivateForwardMessage 扩展API-发送合并转发(好友) +// +// https://docs.go-cqhttp.org/api/#%E5%8F%91%E9%80%81%E5%90%88%E5%B9%B6%E8%BD%AC%E5%8F%91-%E7%BE%A4 +// @route(send_private_forward_msg) +// @rename(m->messages) +func (bot *CQBot) CQSendPrivateForwardMessage(userID int64, m gjson.Result) global.MSG { + if m.Type != gjson.JSON { + return Failed(100) + } + fe := bot.uploadForwardElement(m, userID, message.SourcePrivate) + if fe == nil { + return Failed(100, "EMPTY_NODES", "未找到任何可发送的合并转发信息") + } + mid := bot.SendPrivateMessage(userID, 0, &message.SendingMessage{Elements: []message.IMessageElement{fe}}) + if mid == -1 { + log.Warnf("合并转发(好友)消息发送失败: 账号可能被风控.") + return Failed(100, "SEND_MSG_API_ERROR", "请参考 go-cqhttp 端输出") + } + return OK(global.MSG{"message_id": mid}) +} + // CQSendPrivateMessage 发送私聊消息 // // https://git.io/Jtz1l diff --git a/modules/api/api.go b/modules/api/api.go index b57c2500..63d087e7 100644 --- a/modules/api/api.go +++ b/modules/api/api.go @@ -195,6 +195,12 @@ func (c *Caller) call(action string, p Getter) global.MSG { case "reload_event_filter": p0 := p.Get("file").String() return c.bot.CQReloadEventFilter(p0) + case "send_forward_msg": + p0 := p.Get("group_id").Int() + p1 := p.Get("user_id").Int() + p2 := p.Get("messages") + p3 := p.Get("message_type").String() + return c.bot.CQSendForwardMessage(p0, p1, p2, p3) case "send_group_forward_msg": p0 := p.Get("group_id").Int() p1 := p.Get("messages") @@ -217,6 +223,10 @@ func (c *Caller) call(action string, p Getter) global.MSG { p3 := p.Get("message_type").String() p4 := p.Get("auto_escape").Bool() return c.bot.CQSendMessage(p0, p1, p2, p3, p4) + case "send_private_forward_msg": + p0 := p.Get("user_id").Int() + p1 := p.Get("messages") + return c.bot.CQSendPrivateForwardMessage(p0, p1) case "send_private_msg": p0 := p.Get("user_id").Int() p1 := p.Get("group_id").Int() From c275806c62a4cde69d3af338a1e086a2eda04df0 Mon Sep 17 00:00:00 2001 From: synodriver Date: Fri, 27 May 2022 17:10:23 +0800 Subject: [PATCH 80/93] add group_id for get_forward_msg (#1510) --- coolq/api.go | 14 ++++++++++++-- modules/api/api.go | 3 +++ 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index 8332ac91..fd2566e3 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1572,8 +1572,9 @@ func (bot *CQBot) CQGetForwardMessage(resID string) global.MSG { "user_id": n.SenderId, "nickname": n.SenderName, }, - "time": n.Time, - "content": content, + "time": n.Time, + "content": content, + "group_id": n.GroupId, } } return r @@ -1973,6 +1974,15 @@ func (bot *CQBot) CQGetModelShow(model string) global.MSG { }) } +// CQSendGroupSign 群打卡 +// +// https://club.vip.qq.com/onlinestatus/set +// @route(send_group_sign) +func (bot *CQBot) CQSendGroupSign(groupID int64) global.MSG { + bot.Client.SendGroupSign(groupID) + return OK(nil) +} + // CQSetModelShow 设置在线机型 // // https://club.vip.qq.com/onlinestatus/set diff --git a/modules/api/api.go b/modules/api/api.go index 63d087e7..ae4e9287 100644 --- a/modules/api/api.go +++ b/modules/api/api.go @@ -210,6 +210,9 @@ func (c *Caller) call(action string, p Getter) global.MSG { p1 := p.Get("message") p2 := p.Get("auto_escape").Bool() return c.bot.CQSendGroupMessage(p0, p1, p2) + case "send_group_sign": + p0 := p.Get("group_id").Int() + return c.bot.CQSendGroupSign(p0) case "send_guild_channel_msg": p0 := p.Get("guild_id").Uint() p1 := p.Get("channel_id").Uint() From 43ea459365569968888bd1297f0d34116f9a7ae8 Mon Sep 17 00:00:00 2001 From: MingxuanGame Date: Sat, 28 May 2022 21:54:10 +0800 Subject: [PATCH 81/93] feat: supported finger-guessing message (#1519) --- coolq/cqcode.go | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 8d9de1d1..59c7d23e 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -248,6 +248,13 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r {"value", strconv.FormatInt(int64(o.Value), 10)}, }, } + case *message.FingerGuessingElement: + m = cqcode.Element{ + Type: "rps", + Data: pairs{ + {"value", strconv.FormatInt(int64(o.Value), 10)}, + }, + } case *message.MarketFaceElement: m = cqcode.Element{ Type: "text", @@ -371,6 +378,8 @@ func ToMessageContent(e []message.IMessageElement) (r []global.MSG) { } case *message.DiceElement: m = global.MSG{"type": "dice", "data": global.MSG{"value": o.Value}} + case *message.FingerGuessingElement: + m = global.MSG{"type": "rps", "data": global.MSG{"value": o.Value}} case *message.MarketFaceElement: m = global.MSG{"type": "text", "data": global.MSG{"text": o.Name}} case *message.ServiceElement: @@ -964,6 +973,13 @@ func (bot *CQBot) ToElement(t string, d map[string]string, sourceType message.So return nil, errors.New("invalid dice value " + value) } return message.NewDice(int32(i)), nil + case "rps": + value := d["value"] + i, _ := strconv.ParseInt(value, 10, 64) + if i < 0 || i > 2 { + return nil, errors.New("invalid finger-guessing value " + value) + } + return message.NewFingerGuessing(int32(i)), nil case "xml": resID := d["resid"] template := cqcode.EscapeValue(d["data"]) From 15602e1daa0d1cf97ac30ad6279375c87fecabdb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=BA=90=E6=96=87=E9=9B=A8?= <41315874+fumiama@users.noreply.github.com> Date: Mon, 30 May 2022 14:17:34 +0800 Subject: [PATCH 82/93] revert: re-include url in message (#1521) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * revert: re-include url in message * fix: wrong writer usage * fix: composite literal uses unkeyed fields * 优化buffer * fix: illegal use of non-zero Builder * fix: illegal use of non-zero Builder * fix: make lint happy * fix: replace io.Writer to *strings.Builder * fix: replace io.Writer to *strings.Builder --- coolq/api.go | 10 +++---- coolq/converter.go | 10 +++---- coolq/cqcode.go | 60 +++++++++++++++++++---------------------- coolq/cqcode/element.go | 48 ++++++++++++++++++++------------- coolq/event.go | 20 +++++++------- 5 files changed, 77 insertions(+), 71 deletions(-) diff --git a/coolq/api.go b/coolq/api.go index fd2566e3..7d99bf01 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -1561,7 +1561,7 @@ func (bot *CQBot) CQGetForwardMessage(resID string) global.MSG { r := make([]global.MSG, len(nodes)) for i, n := range nodes { bot.checkMedia(n.Message, 0) - content := ToFormattedMessage(n.Message, message.Source{SourceType: message.SourceGroup}, false) + content := ToFormattedMessage(n.Message, message.Source{SourceType: message.SourceGroup}) if len(n.Message) == 1 { if forward, ok := n.Message[0].(*message.ForwardMessage); ok { content = transformNodes(forward.Nodes) @@ -1610,9 +1610,9 @@ func (bot *CQBot) CQGetMessage(messageID int32) global.MSG { switch o := msg.(type) { case *db.StoredGroupMessage: m["group_id"] = o.GroupCode - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, message.SourceGroup), message.Source{SourceType: message.SourceGroup, PrimaryID: o.GroupCode}, false) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, message.SourceGroup), message.Source{SourceType: message.SourceGroup, PrimaryID: o.GroupCode}) case *db.StoredPrivateMessage: - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, message.SourcePrivate), message.Source{SourceType: message.SourcePrivate}, false) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(o.Content, message.SourcePrivate), message.Source{SourceType: message.SourcePrivate}) } return OK(m) } @@ -1657,7 +1657,7 @@ func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { "tiny_id": fU64(pull[0].Sender.TinyId), "nickname": pull[0].Sender.Nickname, } - m["message"] = ToFormattedMessage(pull[0].Elements, source, false) + m["message"] = ToFormattedMessage(pull[0].Elements, source) m["reactions"] = convertReactions(pull[0].Reactions) bot.InsertGuildChannelMessage(pull[0]) } else { @@ -1672,7 +1672,7 @@ func (bot *CQBot) CQGetGuildMessage(messageID string, noCache bool) global.MSG { "tiny_id": fU64(channelMsgByDB.Attribute.SenderTinyID), "nickname": channelMsgByDB.Attribute.SenderName, } - m["message"] = ToFormattedMessage(bot.ConvertContentMessage(channelMsgByDB.Content, message.SourceGuildChannel), source, false) + m["message"] = ToFormattedMessage(bot.ConvertContentMessage(channelMsgByDB.Content, message.SourceGuildChannel), source) } case message.SourceGuildDirect: // todo(mrs4s): 支持 direct 消息 diff --git a/coolq/converter.go b/coolq/converter.go index 2116c7ac..d185b64c 100644 --- a/coolq/converter.go +++ b/coolq/converter.go @@ -65,7 +65,7 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) *event { SourceType: message.SourceGroup, PrimaryID: m.GroupCode, } - cqm := toStringMessage(m.Elements, source, true) + cqm := toStringMessage(m.Elements, source) typ := "message/group/normal" if m.Sender.Uin == bot.Client.Uin { typ = "message_sent/group/normal" @@ -74,7 +74,7 @@ func (bot *CQBot) formatGroupMessage(m *message.GroupMessage) *event { "anonymous": nil, "font": 0, "group_id": m.GroupCode, - "message": ToFormattedMessage(m.Elements, source, false), + "message": ToFormattedMessage(m.Elements, source), "message_type": "group", "message_seq": m.Id, "raw_message": cqm, @@ -210,11 +210,11 @@ func convertReactions(reactions []*message.GuildMessageEmojiReaction) (r []globa return } -func toStringMessage(m []message.IMessageElement, source message.Source, raw bool) string { - elems := toElements(m, source, raw) +func toStringMessage(m []message.IMessageElement, source message.Source) string { + elems := toElements(m, source) var sb strings.Builder for _, elem := range elems { - sb.WriteString(elem.CQCode()) + elem.WriteCQCodeTo(&sb) } return sb.String() } diff --git a/coolq/cqcode.go b/coolq/cqcode.go index 59c7d23e..17b77778 100644 --- a/coolq/cqcode.go +++ b/coolq/cqcode.go @@ -95,7 +95,7 @@ func replyID(r *message.ReplyElement, source message.Source) int32 { // toElements 将消息元素数组转为MSG数组以用于消息上报 // // nolint:govet -func toElements(e []message.IMessageElement, source message.Source, raw bool) (r []cqcode.Element) { +func toElements(e []message.IMessageElement, source message.Source) (r []cqcode.Element) { type pair = cqcode.Pair // simplify code type pairs = []pair @@ -111,7 +111,7 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r elem := cqcode.Element{ Type: "reply", Data: pairs{ - {"id", strconv.FormatInt(int64(id), 10)}, + {K: "id", V: strconv.FormatInt(int64(id), 10)}, }, } if base.ExtraReplyData { @@ -119,7 +119,7 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r pair{K: "seq", V: strconv.FormatInt(int64(replyElem.ReplySeq), 10)}, pair{K: "qq", V: strconv.FormatInt(replyElem.Sender, 10)}, pair{K: "time", V: strconv.FormatInt(int64(replyElem.Time), 10)}, - pair{K: "text", V: toStringMessage(replyElem.Elements, source, true)}, + pair{K: "text", V: toStringMessage(replyElem.Elements, source)}, ) } r = append(r, elem) @@ -139,14 +139,14 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r m = cqcode.Element{ Type: "text", Data: pairs{ - {"text", o.Content}, + {K: "text", V: o.Content}, }, } case *message.LightAppElement: m = cqcode.Element{ Type: "json", Data: pairs{ - {"data", o.Content}, + {K: "data", V: o.Content}, }, } case *message.AtElement: @@ -157,53 +157,51 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r m = cqcode.Element{ Type: "at", Data: pairs{ - {"qq", target}, + {K: "qq", V: target}, }, } case *message.RedBagElement: m = cqcode.Element{ Type: "redbag", Data: pairs{ - {"title", o.Title}, + {K: "title", V: o.Title}, }, } case *message.ForwardElement: m = cqcode.Element{ Type: "forward", Data: pairs{ - {"id", o.ResId}, + {K: "id", V: o.ResId}, }, } case *message.FaceElement: m = cqcode.Element{ Type: "face", Data: pairs{ - {"id", strconv.FormatInt(int64(o.Index), 10)}, + {K: "id", V: strconv.FormatInt(int64(o.Index), 10)}, }, } case *message.VoiceElement: m = cqcode.Element{ Type: "record", Data: pairs{ - {"file", o.Name}, - {"url", o.Url}, + {K: "file", V: o.Name}, + {K: "url", V: o.Url}, }, } case *message.ShortVideoElement: m = cqcode.Element{ Type: "video", Data: pairs{ - {"file", o.Name}, - {"url", o.Url}, + {K: "file", V: o.Name}, + {K: "url", V: o.Url}, }, } case *message.GroupImageElement: data := pairs{ - {"file", hex.EncodeToString(o.Md5) + ".image"}, - {"subType", strconv.FormatInt(int64(o.ImageBizType), 10)}, - } - if raw { - data = append(data, pair{K: "url", V: o.Url}) + {K: "file", V: hex.EncodeToString(o.Md5) + ".image"}, + {K: "subType", V: strconv.FormatInt(int64(o.ImageBizType), 10)}, + {K: "url", V: o.Url}, } switch { case o.Flash: @@ -218,10 +216,8 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r } case *message.GuildImageElement: data := pairs{ - {"file", hex.EncodeToString(o.Md5) + ".image"}, - } - if raw { - data = append(data, pair{K: "url", V: o.Url}) + {K: "file", V: hex.EncodeToString(o.Md5) + ".image"}, + {K: "url", V: o.Url}, } m = cqcode.Element{ Type: "image", @@ -229,10 +225,8 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r } case *message.FriendImageElement: data := pairs{ - {"file", hex.EncodeToString(o.Md5) + ".image"}, - } - if raw { - data = append(data, pair{K: "url", V: o.Url}) + {K: "file", V: hex.EncodeToString(o.Md5) + ".image"}, + {K: "url", V: o.Url}, } if o.Flash { data = append(data, pair{K: "type", V: "flash"}) @@ -245,29 +239,29 @@ func toElements(e []message.IMessageElement, source message.Source, raw bool) (r m = cqcode.Element{ Type: "dice", Data: pairs{ - {"value", strconv.FormatInt(int64(o.Value), 10)}, + {K: "value", V: strconv.FormatInt(int64(o.Value), 10)}, }, } case *message.FingerGuessingElement: m = cqcode.Element{ Type: "rps", Data: pairs{ - {"value", strconv.FormatInt(int64(o.Value), 10)}, + {K: "value", V: strconv.FormatInt(int64(o.Value), 10)}, }, } case *message.MarketFaceElement: m = cqcode.Element{ Type: "text", Data: pairs{ - {"text", o.Name}, + {K: "text", V: o.Name}, }, } case *message.ServiceElement: m = cqcode.Element{ Type: "xml", Data: pairs{ - {"data", o.Content}, - {"resid", o.ResId}, + {K: "data", V: o.Content}, + {K: "resid", V: o.ResId}, }, } if !strings.Contains(o.Content, " Date: Mon, 30 May 2022 14:19:54 +0800 Subject: [PATCH 83/93] feat: use the same buffer pool as MiraiGo (#1297) --- global/buffer.go | 18 ++++-------------- 1 file changed, 4 insertions(+), 14 deletions(-) diff --git a/global/buffer.go b/global/buffer.go index 73079f32..e899dae3 100644 --- a/global/buffer.go +++ b/global/buffer.go @@ -2,26 +2,16 @@ package global import ( "bytes" - "sync" -) -var bufferPool = sync.Pool{ - New: func() interface{} { - return new(bytes.Buffer) - }, -} + "github.com/Mrs4s/MiraiGo/binary" // 和 MiraiGo 共用同一 buffer 池 +) // NewBuffer 从池中获取新 bytes.Buffer func NewBuffer() *bytes.Buffer { - return bufferPool.Get().(*bytes.Buffer) + return (*bytes.Buffer)(binary.SelectWriter()) } // PutBuffer 将 Buffer放入池中 func PutBuffer(buf *bytes.Buffer) { - // See https://golang.org/issue/23199 - const maxSize = 1 << 16 - if buf != nil && buf.Cap() < maxSize { // 对于大Buffer直接丢弃 - buf.Reset() - bufferPool.Put(buf) - } + binary.PutWriter((*binary.Writer)(buf)) } From cc3745130eff2549788218ea8d9e283a845b9ff6 Mon Sep 17 00:00:00 2001 From: Ink33 Date: Tue, 31 May 2022 14:53:34 +0800 Subject: [PATCH 84/93] chore: bump yaml.in/yaml.v3 v3.0.0 to v3.0.1 (#1523) Signed-off-by: Ink33 --- go.mod | 2 +- go.sum | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 5b70bf7b..6c061290 100644 --- a/go.mod +++ b/go.mod @@ -21,7 +21,7 @@ require ( golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3 golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 golang.org/x/time v0.0.0-20211116232009-f0f3c7e86c11 - gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b + gopkg.in/yaml.v3 v3.0.1 ) require ( diff --git a/go.sum b/go.sum index 1be6fb9b..225fc2df 100644 --- a/go.sum +++ b/go.sum @@ -176,8 +176,8 @@ gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU= gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo= -gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= modernc.org/libc v1.8.1 h1:y9oPIhwcaFXxX7kMp6Qb2ZLKzr0mDkikWN3CV5GS63o= modernc.org/libc v1.8.1/go.mod h1:U1eq8YWr/Kc1RWCMFUWEdkTg8OTcfLw2kY8EDwl039w= modernc.org/mathutil v1.1.1/go.mod h1:mZW8CKdRPY1v87qxC/wUdX5O1qDzXMP5TH3wjfpga6E= From 70d1bfe510f1c425a76f765e0c67a9920061f3f3 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 5 Jun 2022 16:54:52 +0800 Subject: [PATCH 85/93] dep: update dependency --- go.mod | 4 ++-- go.sum | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/go.mod b/go.mod index 6c061290..575c5395 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220524053130-007f228e1092 + github.com/Mrs4s/MiraiGo v0.0.0-20220605085305-ae33763fe10a github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-hide-param v0.1.4 @@ -25,7 +25,7 @@ require ( ) require ( - github.com/RomiChan/protobuf v0.1.1-0.20220524030518-4f349493f9da // indirect + github.com/RomiChan/protobuf v0.1.1-0.20220602121309-9e3b8cbefd7a // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/fumiama/imgsz v0.0.2 // indirect github.com/go-stack/stack v1.8.0 // indirect diff --git a/go.sum b/go.sum index 225fc2df..9674779d 100644 --- a/go.sum +++ b/go.sum @@ -1,9 +1,9 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220524053130-007f228e1092 h1:8TDeBGcywkNWXAmAVVL7u3xIXdlSD0IfXCs/8qf2G0I= -github.com/Mrs4s/MiraiGo v0.0.0-20220524053130-007f228e1092/go.mod h1:7jCgifOheeioTGhQnNUNlinEx7XfBszCEueyZCkTc2A= -github.com/RomiChan/protobuf v0.1.1-0.20220524030518-4f349493f9da h1:T+Sc+QtOfpIRnfnOXaToyLvxmUmFwF2iaqxpJddI4Cc= -github.com/RomiChan/protobuf v0.1.1-0.20220524030518-4f349493f9da/go.mod h1:2Ie+hdBFQpQFDHfeklgxoFmQRCE7O+KwFpISeXq7OwA= +github.com/Mrs4s/MiraiGo v0.0.0-20220605085305-ae33763fe10a h1:DVrEVvLNKb53wTTduRdC+hZ80S/5G9qFmKYmCmIMVws= +github.com/Mrs4s/MiraiGo v0.0.0-20220605085305-ae33763fe10a/go.mod h1:mZp8Lt7uqLCUwSLouB2yuiP467Cwl4mnG9IMAaXUKA0= +github.com/RomiChan/protobuf v0.1.1-0.20220602121309-9e3b8cbefd7a h1:WIfEWYj82oEuPtm5pqlyQmCJCoiw00C6ugZFqHA0cC8= +github.com/RomiChan/protobuf v0.1.1-0.20220602121309-9e3b8cbefd7a/go.mod h1:2Ie+hdBFQpQFDHfeklgxoFmQRCE7O+KwFpISeXq7OwA= github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c h1:cNPOdTNiVwxLpROLjXCgbIPvdkE+BwvxDvgmdYmWx6Q= github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c/go.mod h1:KqZzu7slNKROh3TSYEH/IUMG6f4M+1qubZ5e52QypsE= github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc h1:AAx50/fb/xS4lvsdQg+bFbGvqSDhyV1MF+p2PLCamZ0= From d25209c366a036befa01595e27384673898c0296 Mon Sep 17 00:00:00 2001 From: Mrs4s Date: Sun, 5 Jun 2022 17:35:37 +0800 Subject: [PATCH 86/93] fix #1520 --- coolq/api.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/coolq/api.go b/coolq/api.go index 7d99bf01..1eeb6be1 100644 --- a/coolq/api.go +++ b/coolq/api.go @@ -870,7 +870,7 @@ func (bot *CQBot) uploadForwardElement(m gjson.Result, target int64, sourceType if msgTime == 0 { msgTime = ts.Unix() } - name := e.Get("data.name").Str + name := e.Get("data.[name,nickname].0").Str c := e.Get("data.content") if c.IsArray() { nested := false From e4c73d59a5cba3d2c2fa80ff2602d95a5cc9e618 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 5 Jun 2022 19:04:39 +0800 Subject: [PATCH 87/93] fix #1527 --- server/http.go | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/server/http.go b/server/http.go index 710610de..3fd7c377 100644 --- a/server/http.go +++ b/server/http.go @@ -363,15 +363,16 @@ func (c *HTTPClient) onBotPushEvent(e *coolq.Event) { } req.Header = header res, err = c.client.Do(req) - if err != nil { - if i < c.MaxRetries { - log.Warnf("上报 Event 数据到 %v 失败: %v 将进行第 %d 次重试", c.addr, err, i+1) - } else { - log.Warnf("上报 Event 数据 %s 到 %v 失败: %v 停止上报:已达重试上限", e.JSONBytes(), c.addr, err) - return - } - time.Sleep(time.Millisecond * time.Duration(c.RetriesInterval)) + if err == nil { + break + } + if i < c.MaxRetries { + log.Warnf("上报 Event 数据到 %v 失败: %v 将进行第 %d 次重试", c.addr, err, i+1) + } else { + log.Warnf("上报 Event 数据 %s 到 %v 失败: %v 停止上报:已达重试上限", e.JSONBytes(), c.addr, err) + return } + time.Sleep(time.Millisecond * time.Duration(c.RetriesInterval)) } defer res.Body.Close() From 12391f8df386ab623e460b388cc6d2a9552682d4 Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 5 Jun 2022 21:34:48 +0800 Subject: [PATCH 88/93] ci: change release to draft --- .goreleaser.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.goreleaser.yml b/.goreleaser.yml index cd9d92c3..c3798865 100644 --- a/.goreleaser.yml +++ b/.goreleaser.yml @@ -3,6 +3,9 @@ env: before: hooks: - go mod tidy +release: + draft: true + discussion_category_name: General builds: - id: nowin env: From 23eea9188f0b87afc999e8a9773c5ee199a76b6f Mon Sep 17 00:00:00 2001 From: wdvxdr Date: Sun, 5 Jun 2022 21:41:49 +0800 Subject: [PATCH 89/93] ci: update go version --- .github/workflows/release.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 3963c8d6..a2fb331b 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -17,7 +17,7 @@ jobs: - name: Set up Go uses: actions/setup-go@v2 with: - go-version: '1.17' + go-version: '1.18' - name: Run GoReleaser uses: goreleaser/goreleaser-action@v2 From 7d97216612153fc1a951b0153cd69c59eeba2c33 Mon Sep 17 00:00:00 2001 From: Cinte Date: Mon, 6 Jun 2022 12:38:50 +0800 Subject: [PATCH 90/93] =?UTF-8?q?fix:=20data=E6=96=87=E4=BB=B6=E5=A4=B9?= =?UTF-8?q?=E6=9D=83=E9=99=90=E9=97=AE=E9=A2=98=20(#1529)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * fix: data文件夹权限问题 当权限644时候,data文件夹会由于没有执行权限而无法创建后续的图片...等一系列文件夹。 * 0o744->0o755 --- cmd/gocq/main.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmd/gocq/main.go b/cmd/gocq/main.go index 1cb85cae..dacaead6 100644 --- a/cmd/gocq/main.go +++ b/cmd/gocq/main.go @@ -81,7 +81,7 @@ func Main() { mkCacheDir := func(path string, _type string) { if !global.PathExists(path) { - if err := os.MkdirAll(path, 0o644); err != nil { + if err := os.MkdirAll(path, 0o755); err != nil { log.Fatalf("创建%s缓存文件夹失败: %v", _type, err) } } From b013f662093376d372d598560552b26b94bf9ece Mon Sep 17 00:00:00 2001 From: Mrs4s Date: Mon, 6 Jun 2022 22:40:09 +0800 Subject: [PATCH 91/93] fix #1514 --- modules/mime/mime.go | 3 +++ 1 file changed, 3 insertions(+) diff --git a/modules/mime/mime.go b/modules/mime/mime.go index dbaa831a..f6bfa4ba 100644 --- a/modules/mime/mime.go +++ b/modules/mime/mime.go @@ -31,6 +31,9 @@ func checkImage(r io.ReadSeeker) (ok bool, t string) { if base.SkipMimeScan { return true, "" } + if r == nil { + return false, "image/nil-stream" + } t = scan(r) switch t { case "image/bmp", "image/gif", "image/jpeg", "image/png", "image/webp": From a4a8e94b279d6acce603ecce453e4b3de42a0b37 Mon Sep 17 00:00:00 2001 From: Mrs4s Date: Sat, 11 Jun 2022 18:14:22 +0800 Subject: [PATCH 92/93] update dep --- go.mod | 2 +- go.sum | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/go.mod b/go.mod index 4476534d..4a62380f 100644 --- a/go.mod +++ b/go.mod @@ -4,7 +4,7 @@ go 1.18 require ( github.com/Microsoft/go-winio v0.5.1 - github.com/Mrs4s/MiraiGo v0.0.0-20220605085305-ae33763fe10a + github.com/Mrs4s/MiraiGo v0.0.0-20220606142526-b56c61f5b4d6 github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c github.com/RomiChan/websocket v1.4.3-0.20220123145318-307a86b127bc github.com/fumiama/go-base16384 v1.5.2 diff --git a/go.sum b/go.sum index 265b5fa3..98540b92 100644 --- a/go.sum +++ b/go.sum @@ -1,7 +1,7 @@ github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY= github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84= -github.com/Mrs4s/MiraiGo v0.0.0-20220605085305-ae33763fe10a h1:DVrEVvLNKb53wTTduRdC+hZ80S/5G9qFmKYmCmIMVws= -github.com/Mrs4s/MiraiGo v0.0.0-20220605085305-ae33763fe10a/go.mod h1:mZp8Lt7uqLCUwSLouB2yuiP467Cwl4mnG9IMAaXUKA0= +github.com/Mrs4s/MiraiGo v0.0.0-20220606142526-b56c61f5b4d6 h1:nDIxbI1lLfX4LsslhY5pfYhpb9LRprin59eTEnL8aWU= +github.com/Mrs4s/MiraiGo v0.0.0-20220606142526-b56c61f5b4d6/go.mod h1:mZp8Lt7uqLCUwSLouB2yuiP467Cwl4mnG9IMAaXUKA0= github.com/RomiChan/protobuf v0.1.1-0.20220602121309-9e3b8cbefd7a h1:WIfEWYj82oEuPtm5pqlyQmCJCoiw00C6ugZFqHA0cC8= github.com/RomiChan/protobuf v0.1.1-0.20220602121309-9e3b8cbefd7a/go.mod h1:2Ie+hdBFQpQFDHfeklgxoFmQRCE7O+KwFpISeXq7OwA= github.com/RomiChan/syncx v0.0.0-20220404072119-d7ea0ae15a4c h1:cNPOdTNiVwxLpROLjXCgbIPvdkE+BwvxDvgmdYmWx6Q= From acdd864deaf76dd831540ea885ad24996241117d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=BA=90=E6=96=87=E9=9B=A8?= <41315874+fumiama@users.noreply.github.com> Date: Mon, 13 Jun 2022 12:47:06 +0800 Subject: [PATCH 93/93] sync --- cmd/gocq/banner.go | 1 - cmd/gocq/base.go | 14 +++++++++++++- cmd/gocq/doubleclick.go | 23 ----------------------- main.go | 3 +-- 4 files changed, 14 insertions(+), 27 deletions(-) delete mode 100644 cmd/gocq/doubleclick.go diff --git a/cmd/gocq/banner.go b/cmd/gocq/banner.go index d5517ce9..d3f9f31a 100644 --- a/cmd/gocq/banner.go +++ b/cmd/gocq/banner.go @@ -22,7 +22,6 @@ func PrintBanner() { log.Info("当前版本:", base.Version) if base.Debug { log.SetLevel(log.DebugLevel) - log.SetReportCaller(true) log.Warnf("已开启Debug模式.") // log.Debugf("开发交流群: 192548878") } diff --git a/cmd/gocq/base.go b/cmd/gocq/base.go index 748bc12d..9b7698f8 100644 --- a/cmd/gocq/base.go +++ b/cmd/gocq/base.go @@ -1,14 +1,25 @@ package gocq import ( + "time" + + "github.com/Mrs4s/go-cqhttp/global/terminal" "github.com/Mrs4s/go-cqhttp/internal/base" "github.com/Mrs4s/go-cqhttp/server" + log "github.com/sirupsen/logrus" ) // InitBase 解析 flags 与配置文件到 base func InitBase() { base.Parse() - base.Init() + if !base.FastStart && terminal.RunningByDoubleClick() { + err := terminal.NoMoreDoubleClick() + if err != nil { + log.Errorf("遇到错误: %v", err) + time.Sleep(time.Second * 5) + } + return + } switch { case base.LittleH: base.Help() @@ -17,4 +28,5 @@ func InitBase() { case base.LittleWD != "": base.ResetWorkingDir() } + base.Init() } diff --git a/cmd/gocq/doubleclick.go b/cmd/gocq/doubleclick.go deleted file mode 100644 index f0a0be4e..00000000 --- a/cmd/gocq/doubleclick.go +++ /dev/null @@ -1,23 +0,0 @@ -package gocq - -import ( - "os" - "time" - - log "github.com/sirupsen/logrus" - - "github.com/Mrs4s/go-cqhttp/global/terminal" - "github.com/Mrs4s/go-cqhttp/internal/base" -) - -// CheckDoubleClick 检查双击启动 -func CheckDoubleClick() { - if !base.FastStart && terminal.RunningByDoubleClick() { - err := terminal.NoMoreDoubleClick() - if err != nil { - log.Errorf("遇到错误: %v", err) - time.Sleep(time.Second * 5) - } - os.Exit(0) - } -} diff --git a/main.go b/main.go index fdf5fdd7..db1bbb13 100644 --- a/main.go +++ b/main.go @@ -14,11 +14,10 @@ import ( func main() { gocq.InitBase() gocq.InitLog() - gocq.CheckDoubleClick() gocq.InitCache() gocq.InitDB() gocq.PrintBanner() - gocq.CheckKey(gocq.ParseCommand()) gocq.LoadDevice() + gocq.CheckKey(gocq.ParseCommand()) gocq.Main() }