Updated on 2026-08-14
This commit is contained in:
parent
f000c0c687
commit
f990f3c833
9 changed files with 152 additions and 141 deletions
|
|
@ -16,43 +16,26 @@ internal object YieldBoostStatusConverter {
|
|||
private const val REASON_CLOSED = "closed"
|
||||
|
||||
fun convert(dto: YieldBoostStatusResponse): YieldBoostStatus = when (dto.promoEnrollmentStatus.lowercase()) {
|
||||
STATUS_ACTIVE -> dto.toActive() ?: YieldBoostStatus.NotStarted
|
||||
STATUS_COMPLETED -> dto.toCompleted() ?: YieldBoostStatus.NotStarted
|
||||
STATUS_ACTIVE, STATUS_COMPLETED -> dto.toEnrolled()
|
||||
STATUS_DISQUALIFIED -> YieldBoostStatus.Disqualified(reason = dto.disqualificationReason.toReason())
|
||||
STATUS_NOT_STARTED -> YieldBoostStatus.NotStarted
|
||||
else -> YieldBoostStatus.NotStarted // forward-compat: unknown status → treat as NotStarted
|
||||
}
|
||||
|
||||
/** Backend `"active"` → [YieldBoostStatus.Active]. Returns `null` if mandatory dates can't be parsed. */
|
||||
private fun YieldBoostStatusResponse.toActive(): YieldBoostStatus.Active? {
|
||||
val activation = activationDate?.let { runCatching { Instant.parse(it) }.getOrNull() } ?: return null
|
||||
val qualificationEnd =
|
||||
qualificationEndDate?.let { runCatching { Instant.parse(it) }.getOrNull() } ?: return null
|
||||
return YieldBoostStatus.Active(
|
||||
tokenName = tokenName.orEmpty(),
|
||||
networkId = networkId.orEmpty(),
|
||||
moduleAddress = moduleAddress.orEmpty(),
|
||||
userAddress = userAddress.orEmpty(),
|
||||
contractAddress = contractAddress.orEmpty(),
|
||||
activationDate = activation,
|
||||
qualificationEndDate = qualificationEnd,
|
||||
)
|
||||
}
|
||||
|
||||
private fun YieldBoostStatusResponse.toCompleted(): YieldBoostStatus.Completed? {
|
||||
val activation = activationDate?.let { runCatching { Instant.parse(it) }.getOrNull() } ?: return null
|
||||
val qualificationEnd =
|
||||
qualificationEndDate?.let { runCatching { Instant.parse(it) }.getOrNull() } ?: return null
|
||||
return YieldBoostStatus.Completed(
|
||||
tokenName = tokenName.orEmpty(),
|
||||
networkId = networkId.orEmpty(),
|
||||
moduleAddress = moduleAddress.orEmpty(),
|
||||
userAddress = userAddress.orEmpty(),
|
||||
contractAddress = contractAddress.orEmpty(),
|
||||
activationDate = activation,
|
||||
qualificationEndDate = qualificationEnd,
|
||||
)
|
||||
}
|
||||
/**
|
||||
* Backend `"active"` / `"completed"` → [YieldBoostStatus.Enrolled].
|
||||
*
|
||||
* An unparseable / missing `qualificationEndDate` is kept as `null` (block hidden) — never downgraded to
|
||||
* [YieldBoostStatus.NotStarted], which would re-prompt an already-enrolled user to join.
|
||||
*/
|
||||
private fun YieldBoostStatusResponse.toEnrolled(): YieldBoostStatus.Enrolled = YieldBoostStatus.Enrolled(
|
||||
tokenName = tokenName.orEmpty(),
|
||||
networkId = networkId.orEmpty(),
|
||||
moduleAddress = moduleAddress.orEmpty(),
|
||||
userAddress = userAddress.orEmpty(),
|
||||
contractAddress = contractAddress.orEmpty(),
|
||||
qualificationEndDate = qualificationEndDate?.let { runCatching { Instant.parse(it) }.getOrNull() },
|
||||
)
|
||||
|
||||
private fun String?.toReason(): YieldBoostStatus.Disqualified.Reason = when (this?.lowercase()) {
|
||||
REASON_FROD -> YieldBoostStatus.Disqualified.Reason.FROD
|
||||
|
|
|
|||
|
|
@ -3,11 +3,11 @@ package com.tangem.data.yield.supply.promo.converter
|
|||
import com.google.common.truth.Truth.assertThat
|
||||
import com.tangem.datasource.api.promotion.models.YieldBoostStatusResponse
|
||||
import com.tangem.domain.yield.supply.models.YieldBoostStatus
|
||||
import kotlinx.datetime.Instant
|
||||
import org.junit.jupiter.api.Test
|
||||
|
||||
class YieldBoostStatusConverterTest {
|
||||
|
||||
private val activation = "2026-05-01T00:00:00Z"
|
||||
private val qualificationEnd = "2026-06-01T00:00:00Z"
|
||||
|
||||
@Test
|
||||
|
|
@ -20,7 +20,7 @@ class YieldBoostStatusConverterTest {
|
|||
}
|
||||
|
||||
@Test
|
||||
fun `GIVEN active backend status with valid dates WHEN convert THEN returns Active`() {
|
||||
fun `GIVEN active backend status with valid date WHEN convert THEN returns Enrolled`() {
|
||||
val dto = dto(
|
||||
promoEnrollmentStatus = "active",
|
||||
tokenName = "USD Coin",
|
||||
|
|
@ -28,47 +28,49 @@ class YieldBoostStatusConverterTest {
|
|||
moduleAddress = "0xmodule",
|
||||
userAddress = "0xuser",
|
||||
contractAddress = "0xcontract",
|
||||
activationDate = activation,
|
||||
qualificationEndDate = qualificationEnd,
|
||||
)
|
||||
|
||||
val result = YieldBoostStatusConverter.convert(dto)
|
||||
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Active::class.java)
|
||||
val active = result as YieldBoostStatus.Active
|
||||
assertThat(active.tokenName).isEqualTo("USD Coin")
|
||||
assertThat(active.networkId).isEqualTo("ethereum")
|
||||
assertThat(active.contractAddress).isEqualTo("0xcontract")
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Enrolled::class.java)
|
||||
val enrolled = result as YieldBoostStatus.Enrolled
|
||||
assertThat(enrolled.tokenName).isEqualTo("USD Coin")
|
||||
assertThat(enrolled.networkId).isEqualTo("ethereum")
|
||||
assertThat(enrolled.contractAddress).isEqualTo("0xcontract")
|
||||
assertThat(enrolled.qualificationEndDate).isEqualTo(Instant.parse(qualificationEnd))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `GIVEN active status missing activationDate WHEN convert THEN falls back to NotStarted`() {
|
||||
fun `GIVEN active status missing qualificationEndDate WHEN convert THEN returns Enrolled with null date`() {
|
||||
val dto = dto(
|
||||
promoEnrollmentStatus = "active",
|
||||
activationDate = null,
|
||||
qualificationEndDate = qualificationEnd,
|
||||
contractAddress = "0xcontract",
|
||||
qualificationEndDate = null,
|
||||
)
|
||||
|
||||
val result = YieldBoostStatusConverter.convert(dto)
|
||||
|
||||
assertThat(result).isEqualTo(YieldBoostStatus.NotStarted)
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Enrolled::class.java)
|
||||
assertThat((result as YieldBoostStatus.Enrolled).qualificationEndDate).isNull()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `GIVEN active status with malformed activationDate WHEN convert THEN falls back to NotStarted`() {
|
||||
fun `GIVEN active status with malformed qualificationEndDate WHEN convert THEN returns Enrolled with null date`() {
|
||||
val dto = dto(
|
||||
promoEnrollmentStatus = "active",
|
||||
activationDate = "not-an-iso",
|
||||
qualificationEndDate = qualificationEnd,
|
||||
contractAddress = "0xcontract",
|
||||
qualificationEndDate = "not-an-iso",
|
||||
)
|
||||
|
||||
val result = YieldBoostStatusConverter.convert(dto)
|
||||
|
||||
assertThat(result).isEqualTo(YieldBoostStatus.NotStarted)
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Enrolled::class.java)
|
||||
assertThat((result as YieldBoostStatus.Enrolled).qualificationEndDate).isNull()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `GIVEN completed status with valid dates WHEN convert THEN returns Completed`() {
|
||||
fun `GIVEN completed status with valid date WHEN convert THEN returns Enrolled`() {
|
||||
val dto = dto(
|
||||
promoEnrollmentStatus = "completed",
|
||||
tokenName = "USDT",
|
||||
|
|
@ -76,13 +78,14 @@ class YieldBoostStatusConverterTest {
|
|||
moduleAddress = "0xmodule",
|
||||
userAddress = "0xuser",
|
||||
contractAddress = "0xcontract",
|
||||
activationDate = "2026-04-01T00:00:00Z",
|
||||
qualificationEndDate = "2026-05-01T00:00:00Z",
|
||||
)
|
||||
|
||||
val result = YieldBoostStatusConverter.convert(dto)
|
||||
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Completed::class.java)
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Enrolled::class.java)
|
||||
assertThat((result as YieldBoostStatus.Enrolled).qualificationEndDate)
|
||||
.isEqualTo(Instant.parse("2026-05-01T00:00:00Z"))
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -153,13 +156,12 @@ class YieldBoostStatusConverterTest {
|
|||
moduleAddress = "0xmodule",
|
||||
userAddress = "0xuser",
|
||||
contractAddress = "0xcontract",
|
||||
activationDate = activation,
|
||||
qualificationEndDate = qualificationEnd,
|
||||
)
|
||||
|
||||
val result = YieldBoostStatusConverter.convert(dto)
|
||||
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Active::class.java)
|
||||
assertThat(result).isInstanceOf(YieldBoostStatus.Enrolled::class.java)
|
||||
}
|
||||
|
||||
private fun dto(
|
||||
|
|
@ -169,7 +171,6 @@ class YieldBoostStatusConverterTest {
|
|||
moduleAddress: String? = null,
|
||||
userAddress: String? = null,
|
||||
contractAddress: String? = null,
|
||||
activationDate: String? = null,
|
||||
qualificationEndDate: String? = null,
|
||||
disqualificationReason: String? = null,
|
||||
) = YieldBoostStatusResponse(
|
||||
|
|
@ -179,7 +180,6 @@ class YieldBoostStatusConverterTest {
|
|||
userAddress = userAddress,
|
||||
contractAddress = contractAddress,
|
||||
promoEnrollmentStatus = promoEnrollmentStatus,
|
||||
activationDate = activationDate,
|
||||
qualificationEndDate = qualificationEndDate,
|
||||
disqualificationReason = disqualificationReason,
|
||||
)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue