Skip to content

Commit

Permalink
beta323
Browse files Browse the repository at this point in the history
  • Loading branch information
Hoshinonyaruko committed Feb 18, 2024
1 parent 123ca2f commit 7acd904
Show file tree
Hide file tree
Showing 7 changed files with 80 additions and 6 deletions.
8 changes: 8 additions & 0 deletions botgo/dto/websocket.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,14 @@ type WebsocketAP struct {
SessionStartLimit SessionStartLimit `json:"session_start_limit"`
}

// WebsocketAP wss 单个接入点信息
type WebsocketAPSingle struct {
URL string `json:"url"`
ShardCount uint32 `json:"shards"` //最大值 比如是4个分片就是4
ShardID uint32 `json:"shard_id"` //从0开始的 0 1 2 3 对应上面的
SessionStartLimit SessionStartLimit `json:"session_start_limit"`
}

// SessionStartLimit 链接频控信息
type SessionStartLimit struct {
Total uint32 `json:"total"`
Expand Down
2 changes: 2 additions & 0 deletions botgo/session_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,6 @@ var defaultSessionManager SessionManager = local.New()
type SessionManager interface {
// Start 启动连接,默认使用 apInfo 中的 shards 作为 shard 数量,如果有需要自己指定 shard 数,请修 apInfo 中的信息
Start(apInfo *dto.WebsocketAP, token *token.Token, intents *dto.Intent) error
// 自己指定具体的shard
StartSingle(apInfo *dto.WebsocketAPSingle, token *token.Token, intents *dto.Intent) error
}
30 changes: 30 additions & 0 deletions botgo/sessions/local/local.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,36 @@ func (l *ChanManager) Start(apInfo *dto.WebsocketAP, token *token.Token, intents
return nil
}

// Start 启动指定的分片 session manager 适合想要手动指定目前分片的开发者(分片较少)
func (l *ChanManager) StartSingle(apInfo *dto.WebsocketAPSingle, token *token.Token, intents *dto.Intent) error {
defer log.Sync()
if err := manager.CheckSessionLimitSingle(apInfo); err != nil {
log.Errorf("[ws/session/local] session limited apInfo: %+v", apInfo)
return err
}
startInterval := manager.CalcInterval(apInfo.SessionStartLimit.MaxConcurrency)
log.Infof("[ws/session/local] will start %d sessions and per session start interval is %s",
apInfo.ShardCount, startInterval)

// 只启动一个分片

session := dto.Session{
URL: apInfo.URL,
Token: *token,
Intent: *intents,
LastSeq: 0,
Shards: dto.ShardConfig{
ShardID: apInfo.ShardID,
ShardCount: apInfo.ShardCount,
},
}

time.Sleep(startInterval)
go l.newConnect(session)

return nil
}

// newConnect 启动一个新的连接,如果连接在监听过程中报错了,或者被远端关闭了链接,需要识别关闭的原因,能否继续 resume
// 如果能够 resume,则往 sessionChan 中放入带有 sessionID 的 session
// 如果不能,则清理掉 sessionID,将 session 放入 sessionChan 中
Expand Down
8 changes: 8 additions & 0 deletions botgo/sessions/manager/manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -59,3 +59,11 @@ func CheckSessionLimit(apInfo *dto.WebsocketAP) error {
}
return nil
}

// CheckSessionLimit 检查链接数是否达到限制,如果达到限制需要等待重置
func CheckSessionLimitSingle(apInfo *dto.WebsocketAPSingle) error {
if apInfo.ShardCount > apInfo.SessionStartLimit.Remaining {
return errs.ErrSessionLimit
}
return nil
}
2 changes: 2 additions & 0 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,8 @@ type Settings struct {
LinkPic string `yaml:"link_pic"`
MusicPrefix string `yaml:"music_prefix"`
DisableWebui bool `yaml:"disable_webui"`
ShardCount int `yaml:"shard_count"`
ShardID int `yaml:"shard_id"`
}

// LoadConfig 从文件中加载配置并初始化单例配置
Expand Down
34 changes: 28 additions & 6 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -184,6 +184,12 @@ func main() {
if err != nil {
log.Fatalln(err)
}
fmt.Printf("分片建议\n")
fmt.Printf("建议的分片数量:%d\n", wsInfo.Shards)
fmt.Printf("每 24 小时可创建 Session 数:%d\n", wsInfo.SessionStartLimit.Total)
fmt.Printf("目前还可以创建的 Session 数:%d\n", wsInfo.SessionStartLimit.Remaining)
fmt.Printf("重置计数的剩余时间(ms):%d\n", wsInfo.SessionStartLimit.ResetAfter)
fmt.Printf("每 5s 可以创建的 Session 数:%d\n", wsInfo.SessionStartLimit.MaxConcurrency)

// 定义和初始化intent变量
var intent dto.Intent = 0
Expand All @@ -204,12 +210,28 @@ func main() {

// 启动session manager以管理websocket连接
// 指定需要启动的分片数为 2 的话可以手动修改 wsInfo
go func() {
wsInfo.Shards = 1
if err = botgo.NewSessionManager().Start(wsInfo, token, &intent); err != nil {
log.Fatalln(err)
}
}()
if conf.Settings.ShardCount == 1 {
go func() {
wsInfo.Shards = 1
if err = botgo.NewSessionManager().Start(wsInfo, token, &intent); err != nil {
log.Fatalln(err)
}
}()
log.Printf("不使用分片,所有信息都由当前gensokyo处理...\n")
} else {
go func() {
wsInfoSingle := &dto.WebsocketAPSingle{
URL: wsInfo.URL,
ShardCount: uint32(conf.Settings.ShardCount),
ShardID: uint32(conf.Settings.ShardID),
SessionStartLimit: wsInfo.SessionStartLimit,
}
if err = botgo.NewSessionManager().StartSingle(wsInfoSingle, token, &intent); err != nil {
log.Fatalln(err)
}
}()
log.Printf("使用%d个分片,当前是第%d个分片,比如:[0,4],代表分为四个片,当前链接是第 0 个片,业务稍后应该继续多开gensokyo,可在不同的服务器和ip地址 shard 为[1,4],[2,4],[3,4]的链接,才能完整接收和处理事件。\n", conf.Settings.ShardCount, conf.Settings.ShardID)
}

// 启动多个WebSocket客户端的逻辑
if !allEmpty(conf.Settings.WsAddress) {
Expand Down
2 changes: 2 additions & 0 deletions template/config_template.go
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,8 @@ settings:
idmap_pro : false #需开启hash_id配合,高级id转换增强,可以多个真实值bind到同一个虚拟值,对于每个用户,每个群\私聊\判断私聊\频道,都会产生新的虚拟值,但可以多次bind,bind到同一个数字.数据库负担会变大.
send_delay : 300 #单位 毫秒 默认300ms 可以视情况减少到100或者50
disable_webui: false #禁用webui
shard_count: 1 #分片数量 默认1
shard_id: 0 #当前分片id 默认从0开始,详细请看 https://bot.q.qq.com/wiki/develop/api/gateway/reference.html
title : "Gensokyo © 2023 - Hoshinonyaruko" #程序的标题 如果多个机器人 可根据标题区分
custom_bot_name : "Gensokyo全域机器人" #自定义机器人名字,会在api调用中返回,默认Gensokyo全域机器人
Expand Down

0 comments on commit 7acd904

Please sign in to comment.