1
0
mirror of https://github.com/InsanusMokrassar/TelegramBotAPI.git synced 2024-11-25 11:38:45 +00:00

complete Star Transactions abstractions

This commit is contained in:
InsanusMokrassar 2024-06-23 15:11:03 +06:00
parent 66cf0689e1
commit 63a695dcc5
7 changed files with 206 additions and 46 deletions

View File

@ -558,6 +558,7 @@ const val secretField = "secret"
const val errorsField = "errors" const val errorsField = "errors"
const val sourceField = "source" const val sourceField = "source"
const val receiverField = "receiver"
const val isUnclaimedField = "is_unclaimed" const val isUnclaimedField = "is_unclaimed"
const val fieldNameField = "field_name" const val fieldNameField = "field_name"
const val dataHashField = "data_hash" const val dataHashField = "data_hash"
@ -565,6 +566,7 @@ const val fileHashField = "file_hash"
const val fileHashesField = "file_hashes" const val fileHashesField = "file_hashes"
const val messageField = "message" const val messageField = "message"
const val unspecifiedField = "unspecified" const val unspecifiedField = "unspecified"
const val transactionsField = "transactions"
const val secureDataField = "secure_data" const val secureDataField = "secure_data"
const val nonceField = "nonce" const val nonceField = "nonce"

View File

@ -0,0 +1,10 @@
package dev.inmo.tgbotapi.types
import kotlinx.serialization.Serializable
import kotlin.jvm.JvmInline
@Serializable
@JvmInline
value class StarTransactionId(
val string: String
)

View File

@ -2,6 +2,7 @@ package dev.inmo.tgbotapi.types.payments.stars
import dev.inmo.tgbotapi.types.TelegramDate import dev.inmo.tgbotapi.types.TelegramDate
import dev.inmo.tgbotapi.utils.decodeDataAndJson import dev.inmo.tgbotapi.utils.decodeDataAndJson
import dev.inmo.tgbotapi.utils.internal.ClassCastsIncluded
import kotlinx.serialization.KSerializer import kotlinx.serialization.KSerializer
import kotlinx.serialization.Serializable import kotlinx.serialization.Serializable
import kotlinx.serialization.descriptors.SerialDescriptor import kotlinx.serialization.descriptors.SerialDescriptor
@ -11,6 +12,7 @@ import kotlinx.serialization.json.JsonElement
@Suppress("SERIALIZER_TYPE_INCOMPATIBLE") @Suppress("SERIALIZER_TYPE_INCOMPATIBLE")
@Serializable(RevenueWithdrawalState.Companion::class) @Serializable(RevenueWithdrawalState.Companion::class)
@ClassCastsIncluded
sealed interface RevenueWithdrawalState { sealed interface RevenueWithdrawalState {
val type: String val type: String

View File

@ -1,14 +1,13 @@
package dev.inmo.tgbotapi.types.payments.stars package dev.inmo.tgbotapi.types.payments.stars
import dev.inmo.tgbotapi.types.TelegramDate import dev.inmo.tgbotapi.types.*
import dev.inmo.tgbotapi.types.UserId
import dev.inmo.tgbotapi.types.chat.PreviewUser import dev.inmo.tgbotapi.types.chat.PreviewUser
import dev.inmo.tgbotapi.types.userField
import dev.inmo.tgbotapi.types.withdrawalStateField
import dev.inmo.tgbotapi.utils.decodeDataAndJson import dev.inmo.tgbotapi.utils.decodeDataAndJson
import dev.inmo.tgbotapi.utils.internal.ClassCastsIncluded
import kotlinx.serialization.KSerializer import kotlinx.serialization.KSerializer
import kotlinx.serialization.SerialName import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable import kotlinx.serialization.Serializable
import kotlinx.serialization.Transient
import kotlinx.serialization.descriptors.SerialDescriptor import kotlinx.serialization.descriptors.SerialDescriptor
import kotlinx.serialization.encoding.Decoder import kotlinx.serialization.encoding.Decoder
import kotlinx.serialization.encoding.Encoder import kotlinx.serialization.encoding.Encoder
@ -16,7 +15,9 @@ import kotlinx.serialization.json.JsonElement
@Suppress("SERIALIZER_TYPE_INCOMPATIBLE") @Suppress("SERIALIZER_TYPE_INCOMPATIBLE")
@Serializable(StarTransaction.Companion::class) @Serializable(StarTransaction.Companion::class)
@ClassCastsIncluded
sealed interface StarTransaction { sealed interface StarTransaction {
val id: StarTransactionId
val amount: Int val amount: Int
val date: TelegramDate val date: TelegramDate
val partner: TransactionPartner val partner: TransactionPartner
@ -25,44 +26,58 @@ sealed interface StarTransaction {
@Serializable(StarTransaction.Companion::class) @Serializable(StarTransaction.Companion::class)
data class Incoming( data class Incoming(
@SerialName(idField)
override val id: StarTransactionId,
@SerialName(amountField)
override val amount: Int,
@SerialName(dateField)
override val date: TelegramDate,
@SerialName(sourceField)
override val partner: TransactionPartner
) : StarTransaction { ) : StarTransaction {
override val type: String @Transient
get() = Companion.type override val source: TransactionPartner
get() = partner
companion object { override val receiver: TransactionPartner?
const val type: String = "fragment" get() = null
}
} }
@Serializable(StarTransaction.Companion::class) @Serializable(StarTransaction.Companion::class)
data class User( data class Outgoing(
@SerialName(userField) @SerialName(idField)
val user: PreviewUser override val id: StarTransactionId,
@SerialName(amountField)
override val amount: Int,
@SerialName(dateField)
override val date: TelegramDate,
@SerialName(receiverField)
override val partner: TransactionPartner
) : StarTransaction { ) : StarTransaction {
override val type: String @Transient
get() = Companion.type override val source: TransactionPartner?
get() = null
companion object { override val receiver: TransactionPartner
const val type: String = "user" get() = partner
}
}
@Serializable(StarTransaction.Companion::class)
data object Other : StarTransaction {
override val type: String = "other"
} }
@Serializable(StarTransaction.Companion::class) @Serializable(StarTransaction.Companion::class)
data class Unknown( data class Unknown(
override val type: String, @SerialName(idField)
override val id: StarTransactionId,
override val amount: Int,
override val date: TelegramDate,
override val source: TransactionPartner?,
override val receiver: TransactionPartner?,
val raw: JsonElement? val raw: JsonElement?
) : StarTransaction ) : StarTransaction {
override val partner: TransactionPartner
get() = source ?: receiver ?: error("Unable to take partner from source or receiver. Raw value: $raw")
}
companion object : KSerializer<StarTransaction> { companion object : KSerializer<StarTransaction> {
@Serializable @Serializable
private data class Surrogate( private data class Surrogate(
val type: String, val id: StarTransactionId,
val amount: Int, val amount: Int,
val date: TelegramDate, val date: TelegramDate,
val source: TransactionPartner?, val source: TransactionPartner?,
@ -76,33 +91,46 @@ sealed interface StarTransaction {
val (data, json) = decoder.decodeDataAndJson(Surrogate.serializer()) val (data, json) = decoder.decodeDataAndJson(Surrogate.serializer())
val unknown by lazy { val unknown by lazy {
Unknown(data.type, json) Unknown(
} id = data.id,
return when (data.type) { amount = data.amount,
Other.type -> Other date = data.date,
User.type -> User( source = data.source,
data.user ?: return unknown, receiver = data.receiver,
raw = json
) )
Fragment.type -> Fragment( }
data.withdrawal_state ?: return unknown, return when {
data.source != null -> Incoming(
id = data.id,
amount = data.amount,
date = data.date,
partner = data.source
)
data.receiver != null -> Outgoing(
id = data.id,
amount = data.amount,
date = data.date,
partner = data.receiver
) )
else -> unknown else -> unknown
} }
} }
override fun serialize(encoder: Encoder, value: StarTransaction) { override fun serialize(encoder: Encoder, value: StarTransaction) {
val surrogate = when (value) { if (value is Unknown && value.raw != null) {
Other -> Surrogate(value.type) JsonElement.serializer().serialize(encoder, value.raw)
is User -> Surrogate(value.type, user = value.user) return
is Fragment -> Surrogate(
value.type,
value.withdrawalState
)
is Unknown -> value.raw ?.let {
return JsonElement.serializer().serialize(encoder, it)
} ?: Surrogate(value.type)
} }
val surrogate = Surrogate(
id = value.id,
amount = value.amount,
date = value.date,
source = value.source,
receiver = value.receiver,
)
Surrogate.serializer().serialize(encoder, surrogate) Surrogate.serializer().serialize(encoder, surrogate)
} }
} }

View File

@ -0,0 +1,11 @@
package dev.inmo.tgbotapi.types.payments.stars
import dev.inmo.tgbotapi.types.transactionsField
import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable
@Serializable
data class StarTransactions(
@SerialName(transactionsField)
val transactions: List<StarTransaction>
)

View File

@ -4,6 +4,7 @@ import dev.inmo.tgbotapi.types.chat.PreviewUser
import dev.inmo.tgbotapi.types.userField import dev.inmo.tgbotapi.types.userField
import dev.inmo.tgbotapi.types.withdrawalStateField import dev.inmo.tgbotapi.types.withdrawalStateField
import dev.inmo.tgbotapi.utils.decodeDataAndJson import dev.inmo.tgbotapi.utils.decodeDataAndJson
import dev.inmo.tgbotapi.utils.internal.ClassCastsIncluded
import kotlinx.serialization.KSerializer import kotlinx.serialization.KSerializer
import kotlinx.serialization.SerialName import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable import kotlinx.serialization.Serializable
@ -14,6 +15,7 @@ import kotlinx.serialization.json.JsonElement
@Suppress("SERIALIZER_TYPE_INCOMPATIBLE") @Suppress("SERIALIZER_TYPE_INCOMPATIBLE")
@Serializable(TransactionPartner.Companion::class) @Serializable(TransactionPartner.Companion::class)
@ClassCastsIncluded
sealed interface TransactionPartner { sealed interface TransactionPartner {
val type: String val type: String

View File

@ -426,6 +426,9 @@ import dev.inmo.tgbotapi.types.passport.encrypted.abstracts.EncryptedPassportEle
import dev.inmo.tgbotapi.types.passport.encrypted.abstracts.UnknownEncryptedPassportElement import dev.inmo.tgbotapi.types.passport.encrypted.abstracts.UnknownEncryptedPassportElement
import dev.inmo.tgbotapi.types.payments.PreCheckoutQuery import dev.inmo.tgbotapi.types.payments.PreCheckoutQuery
import dev.inmo.tgbotapi.types.payments.ShippingQuery import dev.inmo.tgbotapi.types.payments.ShippingQuery
import dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState
import dev.inmo.tgbotapi.types.payments.stars.StarTransaction
import dev.inmo.tgbotapi.types.payments.stars.TransactionPartner
import dev.inmo.tgbotapi.types.polls.ApproximateScheduledCloseInfo import dev.inmo.tgbotapi.types.polls.ApproximateScheduledCloseInfo
import dev.inmo.tgbotapi.types.polls.ExactScheduledCloseInfo import dev.inmo.tgbotapi.types.polls.ExactScheduledCloseInfo
import dev.inmo.tgbotapi.types.polls.MultipleAnswersPoll import dev.inmo.tgbotapi.types.polls.MultipleAnswersPoll
@ -5060,6 +5063,108 @@ public inline fun <T>
EncryptedPassportElement.ifEncryptedPassportElementWithSelfie(block: (EncryptedPassportElementWithSelfie) -> T): EncryptedPassportElement.ifEncryptedPassportElementWithSelfie(block: (EncryptedPassportElementWithSelfie) -> T):
T? = encryptedPassportElementWithSelfieOrNull() ?.let(block) T? = encryptedPassportElementWithSelfieOrNull() ?.let(block)
public inline fun RevenueWithdrawalState.failedOrNull(): RevenueWithdrawalState.Failed? = this as?
dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Failed
public inline fun RevenueWithdrawalState.failedOrThrow(): RevenueWithdrawalState.Failed = this as
dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Failed
public inline fun <T> RevenueWithdrawalState.ifFailed(block: (RevenueWithdrawalState.Failed) -> T):
T? = failedOrNull() ?.let(block)
public inline fun RevenueWithdrawalState.pendingOrNull(): RevenueWithdrawalState.Pending? = this as?
dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Pending
public inline fun RevenueWithdrawalState.pendingOrThrow(): RevenueWithdrawalState.Pending = this as
dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Pending
public inline fun <T>
RevenueWithdrawalState.ifPending(block: (RevenueWithdrawalState.Pending) -> T): T? =
pendingOrNull() ?.let(block)
public inline fun RevenueWithdrawalState.succeededOrNull(): RevenueWithdrawalState.Succeeded? = this
as? dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Succeeded
public inline fun RevenueWithdrawalState.succeededOrThrow(): RevenueWithdrawalState.Succeeded = this
as dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Succeeded
public inline fun <T>
RevenueWithdrawalState.ifSucceeded(block: (RevenueWithdrawalState.Succeeded) -> T): T? =
succeededOrNull() ?.let(block)
public inline fun RevenueWithdrawalState.unknownOrNull(): RevenueWithdrawalState.Unknown? = this as?
dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Unknown
public inline fun RevenueWithdrawalState.unknownOrThrow(): RevenueWithdrawalState.Unknown = this as
dev.inmo.tgbotapi.types.payments.stars.RevenueWithdrawalState.Unknown
public inline fun <T>
RevenueWithdrawalState.ifUnknown(block: (RevenueWithdrawalState.Unknown) -> T): T? =
unknownOrNull() ?.let(block)
public inline fun StarTransaction.incomingOrNull(): StarTransaction.Incoming? = this as?
dev.inmo.tgbotapi.types.payments.stars.StarTransaction.Incoming
public inline fun StarTransaction.incomingOrThrow(): StarTransaction.Incoming = this as
dev.inmo.tgbotapi.types.payments.stars.StarTransaction.Incoming
public inline fun <T> StarTransaction.ifIncoming(block: (StarTransaction.Incoming) -> T): T? =
incomingOrNull() ?.let(block)
public inline fun StarTransaction.outgoingOrNull(): StarTransaction.Outgoing? = this as?
dev.inmo.tgbotapi.types.payments.stars.StarTransaction.Outgoing
public inline fun StarTransaction.outgoingOrThrow(): StarTransaction.Outgoing = this as
dev.inmo.tgbotapi.types.payments.stars.StarTransaction.Outgoing
public inline fun <T> StarTransaction.ifOutgoing(block: (StarTransaction.Outgoing) -> T): T? =
outgoingOrNull() ?.let(block)
public inline fun StarTransaction.unknownOrNull(): StarTransaction.Unknown? = this as?
dev.inmo.tgbotapi.types.payments.stars.StarTransaction.Unknown
public inline fun StarTransaction.unknownOrThrow(): StarTransaction.Unknown = this as
dev.inmo.tgbotapi.types.payments.stars.StarTransaction.Unknown
public inline fun <T> StarTransaction.ifUnknown(block: (StarTransaction.Unknown) -> T): T? =
unknownOrNull() ?.let(block)
public inline fun TransactionPartner.fragmentOrNull(): TransactionPartner.Fragment? = this as?
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.Fragment
public inline fun TransactionPartner.fragmentOrThrow(): TransactionPartner.Fragment = this as
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.Fragment
public inline fun <T> TransactionPartner.ifFragment(block: (TransactionPartner.Fragment) -> T): T? =
fragmentOrNull() ?.let(block)
public inline fun TransactionPartner.otherOrNull(): TransactionPartner.Other? = this as?
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.Other
public inline fun TransactionPartner.otherOrThrow(): TransactionPartner.Other = this as
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.Other
public inline fun <T> TransactionPartner.ifOther(block: (TransactionPartner.Other) -> T): T? =
otherOrNull() ?.let(block)
public inline fun TransactionPartner.unknownOrNull(): TransactionPartner.Unknown? = this as?
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.Unknown
public inline fun TransactionPartner.unknownOrThrow(): TransactionPartner.Unknown = this as
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.Unknown
public inline fun <T> TransactionPartner.ifUnknown(block: (TransactionPartner.Unknown) -> T): T? =
unknownOrNull() ?.let(block)
public inline fun TransactionPartner.userOrNull(): TransactionPartner.User? = this as?
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.User
public inline fun TransactionPartner.userOrThrow(): TransactionPartner.User = this as
dev.inmo.tgbotapi.types.payments.stars.TransactionPartner.User
public inline fun <T> TransactionPartner.ifUser(block: (TransactionPartner.User) -> T): T? =
userOrNull() ?.let(block)
public inline fun ScheduledCloseInfo.exactScheduledCloseInfoOrNull(): ExactScheduledCloseInfo? = public inline fun ScheduledCloseInfo.exactScheduledCloseInfoOrNull(): ExactScheduledCloseInfo? =
this as? dev.inmo.tgbotapi.types.polls.ExactScheduledCloseInfo this as? dev.inmo.tgbotapi.types.polls.ExactScheduledCloseInfo