package domain import ( "errors" "strings" "unicode/utf8" ) const ( MaxBusinessWorkHourIntervals = 28 MaxBusinessRecipientUsers = 100 MaxBusinessChatLinks = 100 MaxBusinessChatLinkMessage = MaxMessageTextLength MaxBusinessChatLinkTitle = 64 MaxQuickReplies = 100 MaxQuickReplyMessages = 20 MaxQuickReplyShortcutLength = 32 BusinessAwayCooldownSeconds = 24 * 60 * 60 ) var ( ErrBusinessProfileInvalid = errors.New("business profile invalid") ErrBusinessChatLinkInvalid = errors.New("business chat link invalid") ErrBusinessChatLinkNotFound = errors.New("business chat link not found") ErrBusinessChatLinksTooMuch = errors.New("business chat links too much") ErrBusinessRecipientsEmpty = errors.New("business recipients empty") ErrBotBusinessMissing = errors.New("bot business missing") ErrBotNotConnectedYet = errors.New("bot not connected yet") ErrBotAlreadyDisabled = errors.New("bot already disabled") ErrShortcutInvalid = errors.New("quick reply shortcut invalid") ErrShortcutOccupied = errors.New("quick reply shortcut occupied") ErrQuickRepliesTooMuch = errors.New("quick replies too much") ) type BusinessProfile struct { UserID int64 WorkHours *BusinessWorkHours Location *BusinessLocation Intro *BusinessIntro Greeting *BusinessGreetingMessage Away *BusinessAwayMessage UpdatedAtUnix int64 } type BusinessWeeklyOpen struct { StartMinute int EndMinute int } type BusinessWorkHours struct { TimezoneID string WeeklyOpen []BusinessWeeklyOpen OpenNow bool } type BusinessLocation struct { Address string Geo *GeoPoint } type GeoPoint struct { Lat float64 Long float64 } type BusinessIntro struct { Title string Description string StickerDocumentID int64 } type BusinessRecipients struct { ExistingChats bool NewChats bool Contacts bool NonContacts bool ExcludeSelected bool Users []int64 } type BusinessBotRights struct { Reply bool ReadMessages bool DeleteSentMessages bool DeleteReceivedMessages bool EditName bool EditBio bool EditProfilePhoto bool EditUsername bool ViewGifts bool SellGifts bool ChangeGiftSettings bool TransferAndUpgradeGifts bool TransferStars bool ManageStories bool } type BusinessBotRecipients struct { ExistingChats bool NewChats bool Contacts bool NonContacts bool ExcludeSelected bool Users []int64 ExcludeUsers []int64 } type ConnectedBusinessBot struct { OwnerUserID int64 BotUserID int64 Recipients BusinessBotRecipients Rights BusinessBotRights CreatedAtUnix int64 UpdatedAtUnix int64 } type ConnectedBusinessBotPeerState struct { OwnerUserID int64 PeerUserID int64 Paused bool Disabled bool UpdatedAtUnix int64 } type BusinessGreetingMessage struct { ShortcutID int Recipients BusinessRecipients NoActivityDays int } type BusinessAwayScheduleKind string const ( BusinessAwayScheduleAlways BusinessAwayScheduleKind = "always" BusinessAwayScheduleOutsideWorkHours BusinessAwayScheduleKind = "outside_work_hours" BusinessAwayScheduleCustom BusinessAwayScheduleKind = "custom" ) type BusinessAwaySchedule struct { Kind BusinessAwayScheduleKind StartDate int EndDate int } type BusinessAwayMessage struct { ShortcutID int Schedule BusinessAwaySchedule Recipients BusinessRecipients OfflineOnly bool } type BusinessAutomationKind string const ( BusinessAutomationGreeting BusinessAutomationKind = "greeting" BusinessAutomationAway BusinessAutomationKind = "away" BusinessAutomationAI BusinessAutomationKind = "ai" ) type BusinessAutomationDelivery struct { OwnerUserID int64 PeerUserID int64 Kind BusinessAutomationKind TriggerMessageID int ShortcutID int SentAt int } type BusinessChatLinkInput struct { Message string Entities []MessageEntity Title string } type BusinessChatLink struct { OwnerUserID int64 Slug string Link string Message string Entities []MessageEntity Title string Views int CreatedAt int64 UpdatedAt int64 } type QuickReply struct { OwnerUserID int64 ID int Shortcut string TopMessage int Count int SortOrder int CreatedAt int64 UpdatedAt int64 } type QuickReplyMessage struct { OwnerUserID int64 ShortcutID int ID int RandomID int64 Date int Message string Entities []MessageEntity } type QuickReplyList struct { OwnerUserID int64 QuickReplies []QuickReply Messages []QuickReplyMessage Hash int64 } type QuickReplyMessages struct { OwnerUserID int64 ShortcutID int Messages []QuickReplyMessage Count int Hash int64 } type QuickReplyMutationKind string const ( QuickReplyMutationList QuickReplyMutationKind = "list" QuickReplyMutationNew QuickReplyMutationKind = "new" QuickReplyMutationDelete QuickReplyMutationKind = "delete" QuickReplyMutationMessage QuickReplyMutationKind = "message" QuickReplyMutationIDs QuickReplyMutationKind = "ids" ) type QuickReplyMutation struct { Kind QuickReplyMutationKind List QuickReplyList QuickReply QuickReply ShortcutID int Message QuickReplyMessage MessageIDs []int Date int Pts int PtsCount int } func NormalizeBusinessChatLinkInput(in BusinessChatLinkInput) (BusinessChatLinkInput, error) { in.Message = strings.TrimSpace(in.Message) in.Title = strings.TrimSpace(in.Title) if in.Message == "" || utf8.RuneCountInString(in.Message) > MaxBusinessChatLinkMessage { return BusinessChatLinkInput{}, ErrBusinessChatLinkInvalid } if utf8.RuneCountInString(in.Title) > MaxBusinessChatLinkTitle { return BusinessChatLinkInput{}, ErrBusinessChatLinkInvalid } if len(in.Entities) > MaxMessageEntityCount { return BusinessChatLinkInput{}, ErrBusinessChatLinkInvalid } in.Entities = append([]MessageEntity(nil), in.Entities...) return in, nil } func NormalizeQuickReplyShortcut(shortcut string) (string, error) { shortcut = strings.TrimSpace(shortcut) if shortcut == "" || strings.ContainsAny(shortcut, "\r\n\t") || utf8.RuneCountInString(shortcut) > MaxQuickReplyShortcutLength { return "", ErrShortcutInvalid } return shortcut, nil } func BusinessBotRecipientsMatch(recipients BusinessBotRecipients, existingChat, isContact bool, userID int64) bool { selected := false if existingChat && recipients.ExistingChats { selected = true } if !existingChat && recipients.NewChats { selected = true } if isContact && recipients.Contacts { selected = true } if !isContact && recipients.NonContacts { selected = true } for _, id := range recipients.Users { if id == userID { selected = true break } } for _, id := range recipients.ExcludeUsers { if id == userID { if recipients.ExcludeSelected { selected = true break } return false } } if recipients.ExcludeSelected { return !selected } return selected }