chore: refresh gramsrv public release
This commit is contained in:
parent
75cebe8dbf
commit
70b6820474
1274 changed files with 378751 additions and 59919 deletions
220
internal/rpc/messages_bot_longtail.go
Normal file
220
internal/rpc/messages_bot_longtail.go
Normal file
|
|
@ -0,0 +1,220 @@
|
|||
package rpc
|
||||
|
||||
import (
|
||||
"context"
|
||||
"strconv"
|
||||
"strings"
|
||||
"unicode/utf8"
|
||||
|
||||
"github.com/gotd/td/tg"
|
||||
|
||||
"telesrv/internal/domain"
|
||||
)
|
||||
|
||||
func (r *Router) onMessagesSendWebViewData(ctx context.Context, req *tg.MessagesSendWebViewDataRequest) (tg.UpdatesClass, error) {
|
||||
if req == nil {
|
||||
return nil, botInvalidErr()
|
||||
}
|
||||
userID, _, err := r.currentUserID(ctx)
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
if r.deps.Messages == nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
if req.RandomID == 0 ||
|
||||
strings.TrimSpace(req.ButtonText) == "" ||
|
||||
utf8.RuneCountInString(req.ButtonText) > domain.MaxWebViewDataButtonTextLen ||
|
||||
len(req.Data) > domain.MaxWebViewDataPayloadLen {
|
||||
return nil, buttonDataInvalidErr()
|
||||
}
|
||||
bot, err := r.botUserFromInput(ctx, userID, req.Bot)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if bot.ID == userID {
|
||||
return nil, botInvalidErr()
|
||||
}
|
||||
recipientBlocked, err := r.peerBlocksUser(ctx, userID, bot.ID)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
authKeyID, _ := AuthKeyIDFrom(ctx)
|
||||
sessionID, _ := SessionIDFrom(ctx)
|
||||
res, err := r.deps.Messages.SendPrivateText(ctx, userID, domain.SendPrivateTextRequest{
|
||||
SenderUserID: userID,
|
||||
RecipientUserID: bot.ID,
|
||||
RandomID: req.RandomID,
|
||||
Media: &domain.MessageMedia{
|
||||
Kind: domain.MessageMediaKindService,
|
||||
ServiceAction: &domain.MessageServiceAction{
|
||||
Kind: domain.MessageServiceActionWebViewDataSent,
|
||||
WebViewData: &domain.MessageWebViewDataAction{
|
||||
ButtonText: req.ButtonText,
|
||||
Data: req.Data,
|
||||
},
|
||||
},
|
||||
},
|
||||
Date: int(r.clock.Now().Unix()),
|
||||
OriginAuthKeyID: authKeyID,
|
||||
OriginSessionID: sessionID,
|
||||
RecipientBlocked: recipientBlocked,
|
||||
})
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
users := r.usersForMessageUpdate(ctx, userID, res.SenderMessage)
|
||||
chats := r.chatsForMessageUpdate(ctx, userID, res.SenderMessage)
|
||||
return tgPrivateMessageUpdates(res.SenderEvent, res.SenderMessage, 0, false, users, chats), nil
|
||||
}
|
||||
|
||||
func (r *Router) onMessagesSendBotRequestedPeer(ctx context.Context, req *tg.MessagesSendBotRequestedPeerRequest) (tg.UpdatesClass, error) {
|
||||
if req == nil {
|
||||
return nil, buttonDataInvalidErr()
|
||||
}
|
||||
userID, _, err := r.currentUserID(ctx)
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
if r.deps.Bots == nil || r.deps.Messages == nil || r.deps.Users == nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
botPeer, err := r.checkedDomainPeerFromInputPeer(ctx, userID, req.Peer)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if botPeer.Type != domain.PeerTypeUser {
|
||||
return nil, botInvalidErr()
|
||||
}
|
||||
botUser, found, err := r.deps.Users.ByID(ctx, userID, botPeer.ID)
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
if !found || !botUser.Bot {
|
||||
return nil, botInvalidErr()
|
||||
}
|
||||
webAppReqID, ok := req.GetWebappReqID()
|
||||
if !ok || webAppReqID == "" {
|
||||
return nil, buttonDataInvalidErr()
|
||||
}
|
||||
button, found, err := r.deps.Bots.GetRequestedWebViewButton(ctx, botUser.ID, userID, webAppReqID)
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
if !found || button.ButtonID != req.ButtonID {
|
||||
return nil, buttonDataInvalidErr()
|
||||
}
|
||||
if len(req.RequestedPeers) == 0 || len(req.RequestedPeers) > button.MaxQuantity {
|
||||
return nil, buttonDataInvalidErr()
|
||||
}
|
||||
peers := make([]domain.Peer, 0, len(req.RequestedPeers))
|
||||
for _, peer := range req.RequestedPeers {
|
||||
resolved, err := r.checkedDomainPeerFromInputPeer(ctx, userID, peer)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if !requestedPeerTypeMatches(button.PeerType, resolved) {
|
||||
return nil, buttonDataInvalidErr()
|
||||
}
|
||||
peers = append(peers, resolved)
|
||||
}
|
||||
recipientBlocked, err := r.peerBlocksUser(ctx, userID, botUser.ID)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
authKeyID, _ := AuthKeyIDFrom(ctx)
|
||||
sessionID, _ := SessionIDFrom(ctx)
|
||||
res, err := r.deps.Messages.SendPrivateText(ctx, userID, domain.SendPrivateTextRequest{
|
||||
SenderUserID: userID,
|
||||
RecipientUserID: botUser.ID,
|
||||
RandomID: botRequestedPeerServiceMessageRandomID(userID, botUser.ID, webAppReqID, button.ButtonID, peers),
|
||||
Media: &domain.MessageMedia{
|
||||
Kind: domain.MessageMediaKindService,
|
||||
ServiceAction: &domain.MessageServiceAction{
|
||||
Kind: domain.MessageServiceActionRequestedPeer,
|
||||
RequestedPeer: &domain.MessageRequestedPeerAction{
|
||||
ButtonID: button.ButtonID,
|
||||
Peers: peers,
|
||||
},
|
||||
},
|
||||
},
|
||||
Date: int(r.clock.Now().Unix()),
|
||||
OriginAuthKeyID: authKeyID,
|
||||
OriginSessionID: sessionID,
|
||||
RecipientBlocked: recipientBlocked,
|
||||
})
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
_ = r.deps.Bots.DeleteRequestedWebViewButton(ctx, botUser.ID, userID, webAppReqID)
|
||||
users := r.usersForMessageUpdate(ctx, userID, res.SenderMessage)
|
||||
chats := r.chatsForMessageUpdate(ctx, userID, res.SenderMessage)
|
||||
return tgPrivateMessageUpdates(res.SenderEvent, res.SenderMessage, 0, false, users, chats), nil
|
||||
}
|
||||
|
||||
func requestedPeerTypeMatches(kind string, peer domain.Peer) bool {
|
||||
switch kind {
|
||||
case "user", "":
|
||||
return peer.Type == domain.PeerTypeUser
|
||||
case "chat", "broadcast":
|
||||
return peer.Type == domain.PeerTypeChannel
|
||||
default:
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
func botRequestedPeerServiceMessageRandomID(userID, botUserID int64, reqID string, buttonID int, peers []domain.Peer) int64 {
|
||||
parts := []string{"bot-requested-peer", strconv.FormatInt(userID, 10), strconv.FormatInt(botUserID, 10), reqID, strconv.Itoa(buttonID)}
|
||||
for _, peer := range peers {
|
||||
parts = append(parts, string(peer.Type), strconv.FormatInt(peer.ID, 10))
|
||||
}
|
||||
return -stableBotAppInt64(parts...)
|
||||
}
|
||||
|
||||
func (r *Router) onMessagesGetPreparedInlineMessage(ctx context.Context, req *tg.MessagesGetPreparedInlineMessageRequest) (*tg.MessagesPreparedInlineMessage, error) {
|
||||
if req == nil {
|
||||
return nil, botInvalidErr()
|
||||
}
|
||||
if req.ID == "" {
|
||||
return nil, resultIDEmptyErr()
|
||||
}
|
||||
if len(req.ID) > domain.MaxBotPreparedInlineIDLen {
|
||||
return nil, resultIDInvalidErr()
|
||||
}
|
||||
userID, _, err := r.currentUserID(ctx)
|
||||
if err != nil {
|
||||
return nil, internalErr()
|
||||
}
|
||||
bot, err := r.botUserFromInput(ctx, userID, req.Bot)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
results, ok := r.inlines.preparedInlineContext(ctx, r.clock.Now(), userID, bot.ID, req.ID)
|
||||
if !ok || len(results.Results) != 1 {
|
||||
return nil, resultIDInvalidErr()
|
||||
}
|
||||
out := &tg.MessagesPreparedInlineMessage{
|
||||
QueryID: results.QueryID,
|
||||
Result: tgBotInlineResult(results.Results[0]),
|
||||
PeerTypes: tgPreparedInlinePeerTypes(results.PeerTypes),
|
||||
CacheTime: results.CacheTime,
|
||||
Users: []tg.UserClass{},
|
||||
}
|
||||
if r.deps.Users != nil {
|
||||
if u, found, err := r.deps.Users.ByID(ctx, userID, bot.ID); err == nil && found {
|
||||
out.Users = append(out.Users, r.tgUser(u))
|
||||
}
|
||||
}
|
||||
return out, nil
|
||||
}
|
||||
|
||||
func (r *Router) botUserFromInput(ctx context.Context, userID int64, bot tg.InputUserClass) (domain.User, error) {
|
||||
u, found, err := r.userFromInput(ctx, userID, bot)
|
||||
if err != nil {
|
||||
return domain.User{}, internalErr()
|
||||
}
|
||||
if !found || !u.Bot {
|
||||
return domain.User{}, botInvalidErr()
|
||||
}
|
||||
return u, nil
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue