Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -628,6 +628,13 @@ Example:
Text("This is some text for feature X")
```

**Verifying whether a string key is "real" (already in Lokalise):** if you find a key in a
`strings.xml` and are unsure whether it actually exists in Lokalise or was hand-added, run
`./gradlew downloadStrings` and re-check the file. Because `downloadStrings` regenerates every
`strings.xml` from Lokalise, a key that **survives** the run exists in Lokalise; a key that
**disappears** was only added locally and would break the build once someone else syncs. Use this
before relying on (or committing code that references) a key you didn't personally add to Lokalise.

## Debugging

### Common Issues
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -971,6 +971,11 @@ type ClaimIntent {
"""
displayName: String
"""
Whether this draft is resumable by the member. A draft that has been deleted (see `claimIntentDeleteDraft`)
is no longer resumable.
"""
resumable: Boolean!
"""
The created claim of this intent.
Once this value is returned, the intent is effectively over, and no steps
can be produced or interacted with.
Expand Down Expand Up @@ -3713,6 +3718,10 @@ type Mutation {
"""
claimIntentRegretStep(stepId: ID!): ClaimIntentMutationOutput!
"""
Delete a draft claim intent from the member's perspective (a soft delete) so it is no longer returned by `resumableClaimIntent`.
"""
claimIntentDeleteDraft(id: ID!): Boolean!
"""
Submit a step containing a `ClaimIntentStepContentForm`.
"""
claimIntentSubmitForm(input: ClaimIntentSubmitFormInput!): ClaimIntentMutationOutput!
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -503,8 +503,8 @@
<string name="INBOX_EMPTY_STATE_SUBTITLE">Inga konversationer än. Starta en genom att skriva ett meddelande</string>
<string name="INBOX_EMPTY_STATE_TITLE">Din inkorg är tom</string>
<string name="INBOX_NEW_MESSAGE">Nytt</string>
<string name="INBOX_NEW_MESSAGE_CLAIM_DESCRIPTION">Anmäl något som har hänt med dig eller dina saker</string>
<string name="INBOX_NEW_MESSAGE_SUPPORT_DESCRIPTION">Frågor om din försäkring, betalningar och annat</string>
<string name="INBOX_NEW_MESSAGE_CLAIM_DESCRIPTION">Anmäl något som hänt dig eller dina saker</string>
<string name="INBOX_NEW_MESSAGE_SUPPORT_DESCRIPTION">Frågor om din försäkring, betalningar eller annat</string>
<string name="INSURANCES_CROSS_SELL_DISCOUNTS_AVAILABLE">Erbjudanden</string>
<string name="INSURANCES_NO_ACTIVE">Du har ingen aktiv försäkring</string>
<string name="INSURANCE_ADDONS_SUBHEADING">Tillägg</string>
Expand Down Expand Up @@ -986,6 +986,7 @@
<string name="TIER_FLOW_SELECT_INSURANCE_SUBTITLE">Välj den försäkring du vill uppdatera</string>
<string name="TIER_FLOW_SHOW_COVERAGE_BUTTON">Visa ditt skydd</string>
<string name="TIER_FLOW_SUBTITLE">Välj din skyddsnivå och självrisk</string>
<string name="TIER_FLOW_SUBTITLE_WITHOUT_DEDUCTIBLE">Välj din skyddsnivå</string>
<string name="TIER_FLOW_SUMMARY_CONFIRM_BUTTON">Godkänn ändringar</string>
<string name="TIER_FLOW_SUMMARY_COVERAGE_SUBTITLE">Skyddet</string>
<string name="TIER_FLOW_SUMMARY_DOCUMENTS_SUBTITLE">Dokument</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -986,6 +986,7 @@
<string name="TIER_FLOW_SELECT_INSURANCE_SUBTITLE">Select the insurance you want to edit</string>
<string name="TIER_FLOW_SHOW_COVERAGE_BUTTON">Show coverage</string>
<string name="TIER_FLOW_SUBTITLE">Set your coverage level and deductible</string>
<string name="TIER_FLOW_SUBTITLE_WITHOUT_DEDUCTIBLE">Set your coverage level</string>
<string name="TIER_FLOW_SUMMARY_CONFIRM_BUTTON">Confirm changes</string>
<string name="TIER_FLOW_SUMMARY_COVERAGE_SUBTITLE">Coverage</string>
<string name="TIER_FLOW_SUMMARY_DOCUMENTS_SUBTITLE">Documents</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -502,8 +502,8 @@
<string name="INBOX_EMPTY_STATE_SUBTITLE">Inga konversationer än. Starta en genom att skriva ett meddelande</string>
<string name="INBOX_EMPTY_STATE_TITLE">Din inkorg är tom</string>
<string name="INBOX_NEW_MESSAGE">Nytt</string>
<string name="INBOX_NEW_MESSAGE_CLAIM_DESCRIPTION">Anmäl något som har hänt med dig eller dina saker</string>
<string name="INBOX_NEW_MESSAGE_SUPPORT_DESCRIPTION">Frågor om din försäkring, betalningar och annat</string>
<string name="INBOX_NEW_MESSAGE_CLAIM_DESCRIPTION">Anmäl något som hänt dig eller dina saker</string>
<string name="INBOX_NEW_MESSAGE_SUPPORT_DESCRIPTION">Frågor om din försäkring, betalningar eller annat</string>
<string name="INSURANCES_CROSS_SELL_DISCOUNTS_AVAILABLE">Erbjudanden</string>
<string name="INSURANCES_NO_ACTIVE">Du har ingen aktiv försäkring</string>
<string name="INSURANCE_ADDONS_SUBHEADING">Tillägg</string>
Expand Down Expand Up @@ -985,6 +985,7 @@
<string name="TIER_FLOW_SELECT_INSURANCE_SUBTITLE">Välj den försäkring du vill uppdatera</string>
<string name="TIER_FLOW_SHOW_COVERAGE_BUTTON">Visa ditt skydd</string>
<string name="TIER_FLOW_SUBTITLE">Välj din skyddsnivå och självrisk</string>
<string name="TIER_FLOW_SUBTITLE_WITHOUT_DEDUCTIBLE">Välj din skyddsnivå</string>
<string name="TIER_FLOW_SUMMARY_CONFIRM_BUTTON">Godkänn ändringar</string>
<string name="TIER_FLOW_SUMMARY_COVERAGE_SUBTITLE">Skyddet</string>
<string name="TIER_FLOW_SUMMARY_DOCUMENTS_SUBTITLE">Dokument</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -985,6 +985,7 @@
<string name="TIER_FLOW_SELECT_INSURANCE_SUBTITLE">Select the insurance you want to edit</string>
<string name="TIER_FLOW_SHOW_COVERAGE_BUTTON">Show coverage</string>
<string name="TIER_FLOW_SUBTITLE">Set your coverage level and deductible</string>
<string name="TIER_FLOW_SUBTITLE_WITHOUT_DEDUCTIBLE">Set your coverage level</string>
<string name="TIER_FLOW_SUMMARY_CONFIRM_BUTTON">Confirm changes</string>
<string name="TIER_FLOW_SUMMARY_COVERAGE_SUBTITLE">Coverage</string>
<string name="TIER_FLOW_SUMMARY_DOCUMENTS_SUBTITLE">Documents</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ $addonsFlagOn: Boolean!) {
}
tierLevel
tierName
tierDescription
}
quotes {
currentTotalCost {
Expand Down Expand Up @@ -48,6 +49,7 @@ $addonsFlagOn: Boolean!) {
}
tierLevel
tierName
tierDescription
addons @include(if: $addonsFlagOn) {
addonVariant {
...AddonVariantFragment
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ internal class CreateChangeTierDeductibleIntentUseCaseImpl(
tier = Tier(
tierName = tierName,
tierLevel = tierLevel,
tierDescription = productVariant.tierDescription,
tierDescription = tierDescription ?: productVariant.tierDescription,
tierDisplayName = productVariant.displayNameTier,
),
displayItems = displayItems.toDisplayItems(),
Expand All @@ -126,7 +126,7 @@ internal class CreateChangeTierDeductibleIntentUseCaseImpl(
tier = Tier(
tierName = it.tierName,
tierLevel = it.tierLevel,
tierDescription = it.productVariant.tierDescription,
tierDescription = it.tierDescription ?: it.productVariant.tierDescription,
tierDisplayName = it.productVariant.displayNameTier,
),
addons = it.addons?.map { addon ->
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import hedvigandroid.data_contract.generated.resources.dog
import hedvigandroid.data_contract.generated.resources.home
import hedvigandroid.data_contract.generated.resources.homeowner
import hedvigandroid.data_contract.generated.resources.rental
import hedvigandroid.data_contract.generated.resources.safety
import hedvigandroid.data_contract.generated.resources.student
import hedvigandroid.data_contract.generated.resources.vacation
import hedvigandroid.data_contract.generated.resources.villa
Expand All @@ -25,6 +26,7 @@ enum class ContractGroup {
STUDENT,
COUNTRY_HOME,
QASA_LANDLORD,
PAYMENT_PROTECTION,
UNKNOWN,
}

Expand All @@ -41,6 +43,7 @@ fun ContractGroup.gradientResource(): DrawableResource = when (this) {
ContractGroup.COUNTRY_HOME -> Res.drawable.vacation
ContractGroup.UNKNOWN -> Res.drawable.home
ContractGroup.QASA_LANDLORD -> Res.drawable.home
ContractGroup.PAYMENT_PROTECTION -> Res.drawable.safety
}

fun ContractGroup.pillowResource(): DrawableResource = when (this) {
Expand All @@ -56,6 +59,7 @@ fun ContractGroup.pillowResource(): DrawableResource = when (this) {
ContractGroup.COUNTRY_HOME -> Res.drawable.vacation
ContractGroup.UNKNOWN -> Res.drawable.home
ContractGroup.QASA_LANDLORD -> Res.drawable.home
ContractGroup.PAYMENT_PROTECTION -> Res.drawable.safety
}

fun String.toContractGroup(): ContractGroup = when (this) {
Expand Down Expand Up @@ -132,5 +136,7 @@ fun String.toContractGroup(): ContractGroup = when (this) {

"SE_QASA_LANDLORD" -> ContractGroup.QASA_LANDLORD

"SE_PAYMENT_PROTECTION" -> ContractGroup.PAYMENT_PROTECTION

else -> ContractGroup.UNKNOWN
}
Original file line number Diff line number Diff line change
Expand Up @@ -219,6 +219,8 @@ internal class SelectCoveragePresenter(
),
quotesForChosenTier = currentPartialStateValue.map[chosenTier]!!,
isTierChoiceEnabled = currentPartialStateValue.map.keys.size > 1,
isPaymentProtection =
currentPartialStateValue.contractData.contractGroup == ContractGroup.PAYMENT_PROTECTION,
contractData = currentPartialStateValue.contractData,
chosenInDialogQuote = chosenQuoteInDialog,
chosenInDialogTier = chosenTierInDialog,
Expand Down Expand Up @@ -326,6 +328,9 @@ internal data class SelectCoverageSuccessUiState(
val chosenInDialogQuote: TierDeductibleQuote?,
val isCurrentChosen: Boolean,
val isTierChoiceEnabled: Boolean,
// Payment protection has no real tiers nor comparable coverage: it reuses the tier flow only to pick an
// insured amount. Used to hide the compare/show-coverage button and to swap the deductible-mentioning subtitle.
val isPaymentProtection: Boolean,
// sorted list of tiers with corresponding premiums (depending on selected deductible)
val tiers: List<Pair<Tier, UiMoney>>,
val quotesForChosenTier: List<TierDeductibleQuote>,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,9 @@ import hedvig.resources.TIER_FLOW_SELECT_COVERAGE_SUBTITLE
import hedvig.resources.TIER_FLOW_SELECT_COVERAGE_TITLE
import hedvig.resources.TIER_FLOW_SELECT_DEDUCTIBLE_SUBTITLE
import hedvig.resources.TIER_FLOW_SELECT_DEDUCTIBLE_TITLE
import hedvig.resources.TIER_FLOW_SHOW_COVERAGE_BUTTON
import hedvig.resources.TIER_FLOW_SUBTITLE
import hedvig.resources.TIER_FLOW_SUBTITLE_WITHOUT_DEDUCTIBLE
import hedvig.resources.TIER_FLOW_TITLE
import hedvig.resources.TIER_FLOW_TOTAL
import hedvig.resources.general_cancel_button
Expand Down Expand Up @@ -234,7 +236,12 @@ private fun SelectTierScreen(
lineBreak = LineBreak.Heading,
color = HedvigTheme.colorScheme.textSecondary,
),
text = stringResource(Res.string.TIER_FLOW_SUBTITLE),
// Payment protection has no deductible, so the standard "…level and deductible" subtitle over-promises.
text = if (uiState.isPaymentProtection) {
stringResource(Res.string.TIER_FLOW_SUBTITLE_WITHOUT_DEDUCTIBLE)
} else {
stringResource(Res.string.TIER_FLOW_SUBTITLE)
},
modifier = Modifier.padding(horizontal = 16.dp),
)
Spacer(Modifier.weight(1f))
Expand Down Expand Up @@ -270,14 +277,20 @@ private fun SelectTierScreen(
.fillMaxWidth()
.padding(horizontal = 16.dp),
)
if (uiState.tiers.size > 1) {
if (!uiState.isPaymentProtection) {
Spacer(Modifier.height(8.dp))
HedvigTextButton(
buttonSize = Large,
modifier = Modifier
.fillMaxWidth()
.padding(horizontal = 16.dp),
text = stringResource(Res.string.TIER_FLOW_COMPARE_BUTTON),
text = stringResource(
if (uiState.tiers.size == 1) {
Res.string.TIER_FLOW_SHOW_COVERAGE_BUTTON
} else {
Res.string.TIER_FLOW_COMPARE_BUTTON
},
),
onClick = {
onCompareClick()
},
Expand Down Expand Up @@ -327,7 +340,7 @@ private fun CustomizationCard(
Spacer(Modifier.height(16.dp))
val tierSimpleItems = buildList {
for (tier in tiers) {
add(SimpleDropdownItem(tier.first.tierDisplayName ?: "-"))
add(SimpleDropdownItem(tier.first.tierDisplayName ?: tier.first.tierName))
}
}
val hintText = stringResource(Res.string.TIER_FLOW_COVERAGE_PLACEHOLDER)
Expand Down Expand Up @@ -543,7 +556,7 @@ private fun TierCoverageRadioGroup(
options = tiers.map { pair ->
RadioOption(
id = RadioOptionId(pair.first.tierName),
text = pair.first.tierDisplayName ?: "-",
text = pair.first.tierDisplayName ?: pair.first.tierName,
label = pair.first.tierDescription,
)
},
Expand Down Expand Up @@ -753,6 +766,7 @@ private fun SelectTierScreenPreview() {
),
quotesForChosenTier = listOf(quotesForPreview[0]),
isTierChoiceEnabled = true,
isPaymentProtection = false,
chosenTier = Tier(
"BAS",
tierLevel = 0,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import assertk.assertions.isNull
import assertk.assertions.prop
import basTier
import com.hedvig.android.core.common.ErrorMessage
import com.hedvig.android.data.contract.ContractGroup
import com.hedvig.android.feature.change.tier.data.CurrentContractData
import com.hedvig.android.feature.change.tier.data.GetCurrentContractDataUseCase
import com.hedvig.android.feature.change.tier.navigation.ComparisonKey
Expand Down Expand Up @@ -264,8 +265,56 @@ class SelectCoveragePresenterTest {
.isNull()
}
}

@Test
fun `when the contract is payment protection isPaymentProtection is true`() = runTest {
val tierRepo = FakeChangeTierRepository()
val presenter = SelectCoveragePresenter(
params = params,
tierRepository = tierRepo,
getCurrentContractDataUseCase = FakeGetCurrentContractDataUseCase(),
backstack = TestBackstack(),
)
presenter.test(SelectCoverageState.Loading) {
tierRepo.quoteListTurbine.add(listOf(paymentProtectionQuote))
skipItems(1)
assertThat(awaitItem())
.isInstanceOf(SelectCoverageState.Success::class)
.prop(SelectCoverageState.Success::uiState)
.isInstanceOf(SelectCoverageSuccessUiState::class.java)
.prop(SelectCoverageSuccessUiState::isPaymentProtection)
.isEqualTo(true)
}
}

@Test
fun `when the contract is not payment protection isPaymentProtection is false`() = runTest {
val tierRepo = FakeChangeTierRepository()
val presenter = SelectCoveragePresenter(
params = params,
tierRepository = tierRepo,
getCurrentContractDataUseCase = FakeGetCurrentContractDataUseCase(),
backstack = TestBackstack(),
)
presenter.test(SelectCoverageState.Loading) {
tierRepo.quoteListTurbine.add(listOf(testQuote, testQuote2, currentQuote))
skipItems(1)
assertThat(awaitItem())
.isInstanceOf(SelectCoverageState.Success::class)
.prop(SelectCoverageState.Success::uiState)
.isInstanceOf(SelectCoverageSuccessUiState::class.java)
.prop(SelectCoverageSuccessUiState::isPaymentProtection)
.isEqualTo(false)
}
}
}

// A current quote whose contract group is payment protection, which reuses the tier flow only to pick an
// insured amount. Its id must match FakeChangeTierRepository.getCurrentQuoteId() so it is treated as current.
private val paymentProtectionQuote = currentQuote.copy(
productVariant = currentQuote.productVariant.copy(contractGroup = ContractGroup.PAYMENT_PROTECTION),
)

private class FakeGetCurrentContractDataUseCase() : GetCurrentContractDataUseCase {
override suspend fun invoke(insuranceId: String): Either<ErrorMessage, CurrentContractData> {
return either { CurrentContractData("exposure name") }
Expand Down
Loading