aireply add chatgpt

This commit is contained in:
源文雨 2023-02-27 13:52:12 +08:00
parent 3c905d9061
commit f28e746652
4 changed files with 80 additions and 36 deletions

4
go.mod
View File

@ -4,7 +4,7 @@ go 1.19
require ( require (
github.com/Baidu-AIP/golang-sdk v1.1.1 github.com/Baidu-AIP/golang-sdk v1.1.1
github.com/FloatTech/AnimeAPI v1.6.1-0.20230207081411-573533b18194 github.com/FloatTech/AnimeAPI v1.6.1-0.20230225045520-b537bd7dfbfe
github.com/FloatTech/floatbox v0.0.0-20230207075003-0f70b30c320d github.com/FloatTech/floatbox v0.0.0-20230207075003-0f70b30c320d
github.com/FloatTech/gg v1.1.2 github.com/FloatTech/gg v1.1.2
github.com/FloatTech/imgfactory v0.2.2-0.20230215052637-9f7b05520ca9 github.com/FloatTech/imgfactory v0.2.2-0.20230215052637-9f7b05520ca9
@ -12,7 +12,7 @@ require (
github.com/FloatTech/sqlite v1.5.7 github.com/FloatTech/sqlite v1.5.7
github.com/FloatTech/ttl v0.0.0-20220715042055-15612be72f5b github.com/FloatTech/ttl v0.0.0-20220715042055-15612be72f5b
github.com/FloatTech/zbpctrl v1.5.3-0.20230130095145-714ad318cd52 github.com/FloatTech/zbpctrl v1.5.3-0.20230130095145-714ad318cd52
github.com/FloatTech/zbputils v1.6.2-0.20230215092613-4a7ebf458f16 github.com/FloatTech/zbputils v1.6.2-0.20230217063720-e64cc4bde7c6
github.com/RomiChan/syncx v0.0.0-20221202055724-5f842c53020e github.com/RomiChan/syncx v0.0.0-20221202055724-5f842c53020e
github.com/RomiChan/websocket v1.4.3-0.20220227141055-9b2c6168c9c5 github.com/RomiChan/websocket v1.4.3-0.20220227141055-9b2c6168c9c5
github.com/antchfx/htmlquery v1.2.5 github.com/antchfx/htmlquery v1.2.5

8
go.sum
View File

@ -2,8 +2,8 @@ github.com/Baidu-AIP/golang-sdk v1.1.1 h1:RQsAmgDSAkiq22I6n7XJ2t3afgzFeqjY46FGhv
github.com/Baidu-AIP/golang-sdk v1.1.1/go.mod h1:bXnGw7xPeKt8aF7UCELKrV6UZ/46spItONK1RQBQj1Y= github.com/Baidu-AIP/golang-sdk v1.1.1/go.mod h1:bXnGw7xPeKt8aF7UCELKrV6UZ/46spItONK1RQBQj1Y=
github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
github.com/DATA-DOG/go-sqlmock v1.3.3/go.mod h1:f/Ixk793poVmq4qj/V1dPUg2JEAKC73Q5eFN3EC/SaM= github.com/DATA-DOG/go-sqlmock v1.3.3/go.mod h1:f/Ixk793poVmq4qj/V1dPUg2JEAKC73Q5eFN3EC/SaM=
github.com/FloatTech/AnimeAPI v1.6.1-0.20230207081411-573533b18194 h1:+p85V0fdZNt3UoKreBeI6S3IOPvNmU5/Fnn39ipSkVk= github.com/FloatTech/AnimeAPI v1.6.1-0.20230225045520-b537bd7dfbfe h1:C2PXT21kloAiOfnkg+AHH66CZZrgccz30YjHmKdmVTw=
github.com/FloatTech/AnimeAPI v1.6.1-0.20230207081411-573533b18194/go.mod h1:LCiKZivPVazRRCnnADQfIBFZiIPHHCFqaCpwZWsFehI= github.com/FloatTech/AnimeAPI v1.6.1-0.20230225045520-b537bd7dfbfe/go.mod h1:LCiKZivPVazRRCnnADQfIBFZiIPHHCFqaCpwZWsFehI=
github.com/FloatTech/floatbox v0.0.0-20230207075003-0f70b30c320d h1:vVqMO5Kejt5pueuZvBxfX+psa7UwE110TpITf5eV7Zw= github.com/FloatTech/floatbox v0.0.0-20230207075003-0f70b30c320d h1:vVqMO5Kejt5pueuZvBxfX+psa7UwE110TpITf5eV7Zw=
github.com/FloatTech/floatbox v0.0.0-20230207075003-0f70b30c320d/go.mod h1:OoZE4Ra7olpFaJSrlD6mcyT4chPLg9QBRE1pzTC8R84= github.com/FloatTech/floatbox v0.0.0-20230207075003-0f70b30c320d/go.mod h1:OoZE4Ra7olpFaJSrlD6mcyT4chPLg9QBRE1pzTC8R84=
github.com/FloatTech/gg v1.1.2 h1:YolgOYg3uDHc1+g0bLtt6QuRA/pvLn+b9IBCIhOOX88= github.com/FloatTech/gg v1.1.2 h1:YolgOYg3uDHc1+g0bLtt6QuRA/pvLn+b9IBCIhOOX88=
@ -18,8 +18,8 @@ github.com/FloatTech/ttl v0.0.0-20220715042055-15612be72f5b h1:tvciXWq2nuvTbFeJG
github.com/FloatTech/ttl v0.0.0-20220715042055-15612be72f5b/go.mod h1:fHZFWGquNXuHttu9dUYoKuNbm3dzLETnIOnm1muSfDs= github.com/FloatTech/ttl v0.0.0-20220715042055-15612be72f5b/go.mod h1:fHZFWGquNXuHttu9dUYoKuNbm3dzLETnIOnm1muSfDs=
github.com/FloatTech/zbpctrl v1.5.3-0.20230130095145-714ad318cd52 h1:BrStRXeosWh8L0iA/EjPd8w6xNexDkqki39ITZko/9Q= github.com/FloatTech/zbpctrl v1.5.3-0.20230130095145-714ad318cd52 h1:BrStRXeosWh8L0iA/EjPd8w6xNexDkqki39ITZko/9Q=
github.com/FloatTech/zbpctrl v1.5.3-0.20230130095145-714ad318cd52/go.mod h1:qqMLUwR7tKpqnAqsgI7aZbn0hbs2FEVF4ylMXqIpBdY= github.com/FloatTech/zbpctrl v1.5.3-0.20230130095145-714ad318cd52/go.mod h1:qqMLUwR7tKpqnAqsgI7aZbn0hbs2FEVF4ylMXqIpBdY=
github.com/FloatTech/zbputils v1.6.2-0.20230215092613-4a7ebf458f16 h1:fOnI0V//DOW62vAhnC1a+qDMnlbJIAIiUHVX7CaUk5s= github.com/FloatTech/zbputils v1.6.2-0.20230217063720-e64cc4bde7c6 h1:iHfqarofWkwwPfOG/5XbsvY7JutoEQmhxKvLxrFbiZw=
github.com/FloatTech/zbputils v1.6.2-0.20230215092613-4a7ebf458f16/go.mod h1:Lo7y67u9EGt7l3ZBavc5bbryEIaeRYfbVy9KWIw6qk4= github.com/FloatTech/zbputils v1.6.2-0.20230217063720-e64cc4bde7c6/go.mod h1:Lo7y67u9EGt7l3ZBavc5bbryEIaeRYfbVy9KWIw6qk4=
github.com/PuerkitoBio/goquery v1.5.1/go.mod h1:GsLWisAFVj4WgDibEWF4pvYnkVQBpKBKeU+7zCJoLcc= github.com/PuerkitoBio/goquery v1.5.1/go.mod h1:GsLWisAFVj4WgDibEWF4pvYnkVQBpKBKeU+7zCJoLcc=
github.com/RomiChan/syncx v0.0.0-20221202055724-5f842c53020e h1:wR3MXQ3VbUlPKOOUwLOYgh/QaJThBTYtsl673O3lqSA= github.com/RomiChan/syncx v0.0.0-20221202055724-5f842c53020e h1:wR3MXQ3VbUlPKOOUwLOYgh/QaJThBTYtsl673O3lqSA=
github.com/RomiChan/syncx v0.0.0-20221202055724-5f842c53020e/go.mod h1:vD7Ra3Q9onRtojoY5sMCLQ7JBgjUsrXDnDKyFxqpf9w= github.com/RomiChan/syncx v0.0.0-20221202055724-5f842c53020e/go.mod h1:vD7Ra3Q9onRtojoY5sMCLQ7JBgjUsrXDnDKyFxqpf9w=

View File

@ -32,20 +32,28 @@ const (
mockingbirdttsindex mockingbirdttsindex
) )
// extrattsname is the tts other than genshin vits
var extrattsname = []string{"百度", "拟声鸟"}
const ( const (
defaultttsindexkey = -2905 defaultttsindexkey = -2905
gsapikeyextragrp = -1
chatgptapikeyextragrp = -2
) )
var replyModes = [...]string{"青云客", "小爱"} type replymode struct {
APIKey string // APIKey is for chatgpt
replyModes []string `json:"-"`
}
func setReplyMode(ctx *zero.Ctx, name string) error { func (r *replymode) setReplyMode(ctx *zero.Ctx, name string) error {
gid := ctx.Event.GroupID gid := ctx.Event.GroupID
if gid == 0 { if gid == 0 {
gid = -ctx.Event.UserID gid = -ctx.Event.UserID
} }
var ok bool var ok bool
var index int64 var index int64
for i, s := range replyModes { for i, s := range r.replyModes {
if s == name { if s == name {
ok = true ok = true
index = int64(i) index = int64(i)
@ -62,24 +70,47 @@ func setReplyMode(ctx *zero.Ctx, name string) error {
return m.SetData(gid, (m.GetData(index)&^0xff)|(index&0xff)) return m.SetData(gid, (m.GetData(index)&^0xff)|(index&0xff))
} }
func getReplyMode(ctx *zero.Ctx) aireply.AIReply { func (r *replymode) getReplyMode(ctx *zero.Ctx) aireply.AIReply {
gid := ctx.Event.GroupID gid := ctx.Event.GroupID
if gid == 0 { if gid == 0 {
gid = -ctx.Event.UserID gid = -ctx.Event.UserID
} }
m, ok := ctx.State["manager"].(*ctrl.Control[*zero.Ctx]) m, ok := ctx.State["manager"].(*ctrl.Control[*zero.Ctx])
if ok { if ok {
if m.GetData(gid)&0xff == 1 { switch m.GetData(gid) & 0xff {
case 0:
return aireply.NewQYK(aireply.QYKURL, aireply.QYKBotName)
case 1:
return aireply.NewXiaoAi(aireply.XiaoAiURL, aireply.XiaoAiBotName) return aireply.NewXiaoAi(aireply.XiaoAiURL, aireply.XiaoAiBotName)
case 2:
k := r.getAPIKey(ctx)
if k != "" {
return aireply.NewChatGPT(aireply.ChatGPTURL, k)
} }
return aireply.NewQYK(aireply.QYKURL, aireply.QYKBotName) return aireply.NewQYK(aireply.QYKURL, aireply.QYKBotName)
} }
}
return aireply.NewQYK(aireply.QYKURL, aireply.QYKBotName) return aireply.NewQYK(aireply.QYKURL, aireply.QYKBotName)
} }
func (r *replymode) getAPIKey(ctx *zero.Ctx) string {
if r.APIKey == "" {
m := ctx.State["manager"].(*ctrl.Control[*zero.Ctx])
_ = m.Manager.GetExtra(chatgptapikeyextragrp, &r)
logrus.Debugln("[tts] get api key:", r.APIKey)
}
return r.APIKey
}
func (r *replymode) setAPIKey(m *ctrl.Control[*zero.Ctx], key string) error {
r.APIKey = key
_ = m.Manager.Response(chatgptapikeyextragrp)
return m.Manager.SetExtra(chatgptapikeyextragrp, r)
}
var ttsins = func() map[string]tts.TTS { var ttsins = func() map[string]tts.TTS {
m := make(map[string]tts.TTS, 128) m := make(map[string]tts.TTS, 128)
for _, mode := range append(genshin.SoundList[:], "百度", "拟声鸟") { for _, mode := range append(genshin.SoundList[:], extrattsname...) {
m[mode] = nil m[mode] = nil
} }
return m return m
@ -87,7 +118,7 @@ var ttsins = func() map[string]tts.TTS {
var ttsModes = func() []string { var ttsModes = func() []string {
s := append(genshin.SoundList[:], make([]string, 64-len(genshin.SoundList))...) // 0-63 s := append(genshin.SoundList[:], make([]string, 64-len(genshin.SoundList))...) // 0-63
s = append(s, "百度", "拟声鸟") // 64 65 s = append(s, extrattsname...) // 64 65 ...
return s return s
}() }()
@ -127,7 +158,7 @@ func newttsmode() *ttsmode {
func (t *ttsmode) getAPIKey(ctx *zero.Ctx) string { func (t *ttsmode) getAPIKey(ctx *zero.Ctx) string {
if t.APIKey == "" { if t.APIKey == "" {
m := ctx.State["manager"].(*ctrl.Control[*zero.Ctx]) m := ctx.State["manager"].(*ctrl.Control[*zero.Ctx])
_ = m.Manager.GetExtra(-1, &t) _ = m.Manager.GetExtra(gsapikeyextragrp, &t)
logrus.Debugln("[tts] get api key:", t.APIKey) logrus.Debugln("[tts] get api key:", t.APIKey)
} }
return url.QueryEscape(t.APIKey) return url.QueryEscape(t.APIKey)
@ -135,8 +166,8 @@ func (t *ttsmode) getAPIKey(ctx *zero.Ctx) string {
func (t *ttsmode) setAPIKey(m *ctrl.Control[*zero.Ctx], key string) error { func (t *ttsmode) setAPIKey(m *ctrl.Control[*zero.Ctx], key string) error {
t.APIKey = key t.APIKey = key
_ = m.Manager.Response(-1) _ = m.Manager.Response(gsapikeyextragrp)
return m.Manager.SetExtra(-1, t) return m.Manager.SetExtra(gsapikeyextragrp, t)
} }
func (t *ttsmode) setSoundMode(ctx *zero.Ctx, name string, baiduper, mockingsynt int) error { func (t *ttsmode) setSoundMode(ctx *zero.Ctx, name string, baiduper, mockingsynt int) error {
@ -157,9 +188,9 @@ func (t *ttsmode) setSoundMode(ctx *zero.Ctx, name string, baiduper, mockingsynt
} }
if index == -1 { if index == -1 {
switch name { switch name {
case "百度": case extrattsname[0]:
index = baiduttsindex index = baiduttsindex
case "拟声鸟": case extrattsname[1]:
index = mockingbirdttsindex index = mockingbirdttsindex
default: default:
return errors.New("语音人物" + name + "未注册index") return errors.New("语音人物" + name + "未注册index")
@ -189,9 +220,9 @@ func (t *ttsmode) getSoundMode(ctx *zero.Ctx) (tts.TTS, error) {
ins, ok := ttsins[mode] ins, ok := ttsins[mode]
if !ok || ins == nil { if !ok || ins == nil {
switch mode { switch mode {
case "百度": case extrattsname[0]:
ins = baidutts.NewBaiduTTS(int(i&0x0f00) >> 8) ins = baidutts.NewBaiduTTS(int(i&0x0f00) >> 8)
case "拟声鸟": case extrattsname[1]:
var err error var err error
ins, err = mockingbird.NewMockingBirdTTS(int(i&0xf000) >> 12) ins, err = mockingbird.NewMockingBirdTTS(int(i&0xf000) >> 12)
if err != nil { if err != nil {
@ -234,9 +265,9 @@ func (t *ttsmode) setDefaultSoundMode(name string, baiduper, mockingsynt int) er
} }
if index == -1 { if index == -1 {
switch name { switch name {
case "百度": case extrattsname[0]:
index = baiduttsindex index = baiduttsindex
case "拟声鸟": case extrattsname[1]:
index = mockingbirdttsindex index = mockingbirdttsindex
default: default:
return errors.New("语音人物" + name + "未注册index") return errors.New("语音人物" + name + "未注册index")

View File

@ -15,7 +15,11 @@ import (
"github.com/wdvxdr1123/ZeroBot/message" "github.com/wdvxdr1123/ZeroBot/message"
) )
var t = newttsmode() var replmd = replymode{
replyModes: []string{"青云客", "小爱", "ChatGPT"},
}
var ttsmd = newttsmode()
func init() { // 插件主体 func init() { // 插件主体
ent := control.Register("tts", &ctrl.Options[*zero.Ctx]{ ent := control.Register("tts", &ctrl.Options[*zero.Ctx]{
@ -32,13 +36,13 @@ func init() { // 插件主体
enr := control.Register("aireply", &ctrl.Options[*zero.Ctx]{ enr := control.Register("aireply", &ctrl.Options[*zero.Ctx]{
DisableOnDefault: false, DisableOnDefault: false,
Brief: "人工智能回复", Brief: "人工智能回复",
Help: "- @Bot 任意文本(任意一句话回复)\n- 设置回复模式[青云客|小爱]", Help: "- @Bot 任意文本(任意一句话回复)\n- 设置回复模式[青云客|小爱|ChatGPT]\n- 设置 ChatGPT api key xxx",
PrivateDataFolder: "aireply", PrivateDataFolder: "aireply",
}) })
enr.OnMessage(zero.OnlyToMe).SetBlock(true).Limit(ctxext.LimitByUser). enr.OnMessage(zero.OnlyToMe).SetBlock(true).Limit(ctxext.LimitByUser).
Handle(func(ctx *zero.Ctx) { Handle(func(ctx *zero.Ctx) {
aireply := getReplyMode(ctx) aireply := replmd.getReplyMode(ctx)
reply := message.ParseMessageFromString(aireply.Talk(ctx.Event.UserID, ctx.ExtractPlainText(), zero.BotConfig.NickName[0])) reply := message.ParseMessageFromString(aireply.Talk(ctx.Event.UserID, ctx.ExtractPlainText(), zero.BotConfig.NickName[0]))
// 回复 // 回复
time.Sleep(time.Second * 1) time.Sleep(time.Second * 1)
@ -52,7 +56,7 @@ func init() { // 插件主体
enr.OnPrefix("设置回复模式", zero.AdminPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) { enr.OnPrefix("设置回复模式", zero.AdminPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) {
param := ctx.State["args"].(string) param := ctx.State["args"].(string)
err := setReplyMode(ctx, param) err := replmd.setReplyMode(ctx, param)
if err != nil { if err != nil {
ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err)) ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err))
return return
@ -60,16 +64,25 @@ func init() { // 插件主体
ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text("成功")) ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text("成功"))
}) })
ent.OnRegex(`^设置\s*ChatGPT\s*api\s*key\s*(.*)$`, zero.OnlyPrivate, zero.SuperUserPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) {
err := replmd.setAPIKey(ctx.State["manager"].(*ctrl.Control[*zero.Ctx]), ctx.State["regex_matched"].([]string)[1])
if err != nil {
ctx.SendChain(message.Text("ERROR: ", err))
return
}
ctx.SendChain(message.Text("设置成功"))
})
endpre := regexp.MustCompile(`\pP$`) endpre := regexp.MustCompile(`\pP$`)
ent.OnMessage(zero.OnlyToMe).SetBlock(true).Limit(ctxext.LimitByUser). ent.OnMessage(zero.OnlyToMe).SetBlock(true).Limit(ctxext.LimitByUser).
Handle(func(ctx *zero.Ctx) { Handle(func(ctx *zero.Ctx) {
msg := ctx.ExtractPlainText() msg := ctx.ExtractPlainText()
// 获取回复模式 // 获取回复模式
r := getReplyMode(ctx) r := replmd.getReplyMode(ctx)
// 获取回复的文本 // 获取回复的文本
reply := r.TalkPlain(ctx.Event.UserID, msg, zero.BotConfig.NickName[0]) reply := r.TalkPlain(ctx.Event.UserID, msg, zero.BotConfig.NickName[0])
// 获取语音 // 获取语音
speaker, err := t.getSoundMode(ctx) speaker, err := ttsmd.getSoundMode(ctx)
if err != nil { if err != nil {
ctx.SendChain(message.Text("ERROR: ", err)) ctx.SendChain(message.Text("ERROR: ", err))
return return
@ -104,7 +117,7 @@ func init() { // 插件主体
} }
// 保存设置 // 保存设置
logrus.Debugln("[tts] t.setSoundMode( ctx", param, n, n, ")") logrus.Debugln("[tts] t.setSoundMode( ctx", param, n, n, ")")
err = t.setSoundMode(ctx, param, n, n) err = ttsmd.setSoundMode(ctx, param, n, n)
if err != nil { if err != nil {
ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err)) ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err))
return return
@ -112,7 +125,7 @@ func init() { // 插件主体
if banner, ok := genshin.TestRecord[param]; ok { if banner, ok := genshin.TestRecord[param]; ok {
logrus.Debugln("[tts] banner:", banner, "get sound mode...") logrus.Debugln("[tts] banner:", banner, "get sound mode...")
// 设置验证 // 设置验证
speaker, err := t.getSoundMode(ctx) speaker, err := ttsmd.getSoundMode(ctx)
if err != nil { if err != nil {
ctx.SendChain(message.Text("ERROR: ", err)) ctx.SendChain(message.Text("ERROR: ", err))
return return
@ -146,7 +159,7 @@ func init() { // 插件主体
} }
} }
// 保存设置 // 保存设置
err = t.setDefaultSoundMode(param, n, n) err = ttsmd.setDefaultSoundMode(param, n, n)
if err != nil { if err != nil {
ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err)) ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err))
return return
@ -155,13 +168,13 @@ func init() { // 插件主体
}) })
ent.OnFullMatch("恢复成默认语音模式", zero.AdminPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) { ent.OnFullMatch("恢复成默认语音模式", zero.AdminPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) {
err := t.resetSoundMode(ctx) err := ttsmd.resetSoundMode(ctx)
if err != nil { if err != nil {
ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err)) ctx.SendChain(message.Reply(ctx.Event.MessageID), message.Text(err))
return return
} }
// 设置验证 // 设置验证
speaker, err := t.getSoundMode(ctx) speaker, err := ttsmd.getSoundMode(ctx)
if err != nil { if err != nil {
ctx.SendChain(message.Text("ERROR: ", err)) ctx.SendChain(message.Text("ERROR: ", err))
return return
@ -170,7 +183,7 @@ func init() { // 插件主体
}) })
ent.OnRegex(`^设置原神语音\s*api\s*key\s*([0-9a-zA-Z-_]{54}==)$`, zero.OnlyPrivate, zero.SuperUserPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) { ent.OnRegex(`^设置原神语音\s*api\s*key\s*([0-9a-zA-Z-_]{54}==)$`, zero.OnlyPrivate, zero.SuperUserPermission).SetBlock(true).Handle(func(ctx *zero.Ctx) {
err := t.setAPIKey(ctx.State["manager"].(*ctrl.Control[*zero.Ctx]), ctx.State["regex_matched"].([]string)[1]) err := ttsmd.setAPIKey(ctx.State["manager"].(*ctrl.Control[*zero.Ctx]), ctx.State["regex_matched"].([]string)[1])
if err != nil { if err != nil {
ctx.SendChain(message.Text("ERROR: ", err)) ctx.SendChain(message.Text("ERROR: ", err))
return return