mirror of
https://github.com/InsanusMokrassar/TelegramBotAPI.git
synced 2025-11-16 20:10:18 +00:00
Compare commits
57 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 32fe008eef | |||
| 2b938903b6 | |||
| 080db09d2c | |||
| 0efa52fe00 | |||
| fdf510153d | |||
| edb16d7107 | |||
| c49f400201 | |||
| db7de6edf8 | |||
| 10860e1bb2 | |||
| 46e6eeca9d | |||
| 80be86454d | |||
| d5f5a0e30b | |||
| 051210caf5 | |||
| 284fe58848 | |||
| 38c9732da5 | |||
| dee13c03ae | |||
| 6103b70a47 | |||
| 7f5cd0567b | |||
| af159b89b6 | |||
| efe286c181 | |||
| 821bb5b45c | |||
| c92ed92f7c | |||
| 88f6b349ea | |||
| 6c4afac8f8 | |||
| 6273990b00 | |||
| 1a1fd926dd | |||
| affa2a3a57 | |||
| 73a748d8b3 | |||
| fa4d264df4 | |||
| 1b1da33882 | |||
| ccfb774f33 | |||
| 5215e8a315 | |||
| 97a3901cb9 | |||
| 034e87a8ef | |||
| 156fbd72d4 | |||
| 8ec3e01737 | |||
| 1655bedabe | |||
| ac6b580a7e | |||
| c6692c2509 | |||
| 12846a68b9 | |||
| 21f5808b12 | |||
| 64244a60fe | |||
| 4cd7fdb436 | |||
| 6daf98d47d | |||
| c260597799 | |||
| d59e204002 | |||
| 117d891ff2 | |||
| 1e451af508 | |||
| 051f5e22e7 | |||
| 6873c23309 | |||
| a65971be00 | |||
| 4b5baaff8c | |||
| 0840d2e083 | |||
| 085a225eb4 | |||
| b575871a8e | |||
| c96e162845 | |||
| c471d59b3c |
51
CHANGELOG.md
51
CHANGELOG.md
@@ -1,5 +1,56 @@
|
||||
# TelegramBotAPI changelog
|
||||
|
||||
## 9.2.4
|
||||
|
||||
* `Utils`:
|
||||
* New extensions `*.parseCommandsWithNamedArgs`
|
||||
* `BehaviourBuilder`:
|
||||
* In expectaters and triggers of `commands` add `*WithNamedArgs` variants
|
||||
* In expectaters and triggers of `commands` add opportunity to use custom separator
|
||||
|
||||
## 9.2.3
|
||||
|
||||
* `Core`:
|
||||
* Fix in `VoiceContent#createResend`
|
||||
|
||||
## 9.2.2
|
||||
|
||||
* `Core`:
|
||||
* Fix of [#793](https://github.com/InsanusMokrassar/ktgbotapi/issues/793): Add `PreviewChat`
|
||||
|
||||
## 9.2.1
|
||||
|
||||
* `Version`:
|
||||
* `Ktor`: `2.3.3` -> `2.3.4`
|
||||
* `Core`:
|
||||
* All `ChatMember` inheritors have fixes `status` field
|
||||
|
||||
## 9.2.0
|
||||
|
||||
**Add support of [Telegram Bots API 6.9](https://core.telegram.org/bots/api-changelog#september-22-2023)**
|
||||
|
||||
* Rename `ChatAdministratorRightsImpl` -> `ChatCommonAdministratorRights`
|
||||
* All the request chat keyboards has changed their parameters `ChatAdministratorRights` to `ChatCommonAdministratorRights`
|
||||
|
||||
## 9.1.2
|
||||
|
||||
* `Core`:
|
||||
* Fix of `MessageContent` serialization
|
||||
|
||||
## 9.1.1
|
||||
|
||||
* `Core`:
|
||||
* Potential fix of incorrect parsing in `RawMessageEntity`
|
||||
|
||||
## 9.1.0
|
||||
|
||||
**This update contains adding of [Telegram Bot API 6.8](https://core.telegram.org/bots/api-changelog#august-18-2023) support**
|
||||
|
||||
* `Version`:
|
||||
* `Coroutines`: `1.7.2` -> `1.7.3`
|
||||
* `Ktor`: `2.3.2` -> `2.3.3`
|
||||
* `MicroUtils`: `0.19.7` -> `0.19.9`
|
||||
|
||||
## 9.0.0
|
||||
|
||||
**THIS UPDATE CONTAINS BREAKING CHANGES: USERNAMES OF BOTS NOW BECAME NULLABLE**
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
# TelegramBotAPI [](https://maven-badges.herokuapp.com/maven-central/dev.inmo/tgbotapi) [](https://core.telegram.org/bots/api-changelog#april-21-2023)
|
||||
# TelegramBotAPI [](https://maven-badges.herokuapp.com/maven-central/dev.inmo/tgbotapi) [](https://core.telegram.org/bots/api-changelog#september-22-2023)
|
||||
|
||||
| Docs | [](https://tgbotapi.inmo.dev/index.html) [](https://docs.inmo.dev/tgbotapi/index.html) |
|
||||
|:----------------------:|:-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------:|
|
||||
|
||||
@@ -54,8 +54,8 @@ Object callback = {
|
||||
skipDeprecated.set(true)
|
||||
|
||||
sourceLink {
|
||||
localDirectory.set(file("./"))
|
||||
remoteUrl.set(new URL("https://github.com/InsanusMokrassar/TelegramBotAPI/blob/master/"))
|
||||
localDirectory.set(file("../"))
|
||||
remoteUrl.set(new URL("https://github.com/InsanusMokrassar/ktgbotapi/tree/master"))
|
||||
remoteLineSuffix.set("#L")
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,4 +6,4 @@ kotlin.incremental=true
|
||||
kotlin.incremental.js=true
|
||||
|
||||
library_group=dev.inmo
|
||||
library_version=9.0.0
|
||||
library_version=9.2.4
|
||||
|
||||
@@ -2,18 +2,18 @@
|
||||
|
||||
kotlin = "1.8.22"
|
||||
kotlin-serialization = "1.5.1"
|
||||
kotlin-coroutines = "1.7.2"
|
||||
kotlin-coroutines = "1.7.3"
|
||||
|
||||
javax-activation = "1.1.1"
|
||||
|
||||
korlibs = "4.0.3"
|
||||
uuid = "0.7.1"
|
||||
ktor = "2.3.2"
|
||||
ktor = "2.3.4"
|
||||
|
||||
ksp = "1.8.22-1.0.11"
|
||||
kotlin-poet = "1.14.2"
|
||||
|
||||
microutils = "0.19.7"
|
||||
microutils = "0.19.9"
|
||||
|
||||
github-release-plugin = "2.4.1"
|
||||
dokka = "1.8.20"
|
||||
|
||||
2
gradle/wrapper/gradle-wrapper.properties
vendored
2
gradle/wrapper/gradle-wrapper.properties
vendored
@@ -2,4 +2,4 @@ distributionBase=GRADLE_USER_HOME
|
||||
distributionPath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
zipStorePath=wrapper/dists
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.6.2-bin.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.6.3-bin.zip
|
||||
|
||||
@@ -2,17 +2,17 @@ package dev.inmo.tgbotapi.extensions.api.bot
|
||||
|
||||
import dev.inmo.tgbotapi.bot.TelegramBot
|
||||
import dev.inmo.tgbotapi.requests.bot.SetMyDefaultAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatAdministratorRightsImpl
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatCommonAdministratorRights
|
||||
|
||||
suspend fun TelegramBot.setMyDefaultAdministratorRights(
|
||||
rights: ChatAdministratorRightsImpl,
|
||||
rights: ChatCommonAdministratorRights,
|
||||
forChannels: Boolean? = null
|
||||
) = execute(SetMyDefaultAdministratorRights(rights, forChannels))
|
||||
|
||||
suspend fun TelegramBot.setMyDefaultAdministratorRightsForChannels(
|
||||
rights: ChatAdministratorRightsImpl
|
||||
rights: ChatCommonAdministratorRights
|
||||
) = setMyDefaultAdministratorRights(rights, forChannels = true)
|
||||
|
||||
suspend fun TelegramBot.setMyDefaultAdministratorRightsForGroupsAndSupergroups(
|
||||
rights: ChatAdministratorRightsImpl
|
||||
rights: ChatCommonAdministratorRights
|
||||
) = setMyDefaultAdministratorRights(rights, forChannels = false)
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
package dev.inmo.tgbotapi.extensions.api.chat.forum
|
||||
|
||||
import dev.inmo.tgbotapi.bot.TelegramBot
|
||||
import dev.inmo.tgbotapi.requests.chat.forum.UnpinAllForumTopicMessages
|
||||
import dev.inmo.tgbotapi.requests.chat.forum.UnpinAllGeneralForumTopicMessages
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.ForumTopic
|
||||
import dev.inmo.tgbotapi.types.MessageThreadId
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
|
||||
suspend fun TelegramBot.unpinAllGeneralForumTopicMessages(
|
||||
chatId: ChatIdentifier
|
||||
) = execute(
|
||||
UnpinAllGeneralForumTopicMessages(
|
||||
chatId
|
||||
)
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.unpinAllGeneralForumTopicMessages(
|
||||
chat: Chat
|
||||
) = unpinAllGeneralForumTopicMessages(chat.id)
|
||||
@@ -0,0 +1,157 @@
|
||||
package dev.inmo.tgbotapi.extensions.api.chat.members
|
||||
|
||||
import dev.inmo.tgbotapi.bot.TelegramBot
|
||||
import dev.inmo.tgbotapi.requests.chat.members.PromoteChannelAdministrator
|
||||
import dev.inmo.tgbotapi.requests.chat.members.PromoteChatMember
|
||||
import dev.inmo.tgbotapi.types.IdChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.TelegramDate
|
||||
import dev.inmo.tgbotapi.types.UserId
|
||||
import dev.inmo.tgbotapi.types.chat.PublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
|
||||
suspend fun TelegramBot.promoteChannelAdministrator(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canPostMessages: Boolean? = null,
|
||||
canEditMessages: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = execute(
|
||||
PromoteChannelAdministrator(
|
||||
chatId = chatId,
|
||||
userId = userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteChannelAdministrator(
|
||||
chat: PublicChat,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canPostMessages: Boolean? = null,
|
||||
canEditMessages: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = promoteChannelAdministrator(
|
||||
chat.id,
|
||||
userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteChannelAdministrator(
|
||||
chatId: IdChatIdentifier,
|
||||
user: User,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canPostMessages: Boolean? = null,
|
||||
canEditMessages: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = promoteChannelAdministrator(
|
||||
chatId,
|
||||
user.id,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteChannelAdministrator(
|
||||
chat: PublicChat,
|
||||
user: User,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canPostMessages: Boolean? = null,
|
||||
canEditMessages: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = promoteChannelAdministrator(
|
||||
chat.id,
|
||||
user.id,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
@@ -0,0 +1,116 @@
|
||||
package dev.inmo.tgbotapi.extensions.api.chat.members
|
||||
|
||||
import dev.inmo.tgbotapi.bot.TelegramBot
|
||||
import dev.inmo.tgbotapi.requests.chat.members.PromoteChatMember
|
||||
import dev.inmo.tgbotapi.types.IdChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.TelegramDate
|
||||
import dev.inmo.tgbotapi.types.UserId
|
||||
import dev.inmo.tgbotapi.types.chat.PublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
|
||||
suspend fun TelegramBot.promoteChatAdministrator(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
) = execute(
|
||||
PromoteChatMember(
|
||||
chatId,
|
||||
userId,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat
|
||||
)
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteChatAdministrator(
|
||||
chat: PublicChat,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
) = promoteChatAdministrator(
|
||||
chat.id,
|
||||
userId,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteChatAdministrator(
|
||||
chatId: IdChatIdentifier,
|
||||
user: User,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
) = promoteChatAdministrator(
|
||||
chatId,
|
||||
user.id,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteChatAdministrator(
|
||||
chat: PublicChat,
|
||||
user: User,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
) = promoteChatAdministrator(
|
||||
chat.id,
|
||||
user.id,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat
|
||||
)
|
||||
@@ -1,14 +1,13 @@
|
||||
package dev.inmo.tgbotapi.extensions.api.chat.members
|
||||
|
||||
import dev.inmo.micro_utils.common.Warning
|
||||
import dev.inmo.tgbotapi.bot.TelegramBot
|
||||
import dev.inmo.tgbotapi.requests.chat.members.PromoteChatMember
|
||||
import dev.inmo.tgbotapi.types.IdChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.TelegramDate
|
||||
import dev.inmo.tgbotapi.types.UserId
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.chat.PublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
|
||||
@Warning("This method is too common. Use it with caution")
|
||||
suspend fun TelegramBot.promoteChatMember(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
@@ -24,27 +23,34 @@ suspend fun TelegramBot.promoteChatMember(
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null
|
||||
canManageTopics: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = execute(
|
||||
PromoteChatMember(
|
||||
chatId,
|
||||
userId,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canPostMessages,
|
||||
canEditMessages,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPinMessages,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat,
|
||||
canManageTopics
|
||||
chatId = chatId,
|
||||
userId = userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
)
|
||||
|
||||
@Warning("This method is too common. Use it with caution")
|
||||
suspend fun TelegramBot.promoteChatMember(
|
||||
chat: PublicChat,
|
||||
userId: UserId,
|
||||
@@ -60,25 +66,32 @@ suspend fun TelegramBot.promoteChatMember(
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null
|
||||
canManageTopics: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = promoteChatMember(
|
||||
chat.id,
|
||||
userId,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canPostMessages,
|
||||
canEditMessages,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPinMessages,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat,
|
||||
canManageTopics
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
|
||||
@Warning("This method is too common. Use it with caution")
|
||||
suspend fun TelegramBot.promoteChatMember(
|
||||
chatId: IdChatIdentifier,
|
||||
user: User,
|
||||
@@ -94,25 +107,32 @@ suspend fun TelegramBot.promoteChatMember(
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null
|
||||
canManageTopics: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = promoteChatMember(
|
||||
chatId,
|
||||
user.id,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canPostMessages,
|
||||
canEditMessages,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPinMessages,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat,
|
||||
canManageTopics
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
|
||||
@Warning("This method is too common. Use it with caution")
|
||||
suspend fun TelegramBot.promoteChatMember(
|
||||
chat: PublicChat,
|
||||
user: User,
|
||||
@@ -128,21 +148,27 @@ suspend fun TelegramBot.promoteChatMember(
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null
|
||||
canManageTopics: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = promoteChatMember(
|
||||
chat.id,
|
||||
user.id,
|
||||
untilDate,
|
||||
isAnonymous,
|
||||
canChangeInfo,
|
||||
canPostMessages,
|
||||
canEditMessages,
|
||||
canDeleteMessages,
|
||||
canInviteUsers,
|
||||
canRestrictMembers,
|
||||
canPinMessages,
|
||||
canPromoteMembers,
|
||||
canManageVideoChats,
|
||||
canManageChat,
|
||||
canManageTopics
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
|
||||
@@ -0,0 +1,133 @@
|
||||
package dev.inmo.tgbotapi.extensions.api.chat.members
|
||||
|
||||
import dev.inmo.tgbotapi.bot.TelegramBot
|
||||
import dev.inmo.tgbotapi.requests.chat.members.PromoteChatMember
|
||||
import dev.inmo.tgbotapi.requests.chat.members.PromoteSupergroupAdministrator
|
||||
import dev.inmo.tgbotapi.types.IdChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.TelegramDate
|
||||
import dev.inmo.tgbotapi.types.UserId
|
||||
import dev.inmo.tgbotapi.types.chat.PublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
|
||||
suspend fun TelegramBot.promoteSupergroupAdministrator(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPinMessages: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null,
|
||||
) = execute(
|
||||
PromoteSupergroupAdministrator(
|
||||
chatId = chatId,
|
||||
userId = userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics
|
||||
)
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteSupergroupAdministrator(
|
||||
chat: PublicChat,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPinMessages: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null,
|
||||
) = promoteSupergroupAdministrator(
|
||||
chat.id,
|
||||
userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteSupergroupAdministrator(
|
||||
chatId: IdChatIdentifier,
|
||||
user: User,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPinMessages: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null,
|
||||
) = promoteSupergroupAdministrator(
|
||||
chatId,
|
||||
user.id,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics
|
||||
)
|
||||
|
||||
suspend fun TelegramBot.promoteSupergroupAdministrator(
|
||||
chat: PublicChat,
|
||||
user: User,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPinMessages: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null,
|
||||
) = promoteSupergroupAdministrator(
|
||||
chat.id,
|
||||
user.id,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics
|
||||
)
|
||||
@@ -3,6 +3,10 @@ package dev.inmo.tgbotapi.extensions.behaviour_builder.expectations
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.BehaviourContext
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.handlers_registrar.doWithRegistration
|
||||
import dev.inmo.tgbotapi.extensions.utils.*
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.TelegramBotCommandsDefaults
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgs
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgsSources
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithNamedArgs
|
||||
import dev.inmo.tgbotapi.requests.abstracts.Request
|
||||
import dev.inmo.tgbotapi.types.BotCommand
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.CommonMessage
|
||||
@@ -79,35 +83,54 @@ fun Flow<CommonMessage<TextContent>>.requireCommandsWithoutParams() = filter {
|
||||
}
|
||||
|
||||
/**
|
||||
* Map the commands with their arguments and source messages
|
||||
* Uses [parseCommandsWithArgsSources] on incoming text sources and map them with [CommonMessage]
|
||||
*/
|
||||
fun Flow<CommonMessage<TextContent>>.commandsWithParams(): Flow<Pair<CommonMessage<TextContent>, List<Pair<BotCommandTextSource, Array<TextSource>>>>> = mapNotNull {
|
||||
var currentCommandTextSource: BotCommandTextSource? = null
|
||||
val currentArgs = mutableListOf<TextSource>()
|
||||
val result = mutableListOf<Pair<BotCommandTextSource, Array<TextSource>>>()
|
||||
|
||||
fun addCurrentCommandToResult() {
|
||||
currentCommandTextSource ?.let {
|
||||
result.add(it to currentArgs.toTypedArray())
|
||||
currentArgs.clear()
|
||||
}
|
||||
}
|
||||
|
||||
it.content.textSources.forEach {
|
||||
it.ifBotCommandTextSource {
|
||||
addCurrentCommandToResult()
|
||||
currentCommandTextSource = it
|
||||
return@forEach
|
||||
}
|
||||
currentArgs.add(it)
|
||||
}
|
||||
addCurrentCommandToResult()
|
||||
|
||||
result.toList().takeIf { it.isNotEmpty() } ?.let { result ->
|
||||
it to result
|
||||
}
|
||||
it to it.content.textSources.parseCommandsWithArgsSources().toList()
|
||||
}
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] on incoming text sources and map them with [CommonMessage]
|
||||
*/
|
||||
fun Flow<CommonMessage<TextContent>>.commandsWithArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
): Flow<Pair<CommonMessage<TextContent>, List<Pair<String, Array<String>>>>> = mapNotNull {
|
||||
val commandsWithArgs = it.content.textSources.parseCommandsWithArgs(argsSeparator).toList().ifEmpty {
|
||||
return@mapNotNull null
|
||||
}
|
||||
|
||||
it to commandsWithArgs
|
||||
}
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] on incoming text sources and map them with [CommonMessage]
|
||||
*/
|
||||
fun Flow<CommonMessage<TextContent>>.commandsWithArgs(
|
||||
argsSeparator: String
|
||||
): Flow<Pair<CommonMessage<TextContent>, List<Pair<String, Array<String>>>>> = commandsWithArgs(Regex(argsSeparator))
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithNamedArgs] on incoming text sources and map them with [CommonMessage]
|
||||
*/
|
||||
fun Flow<CommonMessage<TextContent>>.commandsWithNamedArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
): Flow<Pair<CommonMessage<TextContent>, List<Pair<String, List<Pair<String, String>>>>>> = mapNotNull {
|
||||
val commandsWithArgs = it.content.textSources.parseCommandsWithNamedArgs(argsSeparator, nameArgSeparator).toList().ifEmpty {
|
||||
return@mapNotNull null
|
||||
}
|
||||
|
||||
it to commandsWithArgs
|
||||
}
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithNamedArgs] on incoming text sources and map them with [CommonMessage]
|
||||
*/
|
||||
fun Flow<CommonMessage<TextContent>>.commandsWithNamedArgs(
|
||||
argsSeparator: String,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
): Flow<Pair<CommonMessage<TextContent>, List<Pair<String, List<Pair<String, String>>>>>> = commandsWithNamedArgs(Regex(argsSeparator), nameArgSeparator)
|
||||
|
||||
/**
|
||||
* Flat [commandsWithParams]. Each [Pair] of [BotCommandTextSource] and its [Array] of arg text sources will
|
||||
* be associated with its source message
|
||||
|
||||
@@ -62,6 +62,10 @@ suspend fun BehaviourContext.waitText(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitContent(initRequest, errorFactory).mapContent<TextContent>()
|
||||
suspend fun BehaviourContext.waitStory(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitContent(initRequest, errorFactory).mapContent<StoryContent>()
|
||||
suspend fun BehaviourContext.waitVenue(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
|
||||
@@ -74,6 +74,10 @@ suspend fun BehaviourContext.waitTextMessage(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitContentMessage(initRequest, errorFactory).mapWithContent<TextContent>()
|
||||
suspend fun BehaviourContext.waitStoryMessage(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitContentMessage(initRequest, errorFactory).mapWithContent<StoryContent>()
|
||||
suspend fun BehaviourContext.waitVenueMessage(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
|
||||
@@ -174,6 +174,25 @@ suspend fun BehaviourContext.waitWriteAccessAllowed(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEvents<WriteAccessAllowed>(initRequest, errorFactory)
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedFromRequest(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEvents<WriteAccessAllowed.FromRequest>(initRequest, errorFactory)
|
||||
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedFromAttachmentMenu(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEvents<WriteAccessAllowed.FromAttachmentMenu>(initRequest, errorFactory)
|
||||
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedFromWebAppLink(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEvents<WriteAccessAllowed.FromWebAppLink>(initRequest, errorFactory)
|
||||
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedOther(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEvents<WriteAccessAllowed.Other>(initRequest, errorFactory)
|
||||
|
||||
suspend fun BehaviourContext.waitChatSharedRequest(
|
||||
initRequest: Request<*>? = null,
|
||||
|
||||
@@ -171,6 +171,22 @@ suspend fun BehaviourContext.waitWriteAccessAllowedEventsMessages(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEventsMessages<WriteAccessAllowed>(initRequest, errorFactory)
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedFromRequestEventsMessages(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEventsMessages<WriteAccessAllowed.FromRequest>(initRequest, errorFactory)
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedFromAttachmentMenuEventsMessages(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEventsMessages<WriteAccessAllowed.FromAttachmentMenu>(initRequest, errorFactory)
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedFromWebAppLinkEventsMessages(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEventsMessages<WriteAccessAllowed.FromWebAppLink>(initRequest, errorFactory)
|
||||
suspend fun BehaviourContext.waitWriteAccessAllowedOtherEventsMessages(
|
||||
initRequest: Request<*>? = null,
|
||||
errorFactory: NullableRequestBuilder<*> = { null }
|
||||
) = waitEventsMessages<WriteAccessAllowed.Other>(initRequest, errorFactory)
|
||||
|
||||
suspend fun BehaviourContext.waitChatSharedRequestEventsMessages(
|
||||
initRequest: Request<*>? = null,
|
||||
|
||||
@@ -11,7 +11,9 @@ import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.marker_factories.ByC
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.marker_factories.MarkerFactory
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times
|
||||
import dev.inmo.tgbotapi.extensions.utils.botCommandTextSourceOrNull
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithParams
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.TelegramBotCommandsDefaults
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgs
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithNamedArgs
|
||||
import dev.inmo.tgbotapi.types.BotCommand
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.content.TextMessage
|
||||
@@ -124,6 +126,7 @@ suspend fun <BC : BehaviourContext> BC.commandWithArgs(
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, Array<String>>
|
||||
) = command(
|
||||
commandRegex,
|
||||
@@ -132,7 +135,7 @@ suspend fun <BC : BehaviourContext> BC.commandWithArgs(
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory
|
||||
) {
|
||||
val args = it.parseCommandsWithParams().let { commandsWithArgs ->
|
||||
val args = it.parseCommandsWithArgs(argsSeparator = argsSeparator).let { commandsWithArgs ->
|
||||
val key = commandsWithArgs.keys.firstOrNull { it.matches(commandRegex) } ?: return@let null
|
||||
commandsWithArgs[key]
|
||||
} ?: emptyArray()
|
||||
@@ -144,12 +147,14 @@ suspend fun <BC : BehaviourContext> BC.commandWithArgs(
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, Array<String>>
|
||||
) = commandWithArgs(
|
||||
command.toRegex(),
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
@@ -158,12 +163,72 @@ suspend fun <BC : BehaviourContext> BC.commandWithArgs(
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, Array<String>>
|
||||
) = commandWithArgs(
|
||||
botCommand.command,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.commandWithNamedArgs(
|
||||
commandRegex: Regex,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, List<Pair<String, String>>>
|
||||
) = command(
|
||||
commandRegex,
|
||||
requireOnlyCommandInMessage = false,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory
|
||||
) {
|
||||
val args = it.parseCommandsWithNamedArgs(argsSeparator = argsSeparator, nameArgSeparator = nameArgSeparator).let { commandsWithArgs ->
|
||||
val key = commandsWithArgs.keys.firstOrNull { it.matches(commandRegex) } ?: return@let null
|
||||
commandsWithArgs[key]
|
||||
} ?: emptyList()
|
||||
scenarioReceiver(it, args)
|
||||
}
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.commandWithNamedArgs(
|
||||
command: String,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, List<Pair<String, String>>>
|
||||
) = commandWithNamedArgs(
|
||||
command.toRegex(),
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
nameArgSeparator = nameArgSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.commandWithNamedArgs(
|
||||
botCommand: BotCommand,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, List<Pair<String, String>>>
|
||||
) = commandWithNamedArgs(
|
||||
botCommand.command,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
nameArgSeparator = nameArgSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
@@ -172,21 +237,99 @@ suspend fun <BC : BehaviourContext> BC.onCommandWithArgs(
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, Array<String>>
|
||||
): Job = commandWithArgs(commandRegex, initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
): Job = commandWithArgs(
|
||||
commandRegex = commandRegex,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.onCommandWithArgs(
|
||||
command: String,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, Array<String>>
|
||||
): Job = onCommandWithArgs(command.toRegex(), initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
): Job = onCommandWithArgs(
|
||||
commandRegex = command.toRegex(),
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.onCommandWithArgs(
|
||||
botCommand: BotCommand,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, Array<String>>
|
||||
): Job = onCommandWithArgs(botCommand.command, initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
): Job = onCommandWithArgs(
|
||||
command = botCommand.command,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.onCommandWithNamedArgs(
|
||||
commandRegex: Regex,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, List<Pair<String, String>>>
|
||||
) = commandWithNamedArgs(
|
||||
commandRegex,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
nameArgSeparator = nameArgSeparator,
|
||||
scenarioReceiver = scenarioReceiver,
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.onCommandWithNamedArgs(
|
||||
command: String,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, List<Pair<String, String>>>
|
||||
) = onCommandWithNamedArgs(
|
||||
command.toRegex(),
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
nameArgSeparator = nameArgSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
suspend fun <BC : BehaviourContext> BC.onCommandWithNamedArgs(
|
||||
botCommand: BotCommand,
|
||||
initialFilter: CommonMessageFilter<TextContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, TextMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in TextMessage, Any> = ByChatMessageMarkerFactory,
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
scenarioReceiver: CustomBehaviourContextAndTwoTypesReceiver<BC, Unit, TextMessage, List<Pair<String, String>>>
|
||||
) = onCommandWithNamedArgs(
|
||||
botCommand.command,
|
||||
initialFilter = initialFilter,
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory,
|
||||
argsSeparator = argsSeparator,
|
||||
nameArgSeparator = nameArgSeparator,
|
||||
scenarioReceiver = scenarioReceiver
|
||||
)
|
||||
|
||||
@@ -9,7 +9,7 @@ import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.marker_factories.ByC
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.marker_factories.MarkerFactory
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times
|
||||
import dev.inmo.tgbotapi.extensions.utils.botCommandTextSourceOrNull
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithParams
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgs
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.content.TextMessage
|
||||
import dev.inmo.tgbotapi.types.update.abstracts.Update
|
||||
@@ -65,7 +65,7 @@ suspend fun <BC : BehaviourContext> BC.unhandledCommandWithArgs(
|
||||
subcontextUpdatesFilter = subcontextUpdatesFilter,
|
||||
markerFactory = markerFactory
|
||||
) {
|
||||
val args = it.parseCommandsWithParams().let { commandsWithArgs ->
|
||||
val args = it.parseCommandsWithArgs().let { commandsWithArgs ->
|
||||
commandsWithArgs
|
||||
}
|
||||
scenarioReceiver(it, args)
|
||||
|
||||
@@ -248,6 +248,30 @@ suspend fun <BC : BehaviourContext> BC.onText(
|
||||
scenarioReceiver
|
||||
)
|
||||
|
||||
/**
|
||||
* @param initialFilter This filter will be called to remove unnecessary data BEFORE [scenarioReceiver] call
|
||||
* @param subcontextUpdatesFilter This filter will be applied to each update inside of [scenarioReceiver]. For example,
|
||||
* this filter will be used if you will call [dev.inmo.tgbotapi.extensions.behaviour_builder.expectations.waitContentMessage].
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.BehaviourContextAndTwoTypesReceiver] function to create your own.
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.plus] or [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times]
|
||||
* to combinate several filters
|
||||
* @param [markerFactory] Will be used to identify different "stream". [scenarioReceiver] will be called synchronously
|
||||
* in one "stream". Output of [markerFactory] will be used as a key for "stream"
|
||||
* @param scenarioReceiver Main callback which will be used to handle incoming data if [initialFilter] will pass that
|
||||
* data
|
||||
*/
|
||||
suspend fun <BC : BehaviourContext> BC.onStory(
|
||||
initialFilter: CommonMessageFilter<StoryContent>? = CommonMessageFilterExcludeMediaGroups,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, StoryMessage, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in StoryMessage, Any> = ByChatMessageMarkerFactory,
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, StoryMessage>
|
||||
) = onContentMessageWithType(
|
||||
initialFilter,
|
||||
subcontextUpdatesFilter,
|
||||
markerFactory,
|
||||
scenarioReceiver
|
||||
)
|
||||
|
||||
/**
|
||||
* @param initialFilter This filter will be called to remove unnecessary data BEFORE [scenarioReceiver] call
|
||||
* @param subcontextUpdatesFilter This filter will be applied to each update inside of [scenarioReceiver]. For example,
|
||||
|
||||
@@ -4,22 +4,18 @@ package dev.inmo.tgbotapi.extensions.behaviour_builder.triggers_handling
|
||||
|
||||
import dev.inmo.micro_utils.coroutines.*
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.*
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.expectations.waitDeepLinks
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.filters.CommonMessageFilterExcludeMediaGroups
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.filters.MessageFilterByChat
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.SimpleFilter
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.marker_factories.ByChatMessageMarkerFactory
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.marker_factories.MarkerFactory
|
||||
import dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times
|
||||
import dev.inmo.tgbotapi.extensions.utils.*
|
||||
import dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithParams
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.content.TextMessage
|
||||
import dev.inmo.tgbotapi.types.message.textsources.RegularTextSource
|
||||
import dev.inmo.tgbotapi.types.update.abstracts.Update
|
||||
import io.ktor.http.decodeURLQueryComponent
|
||||
import kotlinx.coroutines.Job
|
||||
import kotlinx.coroutines.flow.filter
|
||||
|
||||
private val startRegex = Regex("start")
|
||||
suspend fun <BC : BehaviourContext> BC.onDeepLink(
|
||||
|
||||
@@ -655,10 +655,90 @@ suspend fun <BC : BehaviourContext> BC.onGeneralForumTopicUnhidden(
|
||||
* data
|
||||
*/
|
||||
suspend fun <BC : BehaviourContext> BC.onWriteAccessAllowed(
|
||||
initialFilter: SimpleFilter<SupergroupEventMessage<WriteAccessAllowed>>? = null,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, SupergroupEventMessage<WriteAccessAllowed>, Update>? = MessageFilterByChat,
|
||||
initialFilter: SimpleFilter<ChatEventMessage<WriteAccessAllowed>>? = null,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, ChatEventMessage<WriteAccessAllowed>, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in ChatEventMessage<WriteAccessAllowed>, Any> = ByChatMessageMarkerFactory,
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, SupergroupEventMessage<WriteAccessAllowed>>
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, ChatEventMessage<WriteAccessAllowed>>
|
||||
) = onEventWithCustomChatEventMessage(initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
|
||||
|
||||
/**
|
||||
* @param initialFilter This filter will be called to remove unnecessary data BEFORE [scenarioReceiver] call
|
||||
* @param subcontextUpdatesFilter This filter will be applied to each update inside of [scenarioReceiver]. For example,
|
||||
* this filter will be used if you will call [dev.inmo.tgbotapi.extensions.behaviour_builder.expectations.waitContentMessage].
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.BehaviourContextAndTwoTypesReceiver] function to create your own.
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.plus] or [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times]
|
||||
* to combinate several filters
|
||||
* @param markerFactory Will be used to identify different "stream". [scenarioReceiver] will be called synchronously
|
||||
* in one "stream". Output of [markerFactory] will be used as a key for "stream"
|
||||
* @param scenarioReceiver Main callback which will be used to handle incoming data if [initialFilter] will pass that
|
||||
* data
|
||||
*/
|
||||
suspend fun <BC : BehaviourContext> BC.onWriteAccessAllowedFromRequest(
|
||||
initialFilter: SimpleFilter<ChatEventMessage<WriteAccessAllowed.FromRequest>>? = null,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, ChatEventMessage<WriteAccessAllowed.FromRequest>, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in ChatEventMessage<WriteAccessAllowed.FromRequest>, Any> = ByChatMessageMarkerFactory,
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, ChatEventMessage<WriteAccessAllowed.FromRequest>>
|
||||
) = onEventWithCustomChatEventMessage(initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
|
||||
|
||||
/**
|
||||
* @param initialFilter This filter will be called to remove unnecessary data BEFORE [scenarioReceiver] call
|
||||
* @param subcontextUpdatesFilter This filter will be applied to each update inside of [scenarioReceiver]. For example,
|
||||
* this filter will be used if you will call [dev.inmo.tgbotapi.extensions.behaviour_builder.expectations.waitContentMessage].
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.BehaviourContextAndTwoTypesReceiver] function to create your own.
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.plus] or [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times]
|
||||
* to combinate several filters
|
||||
* @param markerFactory Will be used to identify different "stream". [scenarioReceiver] will be called synchronously
|
||||
* in one "stream". Output of [markerFactory] will be used as a key for "stream"
|
||||
* @param scenarioReceiver Main callback which will be used to handle incoming data if [initialFilter] will pass that
|
||||
* data
|
||||
*/
|
||||
suspend fun <BC : BehaviourContext> BC.onWriteAccessAllowedFromAttachmentMenu(
|
||||
initialFilter: SimpleFilter<ChatEventMessage<WriteAccessAllowed.FromAttachmentMenu>>? = null,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, ChatEventMessage<WriteAccessAllowed.FromAttachmentMenu>, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in ChatEventMessage<WriteAccessAllowed.FromAttachmentMenu>, Any> = ByChatMessageMarkerFactory,
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, ChatEventMessage<WriteAccessAllowed.FromAttachmentMenu>>
|
||||
) = onEventWithCustomChatEventMessage(initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
|
||||
|
||||
/**
|
||||
* @param initialFilter This filter will be called to remove unnecessary data BEFORE [scenarioReceiver] call
|
||||
* @param subcontextUpdatesFilter This filter will be applied to each update inside of [scenarioReceiver]. For example,
|
||||
* this filter will be used if you will call [dev.inmo.tgbotapi.extensions.behaviour_builder.expectations.waitContentMessage].
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.BehaviourContextAndTwoTypesReceiver] function to create your own.
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.plus] or [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times]
|
||||
* to combinate several filters
|
||||
* @param markerFactory Will be used to identify different "stream". [scenarioReceiver] will be called synchronously
|
||||
* in one "stream". Output of [markerFactory] will be used as a key for "stream"
|
||||
* @param scenarioReceiver Main callback which will be used to handle incoming data if [initialFilter] will pass that
|
||||
* data
|
||||
*/
|
||||
suspend fun <BC : BehaviourContext> BC.onWriteAccessAllowedOther(
|
||||
initialFilter: SimpleFilter<ChatEventMessage<WriteAccessAllowed.Other>>? = null,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, ChatEventMessage<WriteAccessAllowed.Other>, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in ChatEventMessage<WriteAccessAllowed.Other>, Any> = ByChatMessageMarkerFactory,
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, ChatEventMessage<WriteAccessAllowed.Other>>
|
||||
) = onEventWithCustomChatEventMessage(initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
|
||||
|
||||
/**
|
||||
* @param initialFilter This filter will be called to remove unnecessary data BEFORE [scenarioReceiver] call
|
||||
* @param subcontextUpdatesFilter This filter will be applied to each update inside of [scenarioReceiver]. For example,
|
||||
* this filter will be used if you will call [dev.inmo.tgbotapi.extensions.behaviour_builder.expectations.waitContentMessage].
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.BehaviourContextAndTwoTypesReceiver] function to create your own.
|
||||
* Use [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.plus] or [dev.inmo.tgbotapi.extensions.behaviour_builder.utils.times]
|
||||
* to combinate several filters
|
||||
* @param markerFactory Will be used to identify different "stream". [scenarioReceiver] will be called synchronously
|
||||
* in one "stream". Output of [markerFactory] will be used as a key for "stream"
|
||||
* @param scenarioReceiver Main callback which will be used to handle incoming data if [initialFilter] will pass that
|
||||
* data
|
||||
*/
|
||||
suspend fun <BC : BehaviourContext> BC.onWriteAccessAllowedFromWebAppLink(
|
||||
initialFilter: SimpleFilter<ChatEventMessage<WriteAccessAllowed.FromWebAppLink>>? = null,
|
||||
subcontextUpdatesFilter: CustomBehaviourContextAndTwoTypesReceiver<BC, Boolean, ChatEventMessage<WriteAccessAllowed.FromWebAppLink>, Update>? = MessageFilterByChat,
|
||||
markerFactory: MarkerFactory<in ChatEventMessage<WriteAccessAllowed.FromWebAppLink>, Any> = ByChatMessageMarkerFactory,
|
||||
scenarioReceiver: CustomBehaviourContextAndTypeReceiver<BC, Unit, ChatEventMessage<WriteAccessAllowed.FromWebAppLink>>
|
||||
) = onEventWithCustomChatEventMessage(initialFilter, subcontextUpdatesFilter, markerFactory, scenarioReceiver)
|
||||
|
||||
|
||||
|
||||
@@ -1,10 +1,17 @@
|
||||
package dev.inmo.tgbotapi.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
|
||||
/**
|
||||
* All inheritors of this interface have [chat] field and related to this [chat]
|
||||
*/
|
||||
interface WithChat {
|
||||
val chat: Chat
|
||||
interface WithPreviewChat {
|
||||
val chat: PreviewChat
|
||||
}
|
||||
|
||||
/**
|
||||
* All inheritors of this interface have [chat] field and related to this [chat]
|
||||
*/
|
||||
@Deprecated("Renamed", ReplaceWith("WithPreviewChat", "dev.inmo.tgbotapi.abstracts.WithPreviewChat"))
|
||||
typealias WithChat = WithPreviewChat
|
||||
|
||||
@@ -2,14 +2,14 @@ package dev.inmo.tgbotapi.requests.bot
|
||||
|
||||
import dev.inmo.tgbotapi.requests.abstracts.SimpleRequest
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatAdministratorRightsImpl
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatCommonAdministratorRights
|
||||
import kotlinx.serialization.*
|
||||
import kotlinx.serialization.builtins.serializer
|
||||
|
||||
@Serializable
|
||||
class SetMyDefaultAdministratorRights(
|
||||
@SerialName(rightsField)
|
||||
val rights: ChatAdministratorRightsImpl,
|
||||
val rights: ChatCommonAdministratorRights,
|
||||
@SerialName(forChannelsField)
|
||||
val forChannels: Boolean? = null
|
||||
) : SimpleRequest<Boolean> {
|
||||
|
||||
@@ -0,0 +1,14 @@
|
||||
package dev.inmo.tgbotapi.requests.chat.forum
|
||||
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import kotlinx.serialization.*
|
||||
|
||||
@Serializable
|
||||
data class UnpinAllGeneralForumTopicMessages (
|
||||
@SerialName(chatIdField)
|
||||
override val chatId: ChatIdentifier,
|
||||
): ModifyForumRequest {
|
||||
override fun method(): String = "unpinAllGeneralForumTopicMessages"
|
||||
override val requestSerializer: SerializationStrategy<*>
|
||||
get() = serializer()
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
package dev.inmo.tgbotapi.requests.chat.members
|
||||
|
||||
import dev.inmo.micro_utils.common.Warning
|
||||
import dev.inmo.tgbotapi.abstracts.types.UntilDate
|
||||
import dev.inmo.tgbotapi.requests.chat.abstracts.ChatMemberRequest
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
@@ -7,6 +8,7 @@ import kotlinx.serialization.*
|
||||
import kotlinx.serialization.builtins.serializer
|
||||
|
||||
@Serializable
|
||||
@Warning("This method is too common. Use it with caution")
|
||||
data class PromoteChatMember(
|
||||
@SerialName(chatIdField)
|
||||
override val chatId: ChatIdentifier,
|
||||
@@ -37,7 +39,13 @@ data class PromoteChatMember(
|
||||
@SerialName(canManageChatField)
|
||||
private val canManageChat: Boolean? = null,
|
||||
@SerialName(canManageTopicsField)
|
||||
private val canManageTopics: Boolean? = null
|
||||
private val canManageTopics: Boolean? = null,
|
||||
@SerialName(canPostStoriesField)
|
||||
private val canPostStories: Boolean? = null,
|
||||
@SerialName(canEditStoriesField)
|
||||
private val canEditStories: Boolean? = null,
|
||||
@SerialName(canDeleteStoriesField)
|
||||
private val canDeleteStories: Boolean? = null
|
||||
) : ChatMemberRequest<Boolean>, UntilDate {
|
||||
override fun method(): String = "promoteChatMember"
|
||||
override val resultDeserializer: DeserializationStrategy<Boolean>
|
||||
@@ -45,3 +53,109 @@ data class PromoteChatMember(
|
||||
override val requestSerializer: SerializationStrategy<*>
|
||||
get() = serializer()
|
||||
}
|
||||
|
||||
fun PromoteChatMember(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
) = PromoteChatMember(
|
||||
chatId = chatId,
|
||||
userId = userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = null,
|
||||
canEditMessages = null,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = null,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = null,
|
||||
canPostStories = null,
|
||||
canEditStories = null,
|
||||
canDeleteStories = null
|
||||
)
|
||||
|
||||
fun PromoteChannelAdministrator(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canPostMessages: Boolean? = null,
|
||||
canEditMessages: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canPostStories: Boolean? = null,
|
||||
canEditStories: Boolean? = null,
|
||||
canDeleteStories: Boolean? = null
|
||||
) = PromoteChatMember(
|
||||
chatId = chatId,
|
||||
userId = userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = null,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = null,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
|
||||
fun PromoteSupergroupAdministrator(
|
||||
chatId: ChatIdentifier,
|
||||
userId: UserId,
|
||||
untilDate: TelegramDate? = null,
|
||||
isAnonymous: Boolean? = null,
|
||||
canChangeInfo: Boolean? = null,
|
||||
canDeleteMessages: Boolean? = null,
|
||||
canInviteUsers: Boolean? = null,
|
||||
canRestrictMembers: Boolean? = null,
|
||||
canPinMessages: Boolean? = null,
|
||||
canPromoteMembers: Boolean? = null,
|
||||
canManageVideoChats: Boolean? = null,
|
||||
canManageChat: Boolean? = null,
|
||||
canManageTopics: Boolean? = null,
|
||||
) = PromoteChatMember(
|
||||
chatId = chatId,
|
||||
userId = userId,
|
||||
untilDate = untilDate,
|
||||
isAnonymous = isAnonymous,
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = null,
|
||||
canEditMessages = null,
|
||||
canDeleteMessages = canDeleteMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
canManageTopics = canManageTopics,
|
||||
canPostStories = null,
|
||||
canEditStories = null,
|
||||
canDeleteStories = null
|
||||
)
|
||||
|
||||
@@ -177,6 +177,11 @@ val stickerKeywordLengthLimit = 0 .. 64
|
||||
|
||||
const val botActionActualityTime: Seconds = 5
|
||||
|
||||
val cloudStorageKeyLimit = 1 .. 128
|
||||
val cloudStorageValueLimit = 0 .. 4096
|
||||
val cloudStorageKeyRegex = Regex("[A-Za-z0-9_-]{${cloudStorageKeyLimit.first},${cloudStorageKeyLimit.last}}")
|
||||
val cloudStorageValueRegex = Regex(".{${cloudStorageValueLimit.first},${cloudStorageValueLimit.last}}")
|
||||
|
||||
// Made as lazy for correct work in K/JS
|
||||
val telegramInlineModeGifPermittedMimeTypes by lazy {
|
||||
listOf(
|
||||
@@ -210,10 +215,12 @@ const val firstNameField = "first_name"
|
||||
const val lastNameField = "last_name"
|
||||
const val languageCodeField = "language_code"
|
||||
const val addedToAttachmentMenuField = "added_to_attachment_menu"
|
||||
const val allowsWriteToPMField = "allows_write_to_pm"
|
||||
const val isPremiumField = "is_premium"
|
||||
const val hasPrivateForwardsField = "has_private_forwards"
|
||||
const val hasRestrictedVoiceAndVideoMessagesField = "has_restricted_voice_and_video_messages"
|
||||
const val emojiStatusCustomEmojiIdField = "emoji_status_custom_emoji_id"
|
||||
const val emojiStatusExpirationDateField = "emoji_status_expiration_date"
|
||||
const val iconCustomEmojiIdField = "icon_custom_emoji_id"
|
||||
const val canJoinGroupsField = "can_join_groups"
|
||||
const val canReadAllGroupMessagesField = "can_read_all_group_messages"
|
||||
@@ -273,6 +280,9 @@ const val correctOptionIdField = "correct_option_id"
|
||||
const val allowsMultipleAnswersField = "allows_multiple_answers"
|
||||
const val isAnonymousField = "is_anonymous"
|
||||
const val canManageTopicsField = "can_manage_topics"
|
||||
const val canPostStoriesField = "can_post_stories"
|
||||
const val canEditStoriesField = "can_edit_stories"
|
||||
const val canDeleteStoriesField = "can_delete_stories"
|
||||
const val captionEntitiesField = "caption_entities"
|
||||
const val hasSpoilerField = "has_spoiler"
|
||||
const val loginUrlField = "login_url"
|
||||
@@ -289,6 +299,7 @@ const val pinnedMessageField = "pinned_message"
|
||||
const val activeUsernamesField = "active_usernames"
|
||||
const val customTitleField = "custom_title"
|
||||
const val optionIdsField = "option_ids"
|
||||
const val voterChatField = "voter_chat"
|
||||
const val ipAddressField = "ip_address"
|
||||
const val linkedChatIdField = "linked_chat_id"
|
||||
const val hasHiddenMembersField = "has_hidden_members"
|
||||
|
||||
@@ -2,7 +2,7 @@ package dev.inmo.tgbotapi.types.buttons
|
||||
|
||||
import dev.inmo.tgbotapi.types.botAdministratorRightsField
|
||||
import dev.inmo.tgbotapi.types.botIsMemberField
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatCommonAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.chatHasUsernameField
|
||||
import dev.inmo.tgbotapi.types.chatIsChannelField
|
||||
import dev.inmo.tgbotapi.types.chatIsCreatedField
|
||||
@@ -30,9 +30,9 @@ data class KeyboardButtonRequestChat(
|
||||
@SerialName(chatIsCreatedField)
|
||||
val isOwnedBy: Boolean? = null,
|
||||
@SerialName(userAdministratorRightsField)
|
||||
val userRightsInChat: ChatAdministratorRights? = null,
|
||||
val userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
@SerialName(botAdministratorRightsField)
|
||||
val botRightsInChat: ChatAdministratorRights? = null,
|
||||
val botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
@SerialName(botIsMemberField)
|
||||
val botIsMember: Boolean? = null
|
||||
) {
|
||||
@@ -41,8 +41,8 @@ data class KeyboardButtonRequestChat(
|
||||
requestId: RequestId,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean? = null
|
||||
) = KeyboardButtonRequestChat(
|
||||
requestId = requestId,
|
||||
@@ -60,8 +60,8 @@ data class KeyboardButtonRequestChat(
|
||||
isForum: Boolean? = null,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean? = null
|
||||
) = KeyboardButtonRequestChat(
|
||||
requestId = requestId,
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
package dev.inmo.tgbotapi.types.buttons.reply
|
||||
|
||||
import dev.inmo.tgbotapi.types.buttons.*
|
||||
import dev.inmo.tgbotapi.types.buttons.InlineKeyboardButtons.*
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatCommonAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.request.RequestId
|
||||
import dev.inmo.tgbotapi.types.webapps.WebAppInfo
|
||||
|
||||
@@ -120,8 +119,8 @@ inline fun requestChatReplyButton(
|
||||
isForum: Boolean? = null,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean = false
|
||||
) = requestChatReplyButton(
|
||||
text,
|
||||
@@ -145,8 +144,8 @@ inline fun requestChannelReplyButton(
|
||||
requestId: RequestId,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean = false
|
||||
) = requestChatReplyButton(
|
||||
text,
|
||||
@@ -170,8 +169,8 @@ inline fun requestChannelReplyButton(
|
||||
isForum: Boolean? = null,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean? = null
|
||||
) = requestChatReplyButton(
|
||||
text,
|
||||
|
||||
@@ -4,51 +4,51 @@ import dev.inmo.tgbotapi.utils.internal.ClassCastsIncluded
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface UsernameChat : Chat {
|
||||
val username: Username?
|
||||
}
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface PrivateChat : Chat, UsernameChat {
|
||||
override val id: UserId
|
||||
val firstName: String
|
||||
val lastName: String
|
||||
}
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface PublicChat : Chat {
|
||||
val title: String
|
||||
}
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface SuperPublicChat : PublicChat, UsernameChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface ChannelChat : SuperPublicChat {
|
||||
override val id: ChatId
|
||||
}
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface GroupChat : PublicChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface SupergroupChat : GroupChat, SuperPublicChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface ForumChat : SupergroupChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface PossiblyPremiumChat : Chat {
|
||||
val isPremium: Boolean
|
||||
}
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
sealed interface AbleToAddInAttachmentMenuChat : Chat {
|
||||
val addedToAttachmentMenu: Boolean
|
||||
}
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
@Serializable(ChatSerializer::class)
|
||||
@ClassCastsIncluded(excludeRegex = ".*Impl")
|
||||
sealed interface Chat {
|
||||
val id: IdChatIdentifier
|
||||
|
||||
@@ -49,13 +49,54 @@ object ChatTypeSerializer : KSerializer<ChatType> {
|
||||
}
|
||||
|
||||
@RiskFeature
|
||||
object PreviewChatSerializer : KSerializer<Chat> {
|
||||
object ChatSerializer : KSerializer<Chat> {
|
||||
@OptIn(InternalSerializationApi::class)
|
||||
override val descriptor: SerialDescriptor = buildSerialDescriptor("PreviewChatSerializer", PolymorphicKind.OPEN)
|
||||
|
||||
override fun deserialize(decoder: Decoder): Chat {
|
||||
val decodedJson = JsonObject.serializer().deserialize(decoder)
|
||||
|
||||
return try {
|
||||
formatter.decodeFromJsonElement(ExtendedChatSerializer, decodedJson)
|
||||
} catch (e: SerializationException) {
|
||||
val type = decodedJson[typeField] ?.jsonPrimitive ?.content ?.asChatType ?: error("Field $typeField must be presented, but absent in $decodedJson")
|
||||
val isForum = decodedJson[isForumField] ?.jsonPrimitive ?.booleanOrNull == true
|
||||
|
||||
when (type) {
|
||||
ChatType.PrivateChatType -> formatter.decodeFromJsonElement(PrivateChatImpl.serializer(), decodedJson)
|
||||
ChatType.GroupChatType -> formatter.decodeFromJsonElement(GroupChatImpl.serializer(), decodedJson)
|
||||
ChatType.SupergroupChatType -> if (isForum) {
|
||||
formatter.decodeFromJsonElement(ForumChatImpl.serializer(), decodedJson)
|
||||
} else {
|
||||
formatter.decodeFromJsonElement(SupergroupChatImpl.serializer(), decodedJson)
|
||||
}
|
||||
ChatType.ChannelChatType -> formatter.decodeFromJsonElement(ChannelChatImpl.serializer(), decodedJson)
|
||||
is ChatType.UnknownChatType -> UnknownChatType(
|
||||
formatter.decodeFromJsonElement(Long.serializer(), decodedJson[chatIdField] ?: JsonPrimitive(-1)).toChatId(),
|
||||
decodedJson.toString(),
|
||||
decodedJson
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun serialize(encoder: Encoder, value: Chat) {
|
||||
when (value) {
|
||||
is ExtendedChat -> ExtendedChatSerializer.serialize(encoder, value)
|
||||
is PreviewChat -> PreviewChatSerializer.serialize(encoder, value)
|
||||
is ExtendedBot -> ExtendedBot.serializer().serialize(encoder, value)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@RiskFeature
|
||||
object PreviewChatSerializer : KSerializer<PreviewChat> {
|
||||
@OptIn(InternalSerializationApi::class)
|
||||
override val descriptor: SerialDescriptor = buildSerialDescriptor("PreviewChatSerializer", PolymorphicKind.OPEN)
|
||||
|
||||
override fun deserialize(decoder: Decoder): PreviewChat {
|
||||
val decodedJson = JsonObject.serializer().deserialize(decoder)
|
||||
|
||||
val type = decodedJson[typeField] ?.jsonPrimitive ?.content ?.asChatType ?: error("Field $typeField must be presented, but absent in $decodedJson")
|
||||
val isForum = decodedJson[isForumField] ?.jsonPrimitive ?.booleanOrNull == true
|
||||
|
||||
@@ -76,16 +117,14 @@ object PreviewChatSerializer : KSerializer<Chat> {
|
||||
}
|
||||
}
|
||||
|
||||
override fun serialize(encoder: Encoder, value: Chat) {
|
||||
override fun serialize(encoder: Encoder, value: PreviewChat) {
|
||||
when (value) {
|
||||
is ExtendedChat -> ExtendedChatSerializer.serialize(encoder, value)
|
||||
is PrivateChatImpl -> PrivateChatImpl.serializer().serialize(encoder, value)
|
||||
is GroupChatImpl -> GroupChatImpl.serializer().serialize(encoder, value)
|
||||
is SupergroupChatImpl -> SupergroupChatImpl.serializer().serialize(encoder, value)
|
||||
is ForumChatImpl -> ForumChatImpl.serializer().serialize(encoder, value)
|
||||
is ChannelChatImpl -> ChannelChatImpl.serializer().serialize(encoder, value)
|
||||
is CommonBot -> CommonBot.serializer().serialize(encoder, value)
|
||||
is ExtendedBot -> ExtendedBot.serializer().serialize(encoder, value)
|
||||
is CommonUser -> CommonUser.serializer().serialize(encoder, value)
|
||||
is UnknownChatType -> JsonObject.serializer().serialize(encoder, value.rawJson)
|
||||
}
|
||||
@@ -128,6 +167,7 @@ sealed class ExtendedChatSerializer : KSerializer<ExtendedChat> {
|
||||
is ExtendedSupergroupChatImpl -> ExtendedSupergroupChatImpl.serializer().serialize(encoder, value)
|
||||
is ExtendedForumChatImpl -> ExtendedForumChatImpl.serializer().serialize(encoder, value)
|
||||
is ExtendedChannelChatImpl -> ExtendedChannelChatImpl.serializer().serialize(encoder, value)
|
||||
is ExtendedBot -> ExtendedBot.serializer().serialize(encoder, value)
|
||||
is UnknownExtendedChat -> JsonObject.serializer().serialize(encoder, value.rawJson)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@ import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.Message
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.TelegramBotAPIMessageDeserializeOnlySerializer
|
||||
import dev.inmo.tgbotapi.utils.RiskFeature
|
||||
import korlibs.time.DateTime
|
||||
import kotlinx.serialization.SerialName
|
||||
import kotlinx.serialization.Serializable
|
||||
import kotlinx.serialization.json.JsonObject
|
||||
@@ -78,7 +79,9 @@ data class ExtendedPrivateChatImpl(
|
||||
@SerialName(hasRestrictedVoiceAndVideoMessagesField)
|
||||
override val hasRestrictedVoiceAndVideoMessages: Boolean = false,
|
||||
@SerialName(emojiStatusCustomEmojiIdField)
|
||||
override val statusEmojiId: CustomEmojiId? = null
|
||||
override val statusEmojiId: CustomEmojiId? = null,
|
||||
@SerialName(emojiStatusExpirationDateField)
|
||||
override val statusEmojiExpiration: TelegramDate? = null
|
||||
) : ExtendedPrivateChat
|
||||
|
||||
typealias ExtendedUser = ExtendedPrivateChatImpl
|
||||
@@ -181,8 +184,10 @@ data class ExtendedBot(
|
||||
@SerialName(canReadAllGroupMessagesField)
|
||||
val canReadAllGroupMessages: Boolean = false,
|
||||
@SerialName(supportInlineQueriesField)
|
||||
val supportsInlineQueries: Boolean = false
|
||||
) : Bot() {
|
||||
val supportsInlineQueries: Boolean = false,
|
||||
@SerialName(photoField)
|
||||
override val chatPhoto: ChatPhoto? = null
|
||||
) : Bot(), ExtendedChat {
|
||||
@SerialName(isBotField)
|
||||
private val isBot = true
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@ package dev.inmo.tgbotapi.types.chat
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.Message
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.TelegramBotAPIMessageDeserializeOnlySerializer
|
||||
import korlibs.time.DateTime
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable(ExtendedChatSerializer.Companion::class)
|
||||
@@ -21,6 +22,7 @@ sealed interface ExtendedPrivateChat : PrivateChat, ExtendedChatWithUsername {
|
||||
val hasPrivateForwards: Boolean
|
||||
val hasRestrictedVoiceAndVideoMessages: Boolean
|
||||
val statusEmojiId: CustomEmojiId?
|
||||
val statusEmojiExpiration: TelegramDate?
|
||||
|
||||
val allowCreateUserIdLink: Boolean
|
||||
get() = hasPrivateForwards
|
||||
|
||||
@@ -15,7 +15,7 @@ data class GroupChatImpl(
|
||||
override val id: ChatId,
|
||||
@SerialName(titleField)
|
||||
override val title: String
|
||||
) : GroupChat
|
||||
) : PreviewGroupChat
|
||||
|
||||
@Serializable
|
||||
@RiskFeature("This class is a subject of changes. It is better to use PrivateChat due")
|
||||
@@ -28,7 +28,7 @@ data class PrivateChatImpl(
|
||||
override val firstName: String = "",
|
||||
@SerialName(lastNameField)
|
||||
override val lastName: String = ""
|
||||
) : PrivateChat
|
||||
) : PreviewPrivateChat
|
||||
|
||||
@Serializable
|
||||
@RiskFeature("This class is a subject of changes. It is better to use SupergroupChat due")
|
||||
@@ -39,7 +39,7 @@ data class SupergroupChatImpl(
|
||||
override val title: String,
|
||||
@SerialName(usernameField)
|
||||
override val username: Username? = null
|
||||
) : SupergroupChat
|
||||
) : PreviewSupergroupChat
|
||||
|
||||
@Serializable
|
||||
@RiskFeature("This class is a subject of changes. It is better to use ForumChat due")
|
||||
@@ -50,7 +50,7 @@ data class ForumChatImpl(
|
||||
override val title: String,
|
||||
@SerialName(usernameField)
|
||||
override val username: Username? = null
|
||||
) : ForumChat
|
||||
) : PreviewForumChat
|
||||
|
||||
@Serializable
|
||||
@RiskFeature("This class is a subject of changes. It is better to use ChannelChat due")
|
||||
@@ -61,14 +61,20 @@ data class ChannelChatImpl(
|
||||
override val title: String,
|
||||
@SerialName(usernameField)
|
||||
override val username: Username? = null
|
||||
) : ChannelChat
|
||||
) : PreviewChannelChat
|
||||
|
||||
@Serializable(UserSerializer::class)
|
||||
sealed class User : PrivateChat
|
||||
|
||||
@Serializable(UserSerializer::class)
|
||||
sealed class PreviewUser : PreviewPrivateChat, User()
|
||||
|
||||
@Serializable(UserSerializer::class)
|
||||
sealed class Bot : User()
|
||||
|
||||
@Serializable(UserSerializer::class)
|
||||
sealed class PreviewBot : PreviewUser()
|
||||
|
||||
@Serializable
|
||||
data class CommonBot(
|
||||
override val id: UserId,
|
||||
@@ -78,7 +84,7 @@ data class CommonBot(
|
||||
override val lastName: String = "",
|
||||
@SerialName(usernameField)
|
||||
override val username: Username? = null,
|
||||
) : Bot() {
|
||||
) : PreviewBot() {
|
||||
@SerialName(isBotField)
|
||||
private val isBot = true
|
||||
}
|
||||
@@ -99,7 +105,7 @@ data class CommonUser(
|
||||
override val isPremium: Boolean = false,
|
||||
@SerialName(addedToAttachmentMenuField)
|
||||
override val addedToAttachmentMenu: Boolean = false
|
||||
) : User(), WithOptionalLanguageCode, PossiblyPremiumChat, AbleToAddInAttachmentMenuChat {
|
||||
) : PreviewUser(), WithOptionalLanguageCode, PossiblyPremiumChat, AbleToAddInAttachmentMenuChat {
|
||||
constructor(
|
||||
id: UserId,
|
||||
firstName: String,
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
package dev.inmo.tgbotapi.types.chat
|
||||
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewChat : Chat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewUsernameChat : PreviewChat, UsernameChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewPrivateChat : PreviewUsernameChat, PrivateChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewPublicChat : PreviewChat, PublicChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewSuperPublicChat : PreviewPublicChat, PreviewUsernameChat, SuperPublicChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewChannelChat : PreviewSuperPublicChat, ChannelChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewGroupChat : PreviewPublicChat, GroupChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewSupergroupChat : PreviewGroupChat, PreviewSuperPublicChat, SupergroupChat
|
||||
|
||||
@Serializable(PreviewChatSerializer::class)
|
||||
sealed interface PreviewForumChat : PreviewSupergroupChat, ForumChat
|
||||
@@ -7,4 +7,4 @@ data class UnknownChatType(
|
||||
override val id: IdChatIdentifier,
|
||||
val raw: String,
|
||||
val rawJson: JsonObject
|
||||
) : Chat
|
||||
) : Chat, PreviewChat
|
||||
|
||||
@@ -35,9 +35,15 @@ data class AdministratorChatMemberImpl(
|
||||
@SerialName(customTitleField)
|
||||
override val customTitle: String? = null,
|
||||
@SerialName(canManageTopicsField)
|
||||
override val canManageTopics: Boolean = false
|
||||
override val canManageTopics: Boolean = false,
|
||||
@SerialName(canPostStoriesField)
|
||||
override val canPostStories: Boolean = false,
|
||||
@SerialName(canEditStoriesField)
|
||||
override val canEditStories: Boolean = false,
|
||||
@SerialName(canDeleteStoriesField)
|
||||
override val canDeleteStories: Boolean = false
|
||||
) : AdministratorChatMember {
|
||||
@SerialName(statusField)
|
||||
@Required
|
||||
private val type: String = "administrator"
|
||||
override val status: ChatMember.Status = ChatMember.Status.Administrator
|
||||
}
|
||||
|
||||
@@ -16,4 +16,43 @@ sealed interface ChatAdministratorRights : SpecialChatAdministratorRights {
|
||||
val canPromoteMembers: Boolean
|
||||
val canPostMessages: Boolean
|
||||
val canEditMessages: Boolean
|
||||
val canPostStories: Boolean
|
||||
val canEditStories: Boolean
|
||||
val canDeleteStories: Boolean
|
||||
|
||||
companion object {
|
||||
operator fun invoke(
|
||||
canChangeInfo: Boolean = false,
|
||||
canPostMessages: Boolean = false,
|
||||
canEditMessages: Boolean = false,
|
||||
canRemoveMessages: Boolean = false,
|
||||
canInviteUsers: Boolean = false,
|
||||
canRestrictMembers: Boolean = false,
|
||||
canPinMessages: Boolean = false,
|
||||
canPromoteMembers: Boolean = false,
|
||||
canManageVideoChats: Boolean = false,
|
||||
canManageChat: Boolean = false,
|
||||
isAnonymous: Boolean = false,
|
||||
canManageTopics: Boolean = false,
|
||||
canPostStories: Boolean = false,
|
||||
canEditStories: Boolean = false,
|
||||
canDeleteStories: Boolean = false
|
||||
) = ChatCommonAdministratorRights(
|
||||
canChangeInfo = canChangeInfo,
|
||||
canPostMessages = canPostMessages,
|
||||
canEditMessages = canEditMessages,
|
||||
canRemoveMessages = canRemoveMessages,
|
||||
canInviteUsers = canInviteUsers,
|
||||
canRestrictMembers = canRestrictMembers,
|
||||
canPinMessages = canPinMessages,
|
||||
canPromoteMembers = canPromoteMembers,
|
||||
canManageVideoChats = canManageVideoChats,
|
||||
canManageChat = canManageChat,
|
||||
isAnonymous = isAnonymous,
|
||||
canManageTopics = canManageTopics,
|
||||
canPostStories = canPostStories,
|
||||
canEditStories = canEditStories,
|
||||
canDeleteStories = canDeleteStories
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,7 +5,7 @@ import kotlinx.serialization.SerialName
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable
|
||||
data class ChatAdministratorRightsImpl(
|
||||
data class ChatCommonAdministratorRights(
|
||||
@SerialName(canChangeInfoField)
|
||||
override val canChangeInfo: Boolean = false,
|
||||
@SerialName(canPostMessagesField)
|
||||
@@ -29,5 +29,20 @@ data class ChatAdministratorRightsImpl(
|
||||
@SerialName(isAnonymousField)
|
||||
override val isAnonymous: Boolean = false,
|
||||
@SerialName(canManageTopicsField)
|
||||
override val canManageTopics: Boolean = false
|
||||
override val canManageTopics: Boolean = false,
|
||||
@SerialName(canPostStoriesField)
|
||||
override val canPostStories: Boolean = false,
|
||||
@SerialName(canEditStoriesField)
|
||||
override val canEditStories: Boolean = false,
|
||||
@SerialName(canDeleteStoriesField)
|
||||
override val canDeleteStories: Boolean = false
|
||||
) : ChatAdministratorRights
|
||||
|
||||
@Deprecated(
|
||||
"Renamed to ChatCommonAdministratorRights and will be removed soon",
|
||||
ReplaceWith(
|
||||
"ChatCommonAdministratorRights",
|
||||
"dev.inmo.tgbotapi.types.chat.member.ChatCommonAdministratorRights"
|
||||
)
|
||||
)
|
||||
typealias ChatAdministratorRightsImpl = ChatCommonAdministratorRights
|
||||
@@ -4,8 +4,10 @@ import dev.inmo.tgbotapi.abstracts.WithUser
|
||||
import dev.inmo.tgbotapi.types.statusField
|
||||
import dev.inmo.tgbotapi.utils.RiskFeature
|
||||
import dev.inmo.tgbotapi.utils.nonstrictJsonFormat
|
||||
import kotlinx.serialization.DeserializationStrategy
|
||||
import kotlinx.serialization.KSerializer
|
||||
import kotlinx.serialization.Serializable
|
||||
import kotlinx.serialization.builtins.serializer
|
||||
import kotlinx.serialization.descriptors.SerialDescriptor
|
||||
import kotlinx.serialization.encoding.Decoder
|
||||
import kotlinx.serialization.encoding.Encoder
|
||||
@@ -13,7 +15,38 @@ import kotlinx.serialization.json.JsonObject
|
||||
import kotlinx.serialization.json.jsonPrimitive
|
||||
|
||||
@Serializable(ChatMemberSerializer::class)
|
||||
sealed interface ChatMember : WithUser
|
||||
sealed interface ChatMember : WithUser {
|
||||
@Serializable(StatusSerializer::class)
|
||||
enum class Status(
|
||||
val status: String,
|
||||
val deserializationStrategy: DeserializationStrategy<ChatMember>
|
||||
) {
|
||||
Creator("creator", OwnerChatMember.serializer()),
|
||||
Administrator("administrator", AdministratorChatMemberImpl.serializer()),
|
||||
Member("member", MemberChatMemberImpl.serializer()),
|
||||
Restricted("restricted", RestrictedChatMember.serializer()),
|
||||
Left("left", LeftChatMemberImpl.serializer()),
|
||||
Kicked("kicked", KickedChatMember.serializer())
|
||||
}
|
||||
|
||||
object StatusSerializer : KSerializer<Status> {
|
||||
override val descriptor: SerialDescriptor
|
||||
get() = String.serializer().descriptor
|
||||
|
||||
override fun deserialize(decoder: Decoder): Status {
|
||||
val status = decoder.decodeString()
|
||||
return Status.values().first {
|
||||
it.status == status
|
||||
}
|
||||
}
|
||||
|
||||
override fun serialize(encoder: Encoder, value: Status) {
|
||||
encoder.encodeString(value.status)
|
||||
}
|
||||
}
|
||||
|
||||
val status: Status
|
||||
}
|
||||
|
||||
@RiskFeature
|
||||
object ChatMemberSerializer : KSerializer<ChatMember> {
|
||||
@@ -21,15 +54,14 @@ object ChatMemberSerializer : KSerializer<ChatMember> {
|
||||
|
||||
override fun deserialize(decoder: Decoder): ChatMember {
|
||||
val json = JsonObject.serializer().deserialize(decoder)
|
||||
return when (json[statusField] ?.jsonPrimitive ?.content ?: error("Status field of chat member must be specified, but incoming json contains next: $json")) {
|
||||
"creator" -> nonstrictJsonFormat.decodeFromJsonElement(OwnerChatMember.serializer(), json)
|
||||
"administrator" -> nonstrictJsonFormat.decodeFromJsonElement(AdministratorChatMemberImpl.serializer(), json)
|
||||
"member" -> nonstrictJsonFormat.decodeFromJsonElement(MemberChatMemberImpl.serializer(), json)
|
||||
"restricted" -> nonstrictJsonFormat.decodeFromJsonElement(RestrictedChatMember.serializer(), json)
|
||||
"left" -> nonstrictJsonFormat.decodeFromJsonElement(LeftChatMemberImpl.serializer(), json)
|
||||
"kicked" -> nonstrictJsonFormat.decodeFromJsonElement(KickedChatMember.serializer(), json)
|
||||
else -> error("Unknown type of chat member in json: $json")
|
||||
}
|
||||
val status = json[statusField] ?.jsonPrimitive ?.content ?: error("Status field of chat member must be specified, but incoming json contains next: $json")
|
||||
return ChatMember.Status.values().firstNotNullOfOrNull {
|
||||
if (it.status == status) {
|
||||
nonstrictJsonFormat.decodeFromJsonElement(it.deserializationStrategy, json)
|
||||
} else {
|
||||
null
|
||||
}
|
||||
} ?: error("Unknown type of chat member in json: $json")
|
||||
}
|
||||
|
||||
override fun serialize(encoder: Encoder, value: ChatMember) {
|
||||
|
||||
@@ -1,9 +1,10 @@
|
||||
package dev.inmo.tgbotapi.types.chat.member
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.WithChat
|
||||
import dev.inmo.tgbotapi.abstracts.WithPreviewChat
|
||||
import dev.inmo.tgbotapi.abstracts.WithUser
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
import kotlinx.serialization.SerialName
|
||||
import kotlinx.serialization.Serializable
|
||||
@@ -11,7 +12,7 @@ import kotlinx.serialization.Serializable
|
||||
@Serializable
|
||||
data class ChatMemberUpdated(
|
||||
@SerialName(chatField)
|
||||
override val chat: Chat,
|
||||
override val chat: PreviewChat,
|
||||
@SerialName(fromField)
|
||||
override val user: User,
|
||||
@SerialName(dateField)
|
||||
@@ -24,4 +25,4 @@ data class ChatMemberUpdated(
|
||||
val inviteLink: ChatInviteLink? = null,
|
||||
@SerialName(viaChatFolderInviteLinkField)
|
||||
val viaChatFolderInviteLink: Boolean? = false
|
||||
) : WithChat, WithUser
|
||||
) : WithPreviewChat, WithUser
|
||||
|
||||
@@ -13,5 +13,5 @@ data class KickedChatMember(
|
||||
) : BannedChatMember {
|
||||
@SerialName(statusField)
|
||||
@Required
|
||||
private val type: String = "kicked"
|
||||
override val status: ChatMember.Status = ChatMember.Status.Kicked
|
||||
}
|
||||
|
||||
@@ -5,8 +5,11 @@ import dev.inmo.tgbotapi.types.chat.User
|
||||
import kotlinx.serialization.*
|
||||
|
||||
@Serializable
|
||||
data class LeftChatMemberImpl(@SerialName(userField) override val user: User) : LeftChatMember {
|
||||
data class LeftChatMemberImpl(
|
||||
@SerialName(userField)
|
||||
override val user: User
|
||||
) : LeftChatMember {
|
||||
@SerialName(statusField)
|
||||
@Required
|
||||
private val type: String = "left"
|
||||
override val status: ChatMember.Status = ChatMember.Status.Left
|
||||
}
|
||||
|
||||
@@ -5,8 +5,11 @@ import dev.inmo.tgbotapi.types.chat.User
|
||||
import kotlinx.serialization.*
|
||||
|
||||
@Serializable
|
||||
data class MemberChatMemberImpl(@SerialName(userField) override val user: User) : MemberChatMember {
|
||||
data class MemberChatMemberImpl(
|
||||
@SerialName(userField)
|
||||
override val user: User
|
||||
) : MemberChatMember {
|
||||
@SerialName(statusField)
|
||||
@Required
|
||||
private val type: String = "member"
|
||||
override val status: ChatMember.Status = ChatMember.Status.Member
|
||||
}
|
||||
|
||||
@@ -36,7 +36,14 @@ data class OwnerChatMember(
|
||||
override val canManageChat: Boolean = true
|
||||
@Transient
|
||||
override val canManageTopics: Boolean = true
|
||||
@Transient
|
||||
override val canPostStories: Boolean = true
|
||||
@Transient
|
||||
override val canEditStories: Boolean = true
|
||||
@Transient
|
||||
override val canDeleteStories: Boolean = true
|
||||
|
||||
@SerialName(statusField)
|
||||
@Required
|
||||
private val type: String = "creator"
|
||||
override val status: ChatMember.Status = ChatMember.Status.Creator
|
||||
}
|
||||
|
||||
@@ -44,5 +44,5 @@ data class RestrictedChatMember(
|
||||
) : BannedChatMember, SpecialRightsChatMember, ChatPermissions {
|
||||
@SerialName(statusField)
|
||||
@Required
|
||||
private val type: String = "restricted"
|
||||
override val status: ChatMember.Status = ChatMember.Status.Restricted
|
||||
}
|
||||
|
||||
@@ -5,12 +5,13 @@ import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.buttons.InlineKeyboardMarkup
|
||||
import dev.inmo.tgbotapi.types.chat.ChannelChat
|
||||
import dev.inmo.tgbotapi.types.chat.CommonBot
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChannelChat
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.*
|
||||
import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
|
||||
data class ChannelContentMessageImpl<T: MessageContent>(
|
||||
override val messageId: MessageId,
|
||||
override val chat: ChannelChat,
|
||||
override val chat: PreviewChannelChat,
|
||||
override val content: T,
|
||||
override val date: DateTime,
|
||||
override val editDate: DateTime?,
|
||||
|
||||
@@ -3,12 +3,13 @@ package dev.inmo.tgbotapi.types.message
|
||||
import korlibs.time.DateTime
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.chat.ChannelChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChannelChat
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.ChannelEvent
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.ChatEventMessage
|
||||
|
||||
data class ChannelEventMessage<T : ChannelEvent>(
|
||||
override val messageId: MessageId,
|
||||
override val chat: ChannelChat,
|
||||
override val chat: PreviewChannelChat,
|
||||
override val chatEvent: T,
|
||||
override val date: DateTime
|
||||
) : ChatEventMessage<T>
|
||||
|
||||
@@ -1,12 +1,75 @@
|
||||
package dev.inmo.tgbotapi.types.message.ChatEvents.forum
|
||||
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.ChatEvent
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.ForumEvent
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.PrivateEvent
|
||||
import dev.inmo.tgbotapi.types.webAppNameField
|
||||
import kotlinx.serialization.KSerializer
|
||||
import kotlinx.serialization.SerialName
|
||||
import kotlinx.serialization.Serializable
|
||||
import kotlinx.serialization.descriptors.SerialDescriptor
|
||||
import kotlinx.serialization.encoding.Decoder
|
||||
import kotlinx.serialization.encoding.Encoder
|
||||
|
||||
@Serializable
|
||||
data class WriteAccessAllowed(
|
||||
@SerialName(webAppNameField)
|
||||
val webAppName: String? = null
|
||||
) : ForumEvent
|
||||
@Serializable(WriteAccessAllowed.Companion::class)
|
||||
sealed interface WriteAccessAllowed : PrivateEvent, ForumEvent {
|
||||
val webAppName: String?
|
||||
get() = null
|
||||
val fromRequest: Boolean
|
||||
get() = false
|
||||
val fromAttachmentMenu: Boolean
|
||||
get() = false
|
||||
|
||||
@Serializable
|
||||
object Other : WriteAccessAllowed
|
||||
@Serializable
|
||||
data class FromWebAppLink(
|
||||
override val webAppName: String
|
||||
) : WriteAccessAllowed
|
||||
@Serializable
|
||||
object FromRequest : WriteAccessAllowed {
|
||||
override val fromRequest: Boolean
|
||||
get() = true
|
||||
}
|
||||
|
||||
@Serializable
|
||||
object FromAttachmentMenu : WriteAccessAllowed {
|
||||
override val fromAttachmentMenu: Boolean
|
||||
get() = true
|
||||
}
|
||||
|
||||
@Serializable
|
||||
private class WriteAccessAllowedRaw(
|
||||
val web_app_name: String? = null,
|
||||
val from_request: Boolean = false,
|
||||
val from_attachment_menu: Boolean = false
|
||||
)
|
||||
|
||||
companion object : KSerializer<WriteAccessAllowed> {
|
||||
override val descriptor: SerialDescriptor
|
||||
get() = WriteAccessAllowedRaw.serializer().descriptor
|
||||
|
||||
override fun deserialize(decoder: Decoder): WriteAccessAllowed {
|
||||
val raw = WriteAccessAllowedRaw.serializer().deserialize(decoder)
|
||||
|
||||
return when {
|
||||
raw.web_app_name != null -> FromWebAppLink(raw.web_app_name)
|
||||
raw.from_request -> FromRequest
|
||||
raw.from_attachment_menu -> Other
|
||||
else -> Other
|
||||
}
|
||||
}
|
||||
|
||||
override fun serialize(encoder: Encoder, value: WriteAccessAllowed) {
|
||||
val raw = when (value) {
|
||||
FromAttachmentMenu -> WriteAccessAllowedRaw(from_attachment_menu = true)
|
||||
FromRequest -> WriteAccessAllowedRaw(from_request = true)
|
||||
Other -> WriteAccessAllowedRaw()
|
||||
is FromWebAppLink -> WriteAccessAllowedRaw(web_app_name = value.webAppName)
|
||||
}
|
||||
WriteAccessAllowedRaw.serializer().serialize(encoder, raw)
|
||||
}
|
||||
|
||||
operator fun invoke(webAppName: String?): WriteAccessAllowed = webAppName ?.let(::FromWebAppLink) ?: Other
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,13 +4,14 @@ import korlibs.time.DateTime
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
import dev.inmo.tgbotapi.types.chat.GroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewGroupChat
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.GroupEvent
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.GroupEventMessage
|
||||
|
||||
data class CommonGroupEventMessage<T : GroupEvent>(
|
||||
override val messageId: MessageId,
|
||||
override val from: User,
|
||||
override val chat: GroupChat,
|
||||
override val chat: PreviewGroupChat,
|
||||
override val chatEvent: T,
|
||||
override val date: DateTime
|
||||
) : GroupEventMessage<T>
|
||||
|
||||
@@ -2,6 +2,7 @@ package dev.inmo.tgbotapi.types.message
|
||||
|
||||
import korlibs.time.DateTime
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewSupergroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
import dev.inmo.tgbotapi.types.chat.SupergroupChat
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.SupergroupEvent
|
||||
@@ -10,7 +11,7 @@ import dev.inmo.tgbotapi.types.message.abstracts.SupergroupEventMessage
|
||||
data class CommonSupergroupEventMessage<T : SupergroupEvent>(
|
||||
override val messageId: MessageId,
|
||||
override val from: User,
|
||||
override val chat: SupergroupChat,
|
||||
override val chat: PreviewSupergroupChat,
|
||||
override val chatEvent: T,
|
||||
override val date: DateTime
|
||||
) : SupergroupEventMessage<T>
|
||||
|
||||
@@ -10,8 +10,8 @@ import dev.inmo.tgbotapi.types.message.abstracts.*
|
||||
import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
|
||||
data class ConnectedFromChannelGroupContentMessageImpl<T : MessageContent>(
|
||||
override val chat: GroupChat,
|
||||
override val channel: ChannelChat,
|
||||
override val chat: PreviewGroupChat,
|
||||
override val channel: PreviewChannelChat,
|
||||
override val messageId: MessageId,
|
||||
override val date: DateTime,
|
||||
override val forwardInfo: ForwardInfo?,
|
||||
@@ -26,8 +26,8 @@ data class ConnectedFromChannelGroupContentMessageImpl<T : MessageContent>(
|
||||
) : ConnectedFromChannelGroupContentMessage<T>
|
||||
|
||||
data class UnconnectedFromChannelGroupContentMessageImpl<T: MessageContent>(
|
||||
override val chat: GroupChat,
|
||||
override val channel: ChannelChat,
|
||||
override val chat: PreviewGroupChat,
|
||||
override val channel: PreviewChannelChat,
|
||||
override val messageId: MessageId,
|
||||
override val date: DateTime,
|
||||
override val forwardInfo: ForwardInfo?,
|
||||
@@ -42,7 +42,7 @@ data class UnconnectedFromChannelGroupContentMessageImpl<T: MessageContent>(
|
||||
) : UnconnectedFromChannelGroupContentMessage<T>
|
||||
|
||||
data class AnonymousGroupContentMessageImpl<T : MessageContent>(
|
||||
override val chat: GroupChat,
|
||||
override val chat: PreviewGroupChat,
|
||||
override val messageId: MessageId,
|
||||
override val date: DateTime,
|
||||
override val forwardInfo: ForwardInfo?,
|
||||
@@ -57,7 +57,7 @@ data class AnonymousGroupContentMessageImpl<T : MessageContent>(
|
||||
) : AnonymousGroupContentMessage<T>
|
||||
|
||||
data class CommonGroupContentMessageImpl<T : MessageContent>(
|
||||
override val chat: GroupChat,
|
||||
override val chat: PreviewGroupChat,
|
||||
override val messageId: MessageId,
|
||||
override val from: User,
|
||||
override val date: DateTime,
|
||||
@@ -72,8 +72,8 @@ data class CommonGroupContentMessageImpl<T : MessageContent>(
|
||||
) : CommonGroupContentMessage<T>
|
||||
|
||||
data class FromChannelForumContentMessageImpl<T: MessageContent>(
|
||||
override val chat: ForumChat,
|
||||
override val channel: ChannelChat,
|
||||
override val chat: PreviewForumChat,
|
||||
override val channel: PreviewChannelChat,
|
||||
override val messageId: MessageId,
|
||||
override val threadId: MessageThreadId,
|
||||
override val date: DateTime,
|
||||
@@ -89,7 +89,7 @@ data class FromChannelForumContentMessageImpl<T: MessageContent>(
|
||||
) : FromChannelForumContentMessage<T>
|
||||
|
||||
data class AnonymousForumContentMessageImpl<T : MessageContent>(
|
||||
override val chat: ForumChat,
|
||||
override val chat: PreviewForumChat,
|
||||
override val messageId: MessageId,
|
||||
override val threadId: MessageThreadId,
|
||||
override val date: DateTime,
|
||||
@@ -105,7 +105,7 @@ data class AnonymousForumContentMessageImpl<T : MessageContent>(
|
||||
) : AnonymousForumContentMessage<T>
|
||||
|
||||
data class CommonForumContentMessageImpl<T : MessageContent>(
|
||||
override val chat: ForumChat,
|
||||
override val chat: PreviewForumChat,
|
||||
override val messageId: MessageId,
|
||||
override val threadId: MessageThreadId,
|
||||
override val from: User,
|
||||
|
||||
@@ -4,13 +4,14 @@ import korlibs.time.DateTime
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.FromUserMessage
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.Message
|
||||
import dev.inmo.tgbotapi.types.passport.PassportData
|
||||
|
||||
data class PassportMessage(
|
||||
override val messageId: MessageId,
|
||||
override val chat: Chat,
|
||||
override val chat: PreviewChat,
|
||||
override val from: User,
|
||||
override val date: DateTime,
|
||||
val passportData: PassportData
|
||||
|
||||
@@ -13,7 +13,7 @@ import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
data class PrivateContentMessageImpl<T: MessageContent>(
|
||||
override val messageId: MessageId,
|
||||
override val from: User,
|
||||
override val chat: Chat,
|
||||
override val chat: PreviewPrivateChat,
|
||||
override val content: T,
|
||||
override val date: DateTime,
|
||||
override val editDate: DateTime?,
|
||||
|
||||
@@ -2,13 +2,14 @@ package dev.inmo.tgbotapi.types.message
|
||||
|
||||
import korlibs.time.DateTime
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewPrivateChat
|
||||
import dev.inmo.tgbotapi.types.chat.PrivateChat
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.PrivateEvent
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.ChatEventMessage
|
||||
|
||||
data class PrivateEventMessage<T : PrivateEvent>(
|
||||
override val messageId: MessageId,
|
||||
override val chat: PrivateChat,
|
||||
override val chat: PreviewPrivateChat,
|
||||
override val chatEvent: T,
|
||||
override val date: DateTime
|
||||
) : ChatEventMessage<T>
|
||||
|
||||
@@ -31,6 +31,7 @@ import dev.inmo.tgbotapi.types.payments.SuccessfulPayment
|
||||
import dev.inmo.tgbotapi.types.polls.Poll
|
||||
import dev.inmo.tgbotapi.types.request.ChatShared
|
||||
import dev.inmo.tgbotapi.types.request.UserShared
|
||||
import dev.inmo.tgbotapi.types.stories.Story
|
||||
import dev.inmo.tgbotapi.types.venue.Venue
|
||||
import kotlinx.serialization.SerialName
|
||||
import kotlinx.serialization.Serializable
|
||||
@@ -42,11 +43,11 @@ internal data class RawMessage(
|
||||
@SerialName(messageIdField)
|
||||
val messageId: MessageId,
|
||||
val date: TelegramDate,
|
||||
private val chat: Chat,
|
||||
private val chat: PreviewChat,
|
||||
@SerialName(messageThreadIdField)
|
||||
private val messageThreadId: MessageThreadId? = null,
|
||||
private val from: User? = null,
|
||||
private val sender_chat: PublicChat? = null,
|
||||
private val sender_chat: PreviewPublicChat? = null,
|
||||
private val forward_from: User? = null,
|
||||
private val forward_from_chat: Chat? = null,
|
||||
private val forward_from_message_id: MessageId? = null,
|
||||
@@ -65,6 +66,7 @@ internal data class RawMessage(
|
||||
private val caption: String? = null,
|
||||
private val caption_entities: RawMessageEntities? = null,
|
||||
private val has_media_spoiler: Boolean? = null,
|
||||
private val story: Story? = null,
|
||||
private val audio: AudioFile? = null,
|
||||
private val document: DocumentFile? = null,
|
||||
private val animation: AnimationFile? = null,
|
||||
@@ -134,6 +136,11 @@ internal data class RawMessage(
|
||||
} ?: emptyList()
|
||||
|
||||
when {
|
||||
story != null -> StoryContent(
|
||||
chat,
|
||||
messageId,
|
||||
story
|
||||
)
|
||||
text != null -> TextContent(text, (entities ?: emptyList()).asTextSources(text))
|
||||
audio != null -> AudioContent(
|
||||
audio,
|
||||
@@ -267,27 +274,27 @@ internal data class RawMessage(
|
||||
try {
|
||||
chatEvent?.let { chatEvent ->
|
||||
when (chat) {
|
||||
is SupergroupChat -> CommonSupergroupEventMessage(
|
||||
is PreviewSupergroupChat -> CommonSupergroupEventMessage(
|
||||
messageId,
|
||||
from ?: error("Supergroup events are expected to contain 'from' field"),
|
||||
chat,
|
||||
chatEvent as? SupergroupEvent ?: throwWrongChatEvent(SupergroupEvent::class, chatEvent),
|
||||
date.asDate
|
||||
)
|
||||
is GroupChat -> CommonGroupEventMessage(
|
||||
is PreviewGroupChat -> CommonGroupEventMessage(
|
||||
messageId,
|
||||
from ?: error("Supergroup events are expected to contain 'from' field"),
|
||||
chat,
|
||||
chatEvent as? GroupEvent ?: throwWrongChatEvent(GroupChat::class, chatEvent),
|
||||
date.asDate
|
||||
)
|
||||
is ChannelChat -> ChannelEventMessage(
|
||||
is PreviewChannelChat -> ChannelEventMessage(
|
||||
messageId,
|
||||
chat,
|
||||
chatEvent as? ChannelEvent ?: throwWrongChatEvent(ChannelEvent::class, chatEvent),
|
||||
date.asDate
|
||||
)
|
||||
is PrivateChat -> PrivateEventMessage(
|
||||
is PreviewPrivateChat -> PrivateEventMessage(
|
||||
messageId,
|
||||
chat,
|
||||
chatEvent as? PrivateEvent ?: throwWrongChatEvent(PrivateEvent::class, chatEvent),
|
||||
@@ -296,8 +303,8 @@ internal data class RawMessage(
|
||||
else -> error("Expected one of the public chats, but was $chat (in extracting of chat event message)")
|
||||
}
|
||||
} ?: content?.let { content -> when (chat) {
|
||||
is PublicChat -> when (chat) {
|
||||
is ChannelChat -> ChannelContentMessageImpl(
|
||||
is PreviewPublicChat -> when (chat) {
|
||||
is PreviewChannelChat -> ChannelContentMessageImpl(
|
||||
messageId,
|
||||
chat,
|
||||
content,
|
||||
@@ -311,17 +318,16 @@ internal data class RawMessage(
|
||||
author_signature,
|
||||
media_group_id
|
||||
)
|
||||
is ForumChat -> if (messageThreadId != null) {
|
||||
is PreviewForumChat -> if (messageThreadId != null) {
|
||||
val chatId = ChatIdWithThreadId(
|
||||
chat.id.chatId,
|
||||
messageThreadId
|
||||
)
|
||||
val actualForumChat = when (chat) {
|
||||
is ExtendedForumChatImpl -> chat.copy(id = chatId)
|
||||
is ForumChatImpl -> chat.copy(id = chatId)
|
||||
}
|
||||
when (sender_chat) {
|
||||
is ChannelChat -> FromChannelForumContentMessageImpl(
|
||||
is PreviewChannelChat -> FromChannelForumContentMessageImpl(
|
||||
actualForumChat,
|
||||
sender_chat,
|
||||
messageId,
|
||||
@@ -337,7 +343,7 @@ internal data class RawMessage(
|
||||
author_signature,
|
||||
media_group_id
|
||||
)
|
||||
is GroupChat -> AnonymousForumContentMessageImpl(
|
||||
is PreviewGroupChat -> AnonymousForumContentMessageImpl(
|
||||
actualForumChat,
|
||||
messageId,
|
||||
messageThreadId,
|
||||
@@ -370,7 +376,7 @@ internal data class RawMessage(
|
||||
}
|
||||
} else {
|
||||
when (sender_chat) {
|
||||
is ChannelChat -> if (is_automatic_forward == true) {
|
||||
is PreviewChannelChat -> if (is_automatic_forward == true) {
|
||||
ConnectedFromChannelGroupContentMessageImpl(
|
||||
chat,
|
||||
sender_chat,
|
||||
@@ -433,8 +439,8 @@ internal data class RawMessage(
|
||||
)
|
||||
}
|
||||
}
|
||||
is GroupChat -> when (sender_chat) {
|
||||
is ChannelChat -> if (is_automatic_forward == true) {
|
||||
is PreviewGroupChat -> when (sender_chat) {
|
||||
is PreviewChannelChat -> if (is_automatic_forward == true) {
|
||||
ConnectedFromChannelGroupContentMessageImpl(
|
||||
chat,
|
||||
sender_chat,
|
||||
@@ -467,7 +473,7 @@ internal data class RawMessage(
|
||||
media_group_id
|
||||
)
|
||||
}
|
||||
is GroupChat -> AnonymousGroupContentMessageImpl(
|
||||
is PreviewGroupChat -> AnonymousGroupContentMessageImpl(
|
||||
chat,
|
||||
messageId,
|
||||
date.asDate,
|
||||
@@ -497,7 +503,7 @@ internal data class RawMessage(
|
||||
)
|
||||
}
|
||||
}
|
||||
is PrivateChat -> PrivateContentMessageImpl(
|
||||
is PreviewPrivateChat -> PrivateContentMessageImpl(
|
||||
messageId,
|
||||
from ?: error("Was detected common message, but owner (sender) of the message was not found"),
|
||||
chat,
|
||||
|
||||
@@ -18,6 +18,30 @@ internal data class RawMessageEntity(
|
||||
internal val range by lazy {
|
||||
offset until (offset + length)
|
||||
}
|
||||
|
||||
val priority by lazy {
|
||||
when (type) {
|
||||
// Types with potential subsources should have priority
|
||||
"mention" -> 0
|
||||
"hashtag" -> 0
|
||||
"cashtag" -> 0
|
||||
"email" -> 0
|
||||
"phone_number" -> 0
|
||||
"bold" -> 0
|
||||
"italic" -> 0
|
||||
"text_mention" -> 0
|
||||
"strikethrough" -> 0
|
||||
"underline" -> 0
|
||||
"spoiler" -> 0
|
||||
"custom_emoji" -> 0
|
||||
"bot_command" -> 1
|
||||
"url" -> 1
|
||||
"code" -> 1
|
||||
"pre" -> 1
|
||||
"text_link" -> 1
|
||||
else -> 1
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
internal fun RawMessageEntity.asTextSource(
|
||||
@@ -85,7 +109,10 @@ private fun createTextSources(
|
||||
originalFullString: String,
|
||||
entities: RawMessageEntities
|
||||
): List<Pair<Int, TextSource>> {
|
||||
val mutableEntities = entities.toMutableList().apply { sortBy { it.offset } }
|
||||
val mutableEntities = entities.toMutableList().apply {
|
||||
sortBy { it.priority } // sorting to fix potential issues in source sorting of entities
|
||||
sortBy { it.offset }
|
||||
}
|
||||
val resultList = mutableListOf<Pair<Int, TextSource>>()
|
||||
|
||||
while (mutableEntities.isNotEmpty()) {
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.ChannelChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChannelChat
|
||||
import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
|
||||
interface ChannelContentMessage<T: MessageContent> : PossiblySentViaBotCommonMessage<T>, SignedMessage, WithSenderChatMessage {
|
||||
override val chat: ChannelChat
|
||||
override val senderChat: ChannelChat
|
||||
override val chat: PreviewChannelChat
|
||||
override val senderChat: PreviewChannelChat
|
||||
get() = chat
|
||||
}
|
||||
|
||||
@@ -1,5 +1,9 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewGroupChat
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.GroupEvent
|
||||
|
||||
interface GroupEventMessage<T : GroupEvent> : ChatEventMessage<T>, FromUserMessage
|
||||
interface GroupEventMessage<T : GroupEvent> : ChatEventMessage<T>, FromUserMessage {
|
||||
override val chat: PreviewGroupChat
|
||||
}
|
||||
|
||||
@@ -1,24 +1,22 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.MessageThreadId
|
||||
import dev.inmo.tgbotapi.types.chat.ChannelChat
|
||||
import dev.inmo.tgbotapi.types.chat.ForumChat
|
||||
import dev.inmo.tgbotapi.types.chat.GroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.*
|
||||
import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
|
||||
sealed interface GroupContentMessage<T : MessageContent> : PublicContentMessage<T> {
|
||||
override val chat: GroupChat
|
||||
override val chat: PreviewGroupChat
|
||||
}
|
||||
|
||||
sealed interface ForumContentMessage<T : MessageContent> : GroupContentMessage<T>, PossiblyTopicMessage {
|
||||
override val chat: ForumChat
|
||||
override val chat: PreviewForumChat
|
||||
override val threadId: MessageThreadId
|
||||
}
|
||||
|
||||
|
||||
sealed interface FromChannelGroupContentMessage<T : MessageContent> : GroupContentMessage<T>, SignedMessage, WithSenderChatMessage {
|
||||
val channel: ChannelChat
|
||||
override val senderChat: ChannelChat
|
||||
val channel: PreviewChannelChat
|
||||
override val senderChat: PreviewChannelChat
|
||||
get() = channel
|
||||
}
|
||||
|
||||
@@ -26,7 +24,7 @@ interface ConnectedFromChannelGroupContentMessage<T: MessageContent> : FromChann
|
||||
interface UnconnectedFromChannelGroupContentMessage<T: MessageContent> : FromChannelGroupContentMessage<T>
|
||||
|
||||
interface AnonymousGroupContentMessage<T : MessageContent> : GroupContentMessage<T>, SignedMessage, WithSenderChatMessage {
|
||||
override val senderChat: GroupChat
|
||||
override val senderChat: PreviewGroupChat
|
||||
get() = chat
|
||||
}
|
||||
|
||||
@@ -35,7 +33,7 @@ interface CommonGroupContentMessage<T : MessageContent> : GroupContentMessage<T>
|
||||
interface FromChannelForumContentMessage<T: MessageContent> : FromChannelGroupContentMessage<T>, ForumContentMessage<T>
|
||||
|
||||
interface AnonymousForumContentMessage<T : MessageContent> : ForumContentMessage<T>, SignedMessage, WithSenderChatMessage {
|
||||
override val senderChat: GroupChat
|
||||
override val senderChat: PreviewGroupChat
|
||||
get() = chat
|
||||
}
|
||||
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import korlibs.time.DateTime
|
||||
import dev.inmo.tgbotapi.abstracts.WithChat
|
||||
import dev.inmo.tgbotapi.abstracts.WithPreviewChat
|
||||
import dev.inmo.tgbotapi.utils.internal.ClassCastsIncluded
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
import dev.inmo.tgbotapi.types.message.RawMessage
|
||||
import kotlinx.serialization.*
|
||||
import kotlinx.serialization.descriptors.*
|
||||
@@ -12,14 +13,14 @@ import kotlinx.serialization.encoding.Decoder
|
||||
import kotlinx.serialization.encoding.Encoder
|
||||
|
||||
@ClassCastsIncluded(excludeRegex = ".*Impl")
|
||||
interface Message : WithChat {
|
||||
interface Message : WithPreviewChat {
|
||||
val messageId: MessageId
|
||||
val date: DateTime
|
||||
}
|
||||
|
||||
data class UnknownMessageType(
|
||||
override val messageId: MessageId,
|
||||
override val chat: Chat,
|
||||
override val chat: PreviewChat,
|
||||
override val date: DateTime,
|
||||
val insideException: Exception
|
||||
) : Message
|
||||
|
||||
@@ -1,5 +1,9 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewPrivateChat
|
||||
import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
|
||||
interface PrivateContentMessage<T: MessageContent> : PossiblySentViaBotCommonMessage<T>, FromUserMessage
|
||||
interface PrivateContentMessage<T: MessageContent> : PossiblySentViaBotCommonMessage<T>, FromUserMessage {
|
||||
override val chat: PreviewPrivateChat
|
||||
}
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewPublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.PublicChat
|
||||
import dev.inmo.tgbotapi.types.message.content.MessageContent
|
||||
|
||||
sealed interface PublicContentMessage<T: MessageContent> : PossiblySentViaBotCommonMessage<T> {
|
||||
override val chat: PublicChat
|
||||
override val chat: PreviewPublicChat
|
||||
}
|
||||
|
||||
@@ -1,5 +1,9 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewGroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewSupergroupChat
|
||||
import dev.inmo.tgbotapi.types.message.ChatEvents.abstracts.SupergroupEvent
|
||||
|
||||
interface SupergroupEventMessage<T : SupergroupEvent> : GroupEventMessage<T>
|
||||
interface SupergroupEventMessage<T : SupergroupEvent> : GroupEventMessage<T> {
|
||||
override val chat: PreviewSupergroupChat
|
||||
}
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
package dev.inmo.tgbotapi.types.message.abstracts
|
||||
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
|
||||
interface WithSenderChatMessage {
|
||||
val senderChat: Chat
|
||||
val senderChat: PreviewChat
|
||||
}
|
||||
|
||||
@@ -13,8 +13,10 @@ import dev.inmo.tgbotapi.types.media.TelegramMedia
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.*
|
||||
import dev.inmo.tgbotapi.types.threadId
|
||||
import dev.inmo.tgbotapi.utils.RiskFeature
|
||||
import kotlinx.serialization.Serializable
|
||||
import kotlinx.serialization.modules.*
|
||||
|
||||
@Serializable
|
||||
sealed interface MessageContent: ResendableContent {
|
||||
companion object {
|
||||
@RiskFeature("This serialization module can be changed in near releases")
|
||||
@@ -49,6 +51,7 @@ sealed interface MessageContent: ResendableContent {
|
||||
subclass(AnimationContent::class)
|
||||
subclass(StickerContent::class)
|
||||
subclass(InvoiceContent::class)
|
||||
subclass(StoryContent::class)
|
||||
|
||||
additionalBuilder()
|
||||
}
|
||||
|
||||
@@ -58,7 +58,6 @@ sealed interface LocationContent : MessageContent {
|
||||
/**
|
||||
* [KSerializer] for [LocationContent]
|
||||
*/
|
||||
@Serializer(LocationContent::class)
|
||||
object LocationContentSerializer : KSerializer<LocationContent> {
|
||||
override val descriptor: SerialDescriptor = buildClassSerialDescriptor("LocationContent") {
|
||||
element(LocationContent::location.name, LocationSerializer.descriptor)
|
||||
@@ -85,7 +84,6 @@ object LocationContentSerializer : KSerializer<LocationContent> {
|
||||
encodeSerializableElement(descriptor, 0, LocationSerializer, value.location)
|
||||
}.endStructure(descriptor)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -94,7 +92,7 @@ object LocationContentSerializer : KSerializer<LocationContent> {
|
||||
*
|
||||
* @see dev.inmo.tgbotapi.extensions.behaviour_builder.utils.followLocation
|
||||
*/
|
||||
@Serializable(LocationContentSerializer::class)
|
||||
@Serializable
|
||||
data class LiveLocationContent(
|
||||
override val location: LiveLocation
|
||||
) : LocationContent {
|
||||
@@ -127,7 +125,7 @@ data class LiveLocationContent(
|
||||
* Just a [LocationContent] with [StaticLocation] [location]. It could be [LiveLocationContent] in previous time in case
|
||||
* when somebody has sent [LiveLocation] in chat and then stop to broadcast location
|
||||
*/
|
||||
@Serializable(LocationContentSerializer::class)
|
||||
@Serializable
|
||||
data class StaticLocationContent(
|
||||
override val location: StaticLocation
|
||||
) : LocationContent {
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
package dev.inmo.tgbotapi.types.message.content
|
||||
|
||||
import dev.inmo.tgbotapi.requests.ForwardMessage
|
||||
import dev.inmo.tgbotapi.requests.abstracts.Request
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.MessageId
|
||||
import dev.inmo.tgbotapi.types.MessageThreadId
|
||||
import dev.inmo.tgbotapi.types.buttons.KeyboardMarkup
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.Message
|
||||
import dev.inmo.tgbotapi.types.stories.Story
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable
|
||||
data class StoryContent(
|
||||
private val chat: Chat,
|
||||
private val messageId: MessageId,
|
||||
val story: Story
|
||||
) : MessageContent {
|
||||
override fun createResend(
|
||||
chatId: ChatIdentifier,
|
||||
messageThreadId: MessageThreadId?,
|
||||
disableNotification: Boolean,
|
||||
protectContent: Boolean,
|
||||
replyToMessageId: MessageId?,
|
||||
allowSendingWithoutReply: Boolean?,
|
||||
replyMarkup: KeyboardMarkup?
|
||||
): Request<out Message> {
|
||||
return ForwardMessage(
|
||||
chat.id,
|
||||
toChatId = chatId,
|
||||
messageId = messageId,
|
||||
threadId = messageThreadId,
|
||||
disableNotification = disableNotification,
|
||||
protectContent = protectContent
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -11,6 +11,7 @@ typealias DiceMessage = CommonMessage<DiceContent>
|
||||
typealias ContactMessage = CommonMessage<ContactContent>
|
||||
typealias PollMessage = CommonMessage<PollContent>
|
||||
typealias TextMessage = CommonMessage<TextContent>
|
||||
typealias StoryMessage = CommonMessage<StoryContent>
|
||||
|
||||
typealias LocationMessage = CommonMessage<LocationContent>
|
||||
typealias LiveLocationMessage = CommonMessage<LiveLocationContent>
|
||||
|
||||
@@ -10,6 +10,7 @@ import dev.inmo.tgbotapi.types.MessageThreadId
|
||||
import dev.inmo.tgbotapi.types.buttons.KeyboardMarkup
|
||||
import dev.inmo.tgbotapi.types.files.VoiceFile
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.ContentMessage
|
||||
import dev.inmo.tgbotapi.types.threadId
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable
|
||||
@@ -27,16 +28,16 @@ data class VoiceContent(
|
||||
allowSendingWithoutReply: Boolean?,
|
||||
replyMarkup: KeyboardMarkup?
|
||||
): Request<ContentMessage<VoiceContent>> = SendVoice(
|
||||
chatId,
|
||||
media.fileId,
|
||||
textSources,
|
||||
media.duration,
|
||||
messageThreadId,
|
||||
disableNotification,
|
||||
protectContent,
|
||||
replyToMessageId,
|
||||
allowSendingWithoutReply,
|
||||
replyMarkup
|
||||
chatId = chatId,
|
||||
voice = media.fileId,
|
||||
entities = textSources,
|
||||
threadId = messageThreadId,
|
||||
duration = media.duration,
|
||||
disableNotification = disableNotification,
|
||||
protectContent = protectContent,
|
||||
replyToMessageId = replyToMessageId,
|
||||
allowSendingWithoutReply = allowSendingWithoutReply,
|
||||
replyMarkup = replyMarkup
|
||||
)
|
||||
|
||||
override fun asTelegramMedia(): TelegramMediaAudio = TelegramMediaAudio(
|
||||
|
||||
@@ -2,19 +2,95 @@ package dev.inmo.tgbotapi.types.polls
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.FromUser
|
||||
import dev.inmo.tgbotapi.types.*
|
||||
import dev.inmo.tgbotapi.types.chat.ChannelChat
|
||||
import dev.inmo.tgbotapi.types.chat.CommonBot
|
||||
import dev.inmo.tgbotapi.types.chat.User
|
||||
import kotlinx.serialization.*
|
||||
import kotlinx.serialization.descriptors.SerialDescriptor
|
||||
import kotlinx.serialization.encoding.Decoder
|
||||
import kotlinx.serialization.encoding.Encoder
|
||||
|
||||
@Serializable
|
||||
data class PollAnswer(
|
||||
@SerialName(pollIdField)
|
||||
val pollId: PollIdentifier,
|
||||
@SerialName(userField)
|
||||
override val user: User,
|
||||
@SerialName(optionIdsField)
|
||||
@Serializable(PollAnswer.Companion::class)
|
||||
sealed interface PollAnswer: FromUser {
|
||||
val pollId: PollIdentifier
|
||||
override val user: User
|
||||
val chosen: List<Int>
|
||||
) : FromUser {
|
||||
@Transient
|
||||
override val from: User
|
||||
get() = user
|
||||
|
||||
@Serializable
|
||||
data class Public(
|
||||
@SerialName(pollIdField)
|
||||
override val pollId: PollIdentifier,
|
||||
@SerialName(userField)
|
||||
override val user: User,
|
||||
@SerialName(optionIdsField)
|
||||
override val chosen: List<Int>,
|
||||
) : PollAnswer
|
||||
|
||||
@Serializable
|
||||
data class Anonymous(
|
||||
@SerialName(pollIdField)
|
||||
override val pollId: PollIdentifier,
|
||||
@SerialName(voterChatField)
|
||||
val voterChat: ChannelChat,
|
||||
@SerialName(optionIdsField)
|
||||
override val chosen: List<Int>
|
||||
) : PollAnswer {
|
||||
@SerialName(userField)
|
||||
override val user: User = defaultUser
|
||||
|
||||
companion object {
|
||||
val defaultUser = CommonBot(
|
||||
UserId(136817688L),
|
||||
"",
|
||||
"",
|
||||
Username("@Channel_Bot")
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
companion object : KSerializer<PollAnswer> {
|
||||
@Serializable
|
||||
private data class PollAnswerSurrogate(
|
||||
@SerialName(pollIdField)
|
||||
val pollId: PollIdentifier,
|
||||
@SerialName(optionIdsField)
|
||||
val chosen: List<Int>,
|
||||
@SerialName(userField)
|
||||
val user: User = Anonymous.defaultUser,
|
||||
@SerialName(voterChatField)
|
||||
val voterChat: ChannelChat? = null
|
||||
)
|
||||
operator fun invoke(
|
||||
pollId: PollIdentifier,
|
||||
user: User,
|
||||
chosen: List<Int>,
|
||||
) = Public(pollId, user, chosen)
|
||||
|
||||
override val descriptor: SerialDescriptor
|
||||
get() = PollAnswerSurrogate.serializer().descriptor
|
||||
|
||||
override fun deserialize(decoder: Decoder): PollAnswer {
|
||||
val surrogate = PollAnswerSurrogate.serializer().deserialize(decoder)
|
||||
return if (surrogate.voterChat != null) {
|
||||
Anonymous(surrogate.pollId, surrogate.voterChat, surrogate.chosen)
|
||||
} else {
|
||||
Public(surrogate.pollId, surrogate.user, surrogate.chosen)
|
||||
}
|
||||
}
|
||||
|
||||
override fun serialize(encoder: Encoder, value: PollAnswer) {
|
||||
PollAnswerSurrogate.serializer().serialize(
|
||||
encoder,
|
||||
PollAnswerSurrogate(
|
||||
value.pollId,
|
||||
value.chosen,
|
||||
value.user,
|
||||
(value as? Anonymous) ?.voterChat
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,8 +7,9 @@ import kotlin.random.Random
|
||||
@Serializable
|
||||
@JvmInline
|
||||
value class RequestId(
|
||||
val int: Int
|
||||
val uShort: UShort
|
||||
) {
|
||||
constructor(int: Int) : this(int.toUShort())
|
||||
companion object {
|
||||
fun random() = RequestId(Random.nextInt())
|
||||
}
|
||||
|
||||
@@ -0,0 +1,6 @@
|
||||
package dev.inmo.tgbotapi.types.stories
|
||||
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable
|
||||
class Story
|
||||
@@ -126,6 +126,17 @@ import dev.inmo.tgbotapi.types.chat.ExtendedSupergroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.ForumChat
|
||||
import dev.inmo.tgbotapi.types.chat.GroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.PossiblyPremiumChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewBot
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChannelChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewForumChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewGroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewPrivateChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewPublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewSuperPublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewSupergroupChat
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewUser
|
||||
import dev.inmo.tgbotapi.types.chat.PreviewUsernameChat
|
||||
import dev.inmo.tgbotapi.types.chat.PrivateChat
|
||||
import dev.inmo.tgbotapi.types.chat.PublicChat
|
||||
import dev.inmo.tgbotapi.types.chat.SuperPublicChat
|
||||
@@ -292,6 +303,7 @@ import dev.inmo.tgbotapi.types.message.content.ResendableContent
|
||||
import dev.inmo.tgbotapi.types.message.content.SpoilerableMediaContent
|
||||
import dev.inmo.tgbotapi.types.message.content.StaticLocationContent
|
||||
import dev.inmo.tgbotapi.types.message.content.StickerContent
|
||||
import dev.inmo.tgbotapi.types.message.content.StoryContent
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.content.TextedContent
|
||||
import dev.inmo.tgbotapi.types.message.content.TextedMediaContent
|
||||
@@ -1968,12 +1980,30 @@ public inline fun Chat.userOrThrow(): User = this as dev.inmo.tgbotapi.types.cha
|
||||
|
||||
public inline fun <T> Chat.ifUser(block: (User) -> T): T? = userOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewUserOrNull(): PreviewUser? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewUser
|
||||
|
||||
public inline fun Chat.previewUserOrThrow(): PreviewUser = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewUser
|
||||
|
||||
public inline fun <T> Chat.ifPreviewUser(block: (PreviewUser) -> T): T? = previewUserOrNull()
|
||||
?.let(block)
|
||||
|
||||
public inline fun Chat.botOrNull(): Bot? = this as? dev.inmo.tgbotapi.types.chat.Bot
|
||||
|
||||
public inline fun Chat.botOrThrow(): Bot = this as dev.inmo.tgbotapi.types.chat.Bot
|
||||
|
||||
public inline fun <T> Chat.ifBot(block: (Bot) -> T): T? = botOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewBotOrNull(): PreviewBot? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewBot
|
||||
|
||||
public inline fun Chat.previewBotOrThrow(): PreviewBot = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewBot
|
||||
|
||||
public inline fun <T> Chat.ifPreviewBot(block: (PreviewBot) -> T): T? = previewBotOrNull()
|
||||
?.let(block)
|
||||
|
||||
public inline fun Chat.commonBotOrNull(): CommonBot? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.CommonBot
|
||||
|
||||
@@ -1991,6 +2021,87 @@ public inline fun Chat.commonUserOrThrow(): CommonUser = this as
|
||||
public inline fun <T> Chat.ifCommonUser(block: (CommonUser) -> T): T? = commonUserOrNull()
|
||||
?.let(block)
|
||||
|
||||
public inline fun Chat.previewChatOrNull(): PreviewChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
|
||||
public inline fun Chat.previewChatOrThrow(): PreviewChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewChat(block: (PreviewChat) -> T): T? = previewChatOrNull()
|
||||
?.let(block)
|
||||
|
||||
public inline fun Chat.previewUsernameChatOrNull(): PreviewUsernameChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewUsernameChat
|
||||
|
||||
public inline fun Chat.previewUsernameChatOrThrow(): PreviewUsernameChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewUsernameChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewUsernameChat(block: (PreviewUsernameChat) -> T): T? =
|
||||
previewUsernameChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewPrivateChatOrNull(): PreviewPrivateChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewPrivateChat
|
||||
|
||||
public inline fun Chat.previewPrivateChatOrThrow(): PreviewPrivateChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewPrivateChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewPrivateChat(block: (PreviewPrivateChat) -> T): T? =
|
||||
previewPrivateChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewPublicChatOrNull(): PreviewPublicChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewPublicChat
|
||||
|
||||
public inline fun Chat.previewPublicChatOrThrow(): PreviewPublicChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewPublicChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewPublicChat(block: (PreviewPublicChat) -> T): T? =
|
||||
previewPublicChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewSuperPublicChatOrNull(): PreviewSuperPublicChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewSuperPublicChat
|
||||
|
||||
public inline fun Chat.previewSuperPublicChatOrThrow(): PreviewSuperPublicChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewSuperPublicChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewSuperPublicChat(block: (PreviewSuperPublicChat) -> T): T? =
|
||||
previewSuperPublicChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewChannelChatOrNull(): PreviewChannelChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewChannelChat
|
||||
|
||||
public inline fun Chat.previewChannelChatOrThrow(): PreviewChannelChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewChannelChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewChannelChat(block: (PreviewChannelChat) -> T): T? =
|
||||
previewChannelChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewGroupChatOrNull(): PreviewGroupChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewGroupChat
|
||||
|
||||
public inline fun Chat.previewGroupChatOrThrow(): PreviewGroupChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewGroupChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewGroupChat(block: (PreviewGroupChat) -> T): T? =
|
||||
previewGroupChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewSupergroupChatOrNull(): PreviewSupergroupChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewSupergroupChat
|
||||
|
||||
public inline fun Chat.previewSupergroupChatOrThrow(): PreviewSupergroupChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewSupergroupChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewSupergroupChat(block: (PreviewSupergroupChat) -> T): T? =
|
||||
previewSupergroupChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.previewForumChatOrNull(): PreviewForumChat? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.PreviewForumChat
|
||||
|
||||
public inline fun Chat.previewForumChatOrThrow(): PreviewForumChat = this as
|
||||
dev.inmo.tgbotapi.types.chat.PreviewForumChat
|
||||
|
||||
public inline fun <T> Chat.ifPreviewForumChat(block: (PreviewForumChat) -> T): T? =
|
||||
previewForumChatOrNull() ?.let(block)
|
||||
|
||||
public inline fun Chat.unknownChatTypeOrNull(): UnknownChatType? = this as?
|
||||
dev.inmo.tgbotapi.types.chat.UnknownChatType
|
||||
|
||||
@@ -3480,6 +3591,15 @@ public inline fun ResendableContent.stickerContentOrThrow(): StickerContent = th
|
||||
public inline fun <T> ResendableContent.ifStickerContent(block: (StickerContent) -> T): T? =
|
||||
stickerContentOrNull() ?.let(block)
|
||||
|
||||
public inline fun ResendableContent.storyContentOrNull(): StoryContent? = this as?
|
||||
dev.inmo.tgbotapi.types.message.content.StoryContent
|
||||
|
||||
public inline fun ResendableContent.storyContentOrThrow(): StoryContent = this as
|
||||
dev.inmo.tgbotapi.types.message.content.StoryContent
|
||||
|
||||
public inline fun <T> ResendableContent.ifStoryContent(block: (StoryContent) -> T): T? =
|
||||
storyContentOrNull() ?.let(block)
|
||||
|
||||
public inline fun ResendableContent.textContentOrNull(): TextContent? = this as?
|
||||
dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
|
||||
|
||||
@@ -21,6 +21,7 @@ fun Flow<ContentMessage<*>>.onlyPhotoContentMessages() = withContentType<PhotoCo
|
||||
fun Flow<ContentMessage<*>>.onlyPollContentMessages() = withContentType<PollContent>()
|
||||
fun Flow<ContentMessage<*>>.onlyStickerContentMessages() = withContentType<StickerContent>()
|
||||
fun Flow<ContentMessage<*>>.onlyTextContentMessages() = withContentType<TextContent>()
|
||||
fun Flow<ContentMessage<*>>.onlyStoryContentMessages() = withContentType<StoryContent>()
|
||||
fun Flow<ContentMessage<*>>.onlyVenueContentMessages() = withContentType<VenueContent>()
|
||||
fun Flow<ContentMessage<*>>.onlyVideoContentMessages() = withContentType<VideoContent>()
|
||||
fun Flow<ContentMessage<*>>.onlyVideoNoteContentMessages() = withContentType<VideoNoteContent>()
|
||||
|
||||
@@ -0,0 +1,247 @@
|
||||
package dev.inmo.tgbotapi.extensions.utils.extensions
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.TextedWithTextSources
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.ContentMessage
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.textsources.BotCommandTextSource
|
||||
import dev.inmo.tgbotapi.types.message.textsources.TextSource
|
||||
|
||||
object TelegramBotCommandsDefaults {
|
||||
const val defaultArgsSeparator = " "
|
||||
val defaultArgsSeparatorRegex = Regex(defaultArgsSeparator)
|
||||
const val defaultNamesArgsSeparator = "="
|
||||
val defaultNamesArgsSeparatorRegex = Regex(defaultNamesArgsSeparator)
|
||||
}
|
||||
|
||||
@Deprecated(message = "Replaced", replaceWith = ReplaceWith("TelegramBotCommandsDefaults.defaultArgsSeparatorRegex", "dev.inmo.tgbotapi.extensions.utils.extensions.TelegramBotCommandsDefaults"))
|
||||
val defaultArgsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun List<TextSource>.parseCommandsWithArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
): MutableMap<String, Array<String>> {
|
||||
val result = mutableMapOf<String, Array<String>>()
|
||||
var currentBotCommandSource: BotCommandTextSource? = null
|
||||
var currentArgs = ""
|
||||
|
||||
fun includeCurrent() = currentBotCommandSource?.let {
|
||||
currentArgs = currentArgs.trim()
|
||||
result[it.command] = if (currentArgs.isNotEmpty()) {
|
||||
currentArgs.split(argsSeparator).toTypedArray()
|
||||
} else {
|
||||
emptyArray()
|
||||
}
|
||||
currentArgs = ""
|
||||
currentBotCommandSource = null
|
||||
}
|
||||
|
||||
for (textSource in this) {
|
||||
if (textSource is BotCommandTextSource) {
|
||||
includeCurrent()
|
||||
currentBotCommandSource = textSource
|
||||
} else {
|
||||
currentArgs += textSource.source
|
||||
}
|
||||
}
|
||||
includeCurrent()
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun TextedWithTextSources.parseCommandsWithArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
) = textSources?.parseCommandsWithArgs(argsSeparator) ?: emptyMap()
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun ContentMessage<TextContent>.parseCommandsWithArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
) = content.parseCommandsWithArgs(argsSeparator)
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun List<TextSource>.parseCommandsWithArgs(
|
||||
argsSeparator: String
|
||||
): MutableMap<String, Array<String>> = parseCommandsWithArgs(Regex(argsSeparator))
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun TextedWithTextSources.parseCommandsWithArgs(
|
||||
argsSeparator: String
|
||||
) = parseCommandsWithArgs(Regex(argsSeparator))
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun ContentMessage<TextContent>.parseCommandsWithArgs(
|
||||
argsSeparator: String
|
||||
) = parseCommandsWithArgs(Regex(argsSeparator))
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] to create base [argsSeparator] split args for commands and map their as k-v pairs.
|
||||
* Sample:
|
||||
*
|
||||
* ```bash
|
||||
* /command args1=value1 arg2=value2 arg1=value3
|
||||
* ```
|
||||
*
|
||||
* Will produce [Map] with one key `command` and the list of three pairs:
|
||||
*
|
||||
* 1. `args1` to `value1`
|
||||
* 2. `args2` to `value2`
|
||||
* 3. `args1` to `value3`
|
||||
*
|
||||
* @return Array of named arguments
|
||||
*/
|
||||
fun List<TextSource>.parseCommandsWithNamedArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
): Map<String, List<Pair<String, String>>> {
|
||||
val withArgs = parseCommandsWithArgs(argsSeparator)
|
||||
|
||||
return withArgs.mapValues { (k, v) ->
|
||||
v.flatMap {
|
||||
it.split(nameArgSeparator, 2).map { v -> it to v }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] to create base [argsSeparator] split args for commands and map their as k-v pairs.
|
||||
* Sample:
|
||||
*
|
||||
* ```bash
|
||||
* /command args1=value1 arg2=value2 arg1=value3
|
||||
* ```
|
||||
*
|
||||
* Will produce [Map] with one key `command` and the list of three pairs:
|
||||
*
|
||||
* 1. `args1` to `value1`
|
||||
* 2. `args2` to `value2`
|
||||
* 3. `args1` to `value3`
|
||||
*
|
||||
* @return Array of named arguments
|
||||
*/
|
||||
fun TextedWithTextSources.parseCommandsWithNamedArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
) = textSources?.parseCommandsWithNamedArgs(argsSeparator = argsSeparator, nameArgSeparator = nameArgSeparator) ?: emptyMap()
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] to create base [argsSeparator] split args for commands and map their as k-v pairs.
|
||||
* Sample:
|
||||
*
|
||||
* ```bash
|
||||
* /command args1=value1 arg2=value2 arg1=value3
|
||||
* ```
|
||||
*
|
||||
* Will produce [Map] with one key `command` and the list of three pairs:
|
||||
*
|
||||
* 1. `args1` to `value1`
|
||||
* 2. `args2` to `value2`
|
||||
* 3. `args1` to `value3`
|
||||
*
|
||||
* @return Array of named arguments
|
||||
*/
|
||||
fun ContentMessage<TextContent>.parseCommandsWithNamedArgs(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
) = content.parseCommandsWithNamedArgs(argsSeparator = argsSeparator, nameArgSeparator = nameArgSeparator)
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] to create base [argsSeparator] split args for commands and map their as k-v pairs.
|
||||
* Sample:
|
||||
*
|
||||
* ```bash
|
||||
* /command args1=value1 arg2=value2 arg1=value3
|
||||
* ```
|
||||
*
|
||||
* Will produce [Map] with one key `command` and the list of three pairs:
|
||||
*
|
||||
* 1. `args1` to `value1`
|
||||
* 2. `args2` to `value2`
|
||||
* 3. `args1` to `value3`
|
||||
*
|
||||
* @return Array of named arguments
|
||||
*/
|
||||
fun List<TextSource>.parseCommandsWithNamedArgs(
|
||||
argsSeparator: String,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
): Map<String, List<Pair<String, String>>> = parseCommandsWithNamedArgs(Regex(pattern = argsSeparator), nameArgSeparator)
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] to create base [argsSeparator] split args for commands and map their as k-v pairs.
|
||||
* Sample:
|
||||
*
|
||||
* ```bash
|
||||
* /command args1=value1 arg2=value2 arg1=value3
|
||||
* ```
|
||||
*
|
||||
* Will produce [Map] with one key `command` and the list of three pairs:
|
||||
*
|
||||
* 1. `args1` to `value1`
|
||||
* 2. `args2` to `value2`
|
||||
* 3. `args1` to `value3`
|
||||
*
|
||||
* @return Array of named arguments
|
||||
*/
|
||||
fun TextedWithTextSources.parseCommandsWithNamedArgs(
|
||||
argsSeparator: String,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
) = parseCommandsWithNamedArgs(argsSeparator = Regex(pattern = argsSeparator), nameArgSeparator = nameArgSeparator)
|
||||
|
||||
/**
|
||||
* Uses [parseCommandsWithArgs] to create base [argsSeparator] split args for commands and map their as k-v pairs.
|
||||
* Sample:
|
||||
*
|
||||
* ```bash
|
||||
* /command args1=value1 arg2=value2 arg1=value3
|
||||
* ```
|
||||
*
|
||||
* Will produce [Map] with one key `command` and the list of three pairs:
|
||||
*
|
||||
* 1. `args1` to `value1`
|
||||
* 2. `args2` to `value2`
|
||||
* 3. `args1` to `value3`
|
||||
*
|
||||
* @return Array of named arguments
|
||||
*/
|
||||
fun ContentMessage<TextContent>.parseCommandsWithNamedArgs(
|
||||
argsSeparator: String,
|
||||
nameArgSeparator: Regex = TelegramBotCommandsDefaults.defaultNamesArgsSeparatorRegex,
|
||||
) = parseCommandsWithNamedArgs(argsSeparator = Regex(pattern = argsSeparator), nameArgSeparator = nameArgSeparator)
|
||||
|
||||
|
||||
// Deprecations
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
@Deprecated("Renamed", ReplaceWith("parseCommandsWithArgs(argsSeparator)", "dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgs"))
|
||||
fun List<TextSource>.parseCommandsWithParams(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
): MutableMap<String, Array<String>> = parseCommandsWithArgs(argsSeparator)
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
@Deprecated("Renamed", ReplaceWith("parseCommandsWithArgs(argsSeparator)", "dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgs"))
|
||||
fun TextedWithTextSources.parseCommandsWithParams(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
) = parseCommandsWithArgs(argsSeparator)
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
@Deprecated("Renamed", ReplaceWith("parseCommandsWithArgs(argsSeparator)", "dev.inmo.tgbotapi.extensions.utils.extensions.parseCommandsWithArgs"))
|
||||
fun ContentMessage<TextContent>.parseCommandsWithParams(
|
||||
argsSeparator: Regex = TelegramBotCommandsDefaults.defaultArgsSeparatorRegex
|
||||
) = parseCommandsWithArgs(argsSeparator)
|
||||
@@ -0,0 +1,53 @@
|
||||
package dev.inmo.tgbotapi.extensions.utils.extensions
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.TextedWithTextSources
|
||||
import dev.inmo.tgbotapi.extensions.utils.botCommandTextSourceOrNull
|
||||
import dev.inmo.tgbotapi.extensions.utils.ifBotCommandTextSource
|
||||
import dev.inmo.tgbotapi.extensions.utils.whenBotCommandTextSource
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.ContentMessage
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.textsources.BotCommandTextSource
|
||||
import dev.inmo.tgbotapi.types.message.textsources.TextSource
|
||||
|
||||
// Sources
|
||||
|
||||
/**
|
||||
* Parse text sources to find commands with their arguments. This method will skip all the text sources __before__
|
||||
* first command and all following text sources until the next command will be guessed as an args of last found command
|
||||
*/
|
||||
fun List<TextSource>.parseCommandsWithArgsSources(): Map<BotCommandTextSource, Array<TextSource>> {
|
||||
var currentCommandTextSource: BotCommandTextSource? = null
|
||||
val currentArgs = mutableListOf<TextSource>()
|
||||
val result = mutableMapOf<BotCommandTextSource, Array<TextSource>>()
|
||||
|
||||
fun addCurrentCommandToResult() {
|
||||
currentCommandTextSource ?.let {
|
||||
result[it] = currentArgs.toTypedArray()
|
||||
currentArgs.clear()
|
||||
}
|
||||
}
|
||||
|
||||
forEach {
|
||||
it.whenBotCommandTextSource {
|
||||
addCurrentCommandToResult()
|
||||
currentCommandTextSource = it
|
||||
return@forEach
|
||||
}
|
||||
currentArgs.add(it)
|
||||
}
|
||||
addCurrentCommandToResult()
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse text sources to find commands with their arguments. This method will skip all the text sources __before__
|
||||
* first command and all following text sources until the next command will be guessed as an args of last found command
|
||||
*/
|
||||
fun TextedWithTextSources.parseCommandsWithArgsSources() = textSources?.parseCommandsWithArgsSources() ?: emptyMap()
|
||||
|
||||
/**
|
||||
* Parse text sources to find commands with their arguments. This method will skip all the text sources __before__
|
||||
* first command and all following text sources until the next command will be guessed as an args of last found command
|
||||
*/
|
||||
fun ContentMessage<TextContent>.parseCommandsWithArgsSources() = content.parseCommandsWithArgsSources()
|
||||
@@ -1,7 +1,7 @@
|
||||
package dev.inmo.tgbotapi.extensions.utils.extensions
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.FromUser
|
||||
import dev.inmo.tgbotapi.abstracts.WithChat
|
||||
import dev.inmo.tgbotapi.abstracts.WithPreviewChat
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
import dev.inmo.tgbotapi.types.UserId
|
||||
import dev.inmo.tgbotapi.types.chat.Chat
|
||||
@@ -15,13 +15,13 @@ import kotlinx.coroutines.flow.transform
|
||||
* Will pass only those [T] which have [sameChat] as [chatId]
|
||||
*/
|
||||
@Suppress("NOTHING_TO_INLINE")
|
||||
inline fun <T : WithChat> Flow<T>.fromChat(chatId: ChatIdentifier): Flow<T> = filter { it.sameChat(chatId) }
|
||||
inline fun <T : WithPreviewChat> Flow<T>.fromChat(chatId: ChatIdentifier): Flow<T> = filter { it.sameChat(chatId) }
|
||||
|
||||
/**
|
||||
* Will pass only those [T] which have [sameChat] as [chatId]
|
||||
*/
|
||||
@Suppress("NOTHING_TO_INLINE")
|
||||
inline fun <T : WithChat> Flow<T>.fromChat(chat: Chat): Flow<T> = fromChat(chat.id)
|
||||
inline fun <T : WithPreviewChat> Flow<T>.fromChat(chat: Chat): Flow<T> = fromChat(chat.id)
|
||||
|
||||
/**
|
||||
* @return [Flow] with the [FromUser.user] field [User.id] the same as [userId]
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
package dev.inmo.tgbotapi.extensions.utils.extensions
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.WithChat
|
||||
import dev.inmo.tgbotapi.abstracts.WithPreviewChat
|
||||
import dev.inmo.tgbotapi.extensions.utils.usernameChatOrNull
|
||||
import dev.inmo.tgbotapi.extensions.utils.whenUsernameChat
|
||||
import dev.inmo.tgbotapi.types.ChatIdentifier
|
||||
@@ -16,21 +16,23 @@ import dev.inmo.tgbotapi.utils.extensions.threadIdOrNull
|
||||
* @return true in case if [this] message is placed in the chat with id == [chatId]
|
||||
*/
|
||||
@Suppress("NOTHING_TO_INLINE")
|
||||
inline fun WithChat.sameChat(chatId: ChatIdentifier) = chat.id == chatId || (chatId is Username && chat.whenUsernameChat {
|
||||
it.username == chatId
|
||||
} ?: false)
|
||||
inline fun WithPreviewChat.sameChat(chatId: ChatIdentifier) =
|
||||
chat.id == chatId || (chatId is Username && chat.whenUsernameChat {
|
||||
it.username == chatId
|
||||
} ?: false)
|
||||
|
||||
/**
|
||||
* @return true in case if [this] message is placed in the [chat]
|
||||
*/
|
||||
@Suppress("NOTHING_TO_INLINE")
|
||||
inline fun WithChat.sameChat(chat: Chat) = sameChat(chat.id) || chat.usernameChatOrNull() ?.username ?.let { sameChat(it) } ?: false
|
||||
inline fun WithPreviewChat.sameChat(chat: Chat) =
|
||||
sameChat(chat.id) || chat.usernameChatOrNull()?.username?.let { sameChat(it) } ?: false
|
||||
|
||||
/**
|
||||
* @return true in case if [this] message is placed in the same chat that [other]
|
||||
*/
|
||||
@Suppress("NOTHING_TO_INLINE")
|
||||
inline fun WithChat.sameChat(other: Message) = sameChat(other.chat)
|
||||
inline fun WithPreviewChat.sameChat(other: Message) = sameChat(other.chat)
|
||||
|
||||
/**
|
||||
* @return true in case if [this] message is from the same chat (with id == [chatId]) and [this] [Message.messageId]
|
||||
|
||||
@@ -1,54 +0,0 @@
|
||||
package dev.inmo.tgbotapi.extensions.utils.extensions
|
||||
|
||||
import dev.inmo.tgbotapi.abstracts.TextedWithTextSources
|
||||
import dev.inmo.tgbotapi.types.message.abstracts.ContentMessage
|
||||
import dev.inmo.tgbotapi.types.message.content.TextContent
|
||||
import dev.inmo.tgbotapi.types.message.textsources.BotCommandTextSource
|
||||
import dev.inmo.tgbotapi.types.message.textsources.TextSource
|
||||
|
||||
|
||||
val defaultArgsSeparator = Regex(" ")
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun List<TextSource>.parseCommandsWithParams(
|
||||
argsSeparator: Regex = defaultArgsSeparator
|
||||
): MutableMap<String, Array<String>> {
|
||||
val result = mutableMapOf<String, Array<String>>()
|
||||
var currentBotCommandSource: BotCommandTextSource? = null
|
||||
var currentArgs = ""
|
||||
fun includeCurrent() = currentBotCommandSource ?.let {
|
||||
currentArgs = currentArgs.trim()
|
||||
result[it.command] = if (currentArgs.isNotEmpty()) {
|
||||
currentArgs.split(argsSeparator).toTypedArray()
|
||||
} else {
|
||||
emptyArray()
|
||||
}
|
||||
currentArgs = ""
|
||||
currentBotCommandSource = null
|
||||
}
|
||||
for (textSource in this) {
|
||||
if (textSource is BotCommandTextSource) {
|
||||
includeCurrent()
|
||||
currentBotCommandSource = textSource
|
||||
} else {
|
||||
currentArgs += textSource.source
|
||||
}
|
||||
}
|
||||
includeCurrent()
|
||||
return result
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun TextedWithTextSources.parseCommandsWithParams(
|
||||
argsSeparator: Regex = defaultArgsSeparator
|
||||
) = textSources ?.parseCommandsWithParams(argsSeparator) ?: emptyMap()
|
||||
|
||||
/**
|
||||
* Parse commands and their args. Logic will find command, get all subsequent data as args until new command
|
||||
*/
|
||||
fun ContentMessage<TextContent>.parseCommandsWithParams(
|
||||
argsSeparator: Regex = defaultArgsSeparator
|
||||
) = content.parseCommandsWithParams(argsSeparator)
|
||||
@@ -120,6 +120,11 @@ fun FlowsUpdatesFilter.textMessages(
|
||||
scopeToIncludeChannels: CoroutineScope? = null
|
||||
) = filterContentMessages<TextContent>(scopeToIncludeChannels)
|
||||
|
||||
fun Flow<BaseSentMessageUpdate>.storyMessages() = filterContentMessages<StoryContent>()
|
||||
fun FlowsUpdatesFilter.storyMessages(
|
||||
scopeToIncludeChannels: CoroutineScope? = null
|
||||
) = filterContentMessages<StoryContent>(scopeToIncludeChannels)
|
||||
|
||||
fun Flow<BaseSentMessageUpdate>.venueMessages() = filterContentMessages<VenueContent>()
|
||||
fun FlowsUpdatesFilter.venueMessages(
|
||||
scopeToIncludeChannels: CoroutineScope? = null
|
||||
|
||||
@@ -3,7 +3,7 @@ package dev.inmo.tgbotapi.extensions.utils.types.buttons
|
||||
import dev.inmo.tgbotapi.types.buttons.*
|
||||
import dev.inmo.tgbotapi.types.buttons.reply.requestChatReplyButton
|
||||
import dev.inmo.tgbotapi.types.buttons.reply.requestUserReplyButton
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.chat.member.ChatCommonAdministratorRights
|
||||
import dev.inmo.tgbotapi.types.request.RequestId
|
||||
import dev.inmo.tgbotapi.types.webapps.WebAppInfo
|
||||
import dev.inmo.tgbotapi.utils.*
|
||||
@@ -220,8 +220,8 @@ inline fun ReplyKeyboardRowBuilder.requestChatButton(
|
||||
isForum: Boolean? = null,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean? = null
|
||||
) = requestChatButton(
|
||||
text,
|
||||
@@ -248,8 +248,8 @@ inline fun ReplyKeyboardRowBuilder.requestChannelButton(
|
||||
requestId: RequestId,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean? = null
|
||||
) = requestChatButton(
|
||||
text,
|
||||
@@ -275,8 +275,8 @@ inline fun ReplyKeyboardRowBuilder.requestGroupButton(
|
||||
isForum: Boolean? = null,
|
||||
isPublic: Boolean? = null,
|
||||
isOwnedBy: Boolean? = null,
|
||||
userRightsInChat: ChatAdministratorRights? = null,
|
||||
botRightsInChat: ChatAdministratorRights? = null,
|
||||
userRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botRightsInChat: ChatCommonAdministratorRights? = null,
|
||||
botIsMember: Boolean? = null
|
||||
) = requestChatButton(
|
||||
text,
|
||||
|
||||
@@ -8,7 +8,9 @@ sealed interface Color {
|
||||
value class BackgroundColor(override val value: String) : Color
|
||||
|
||||
@Serializable
|
||||
value class Hex(override val value: String) : Color
|
||||
value class Hex(override val value: String) : Color {
|
||||
constructor(r: UByte, g: UByte, b: UByte) : this("#${r.toString(16).padStart(2, '0')}${g.toString(16).padStart(2, '0')}${b.toString(16).padStart(2, '0')}")
|
||||
}
|
||||
|
||||
companion object {
|
||||
val BackgroundColor = BackgroundColor("bg_color")
|
||||
|
||||
@@ -8,3 +8,5 @@ typealias InvoiceClosedEventHandler = WebApp.(InvoiceClosedInfo) -> Unit
|
||||
typealias PopupClosedEventHandler = WebApp.(String?) -> Unit
|
||||
typealias QRTextReceivedEventHandler = WebApp.(String) -> Boolean
|
||||
typealias TextReceivedEventHandler = WebApp.(String) -> Unit
|
||||
typealias WriteAccessRequestedHandler = WebApp.(Boolean) -> Unit
|
||||
typealias ContactRequestedHandler = WebApp.(Boolean) -> Unit
|
||||
|
||||
@@ -10,4 +10,6 @@ sealed class EventType(val typeName: String) {
|
||||
object PopupClosed : EventType("popupClosed")
|
||||
object QRTextReceived : EventType("qrTextReceived")
|
||||
object ClipboardTextReceived : EventType("clipboardTextReceived")
|
||||
object WriteAccessRequested : EventType("writeAccessRequested")
|
||||
object ContactRequested : EventType("contactRequested")
|
||||
}
|
||||
|
||||
@@ -0,0 +1,14 @@
|
||||
package dev.inmo.tgbotapi.webapps
|
||||
|
||||
external interface RequestStatus {
|
||||
val status: String
|
||||
}
|
||||
|
||||
inline val RequestStatus.isCancelled: Boolean
|
||||
get() = status == "cancelled"
|
||||
|
||||
inline val RequestStatus.isAllowed: Boolean
|
||||
get() = status == "allowed"
|
||||
|
||||
inline val RequestStatus.isSent: Boolean
|
||||
get() = status == "sent"
|
||||
@@ -1,9 +1,11 @@
|
||||
package dev.inmo.tgbotapi.webapps
|
||||
|
||||
import dev.inmo.tgbotapi.utils.TelegramAPIUrlsKeeper
|
||||
import dev.inmo.tgbotapi.webapps.cloud.CloudStorage
|
||||
import dev.inmo.tgbotapi.webapps.haptic.HapticFeedback
|
||||
import dev.inmo.tgbotapi.webapps.invoice.InvoiceClosedInfo
|
||||
import dev.inmo.tgbotapi.webapps.popup.*
|
||||
import kotlin.js.Json
|
||||
|
||||
external class WebApp {
|
||||
val version: String
|
||||
@@ -15,6 +17,7 @@ external class WebApp {
|
||||
|
||||
val headerColor: HEXColor?
|
||||
fun setHeaderColor(color: Color.BackgroundColor)
|
||||
fun setHeaderColor(color: Color.Hex)
|
||||
val backgroundColor: HEXColor?
|
||||
fun setBackgroundColor(color: Color.Hex)
|
||||
fun setBackgroundColor(color: Color.BackgroundColor)
|
||||
@@ -48,6 +51,9 @@ external class WebApp {
|
||||
@JsName("HapticFeedback")
|
||||
val hapticFeedback: HapticFeedback
|
||||
|
||||
@JsName("CloudStorage")
|
||||
val cloudStorage: CloudStorage
|
||||
|
||||
internal fun onEvent(type: String, callback: () -> Unit)
|
||||
@JsName("onEvent")
|
||||
internal fun onEventWithViewportChangedData(type: String, callback: (ViewportChangedData) -> Unit)
|
||||
@@ -59,6 +65,10 @@ external class WebApp {
|
||||
internal fun onEventWithQRTextInfo(type: String, callback: (String) -> Boolean)
|
||||
@JsName("onEvent")
|
||||
internal fun onEventWithTextInfo(type: String, callback: (String) -> Unit)
|
||||
@JsName("onEvent")
|
||||
internal fun onEventWithWriteAccessRequested(type: String, callback: (RequestStatus) -> Unit)
|
||||
@JsName("onEvent")
|
||||
internal fun onEventWithContactRequested(type: String, callback: (RequestStatus) -> Unit)
|
||||
|
||||
fun offEvent(type: String, callback: () -> Unit)
|
||||
@JsName("offEvent")
|
||||
@@ -76,6 +86,9 @@ external class WebApp {
|
||||
fun openLink(url: String)
|
||||
fun openTelegramLink(url: String)
|
||||
fun openInvoice(url: String, callback: (InvoiceClosedInfo) -> Unit = definedExternally)
|
||||
|
||||
fun requestWriteAccess(callback: ((Boolean) -> Unit)? = definedExternally)
|
||||
fun requestContact(callback: ((Boolean) -> Unit)? = definedExternally)
|
||||
}
|
||||
|
||||
val WebApp.colorScheme: ColorScheme
|
||||
@@ -157,6 +170,30 @@ fun WebApp.onEvent(type: EventType.ClipboardTextReceived, eventHandler: TextRece
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The callback which should be used in case you want to turn off events handling
|
||||
*/
|
||||
fun WebApp.onEvent(type: EventType.WriteAccessRequested, eventHandler: WriteAccessRequestedHandler) = { it: RequestStatus ->
|
||||
eventHandler(js("this").unsafeCast<WebApp>(), it.isAllowed)
|
||||
}.also {
|
||||
onEventWithWriteAccessRequested(
|
||||
type.typeName,
|
||||
callback = it
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The callback which should be used in case you want to turn off events handling
|
||||
*/
|
||||
fun WebApp.onEvent(type: EventType.ContactRequested, eventHandler: ContactRequestedHandler) = { it: RequestStatus ->
|
||||
eventHandler(js("this").unsafeCast<WebApp>(), it.isSent)
|
||||
}.also {
|
||||
onEventWithContactRequested(
|
||||
type.typeName,
|
||||
callback = it
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The callback which should be used in case you want to turn off events handling
|
||||
*/
|
||||
@@ -193,6 +230,14 @@ fun WebApp.onQRTextReceived(eventHandler: QRTextReceivedEventHandler) = onEvent(
|
||||
* @return The callback which should be used in case you want to turn off events handling
|
||||
*/
|
||||
fun WebApp.onClipboardTextReceived(eventHandler: TextReceivedEventHandler) = onEvent(EventType.ClipboardTextReceived, eventHandler)
|
||||
/**
|
||||
* @return The callback which should be used in case you want to turn off events handling
|
||||
*/
|
||||
fun WebApp.onWriteAccessRequested(eventHandler: WriteAccessRequestedHandler) = onEvent(EventType.WriteAccessRequested, eventHandler)
|
||||
/**
|
||||
* @return The callback which should be used in case you want to turn off events handling
|
||||
*/
|
||||
fun WebApp.onContactRequested(eventHandler: ContactRequestedHandler) = onEvent(EventType.ContactRequested, eventHandler)
|
||||
|
||||
fun WebApp.isInitDataSafe(botToken: String) = TelegramAPIUrlsKeeper(botToken).checkWebAppData(
|
||||
initData,
|
||||
|
||||
@@ -20,6 +20,10 @@ external interface WebAppUser {
|
||||
val is_premium: Boolean?
|
||||
@JsName(photoUrlField)
|
||||
val photoUrl: String?
|
||||
@JsName(addedToAttachmentMenuField)
|
||||
val addedToAttachmentMenu: Boolean?
|
||||
@JsName(allowsWriteToPMField)
|
||||
val allowsWriteToPM: Boolean?
|
||||
}
|
||||
|
||||
val WebAppUser.isPremium
|
||||
|
||||
@@ -0,0 +1,139 @@
|
||||
package dev.inmo.tgbotapi.webapps.cloud
|
||||
|
||||
import kotlin.js.Json
|
||||
|
||||
external interface CloudStorage {
|
||||
fun setItem(
|
||||
key: CloudStorageKey,
|
||||
value: CloudStorageValue,
|
||||
callback: (e: Any?, success: Boolean?) -> Unit = definedExternally
|
||||
): CloudStorage
|
||||
fun getItem(
|
||||
key: CloudStorageKey,
|
||||
callback: (e: Any?, value: CloudStorageValue?) -> Unit
|
||||
): CloudStorage
|
||||
fun getItems(
|
||||
key: Array<CloudStorageKey>,
|
||||
callback: (e: Any?, values: Array<CloudStorageValue>?) -> Unit
|
||||
): CloudStorage
|
||||
fun removeItem(
|
||||
key: CloudStorageKey,
|
||||
callback: (e: Any?, success: Boolean?) -> Unit
|
||||
): CloudStorage
|
||||
fun removeItems(
|
||||
key: Array<CloudStorageKey>,
|
||||
callback: (e: Any?, success: Boolean?) -> Unit
|
||||
): CloudStorage
|
||||
fun getKeys(
|
||||
callback: (e: Any?, success: Array<CloudStorageKey>?) -> Unit
|
||||
): CloudStorage
|
||||
}
|
||||
|
||||
private fun <T> resultsToResult(e: Any?, v: T?): Result<T> = when {
|
||||
e != null -> Result.failure(IllegalStateException(JSON.stringify(e)))
|
||||
v != null -> Result.success(v)
|
||||
else -> Result.failure(IllegalStateException("Both value and e"))
|
||||
}
|
||||
|
||||
fun CloudStorage.set(
|
||||
key: String,
|
||||
value: String,
|
||||
callback: (result: Result<Boolean>) -> Unit = {}
|
||||
) = setItem(CloudStorageKey(key), CloudStorageValue(value)) { e, v -> callback(resultsToResult(e, v)) }
|
||||
|
||||
fun CloudStorage.get(
|
||||
key: CloudStorageKey,
|
||||
callback: (result: Result<CloudStorageValue>) -> Unit
|
||||
) = getItem(key) { e, v -> callback(resultsToResult(e, v)) }
|
||||
|
||||
fun CloudStorage.get(
|
||||
key: String,
|
||||
callback: (result: Result<CloudStorageValue>) -> Unit
|
||||
) = get(CloudStorageKey(key), callback)
|
||||
|
||||
fun CloudStorage.get(
|
||||
keys: Array<CloudStorageKey>,
|
||||
callback: (result: Result<Array<CloudStorageValue>>) -> Unit
|
||||
) = getItems(
|
||||
keys
|
||||
) { e, v -> callback(resultsToResult(e, v)) }
|
||||
|
||||
fun CloudStorage.get(
|
||||
keys: Array<String>,
|
||||
callback: (result: Result<Array<CloudStorageValue>>) -> Unit
|
||||
) = get(
|
||||
Array(keys.size) {
|
||||
CloudStorageKey(keys[it])
|
||||
},
|
||||
callback
|
||||
)
|
||||
|
||||
fun CloudStorage.get(
|
||||
key: String,
|
||||
key2: String,
|
||||
vararg otherKeys: String,
|
||||
callback: (result: Result<Array<CloudStorageValue>>) -> Unit
|
||||
) = get(
|
||||
arrayOf(key, key2) + otherKeys,
|
||||
callback
|
||||
)
|
||||
|
||||
fun CloudStorage.remove(
|
||||
key: CloudStorageKey,
|
||||
callback: (result: Result<Boolean>) -> Unit
|
||||
) = removeItem(key) { e, v -> callback(resultsToResult(e, v)) }
|
||||
|
||||
fun CloudStorage.remove(
|
||||
key: String,
|
||||
callback: (result: Result<Boolean>) -> Unit
|
||||
) = remove(CloudStorageKey(key), callback)
|
||||
|
||||
fun CloudStorage.remove(
|
||||
keys: Array<CloudStorageKey>,
|
||||
callback: (result: Result<Boolean>) -> Unit
|
||||
) = removeItems(
|
||||
keys
|
||||
) { e, v -> callback(resultsToResult(e, v)) }
|
||||
|
||||
fun CloudStorage.remove(
|
||||
keys: Array<String>,
|
||||
callback: (result: Result<Boolean>) -> Unit
|
||||
) = remove(
|
||||
Array(keys.size) {
|
||||
CloudStorageKey(keys[it])
|
||||
},
|
||||
callback
|
||||
)
|
||||
|
||||
fun CloudStorage.remove(
|
||||
key: String,
|
||||
key2: String,
|
||||
vararg otherKeys: String,
|
||||
callback: (result: Result<Boolean>) -> Unit
|
||||
) = remove(
|
||||
arrayOf(key, key2) + otherKeys,
|
||||
callback
|
||||
)
|
||||
|
||||
fun CloudStorage.keys(
|
||||
callback: (result: Result<Array<CloudStorageKey>>) -> Unit
|
||||
) = getKeys { e, v -> callback(resultsToResult(e, v)) }
|
||||
|
||||
fun CloudStorage.getAll(callback: (result: Result<Map<CloudStorageKey, CloudStorageValue>>) -> Unit) = keys {
|
||||
it.onSuccess { keys ->
|
||||
console.log(keys)
|
||||
get(keys) {
|
||||
it.onSuccess { values ->
|
||||
console.log(values)
|
||||
val resultMap = keys.withIndex().mapNotNull { (i, it) ->
|
||||
it to (values.getOrNull(i) ?: return@mapNotNull null)
|
||||
}.toMap()
|
||||
callback(Result.success(resultMap))
|
||||
}.onFailure {
|
||||
callback(Result.failure(it))
|
||||
}
|
||||
}
|
||||
}.onFailure {
|
||||
callback(Result.failure(it))
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
package dev.inmo.tgbotapi.webapps.cloud
|
||||
|
||||
import dev.inmo.tgbotapi.types.cloudStorageKeyRegex
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable
|
||||
value class CloudStorageKey(val key: String) {
|
||||
init {
|
||||
require(key.matches(cloudStorageKeyRegex)) {
|
||||
"'$key' must pass $cloudStorageKeyRegex in case you wish to use it as key for cloud storage operations"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
package dev.inmo.tgbotapi.webapps.cloud
|
||||
|
||||
import dev.inmo.tgbotapi.types.cloudStorageKeyRegex
|
||||
import dev.inmo.tgbotapi.types.cloudStorageValueRegex
|
||||
import kotlinx.serialization.Serializable
|
||||
|
||||
@Serializable
|
||||
value class CloudStorageValue(val value: String) {
|
||||
init {
|
||||
require(value.matches(cloudStorageValueRegex)) {
|
||||
"'$value' must pass $cloudStorageValueRegex in case you wish to use it as key for cloud storage operations"
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user