diff --git a/wallet/src/main/java/net/taler/wallet/peer/ExpirationComposable.kt b/wallet/src/main/java/net/taler/wallet/peer/ExpirationComposable.kt
index 4393e470..32858701 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/ExpirationComposable.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/ExpirationComposable.kt
@@ -26,13 +26,30 @@ import androidx.compose.foundation.lazy.items
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
+import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
+import net.taler.common.Timestamp
+import net.taler.lib.android.toAbsoluteTime
import net.taler.wallet.R
import net.taler.wallet.compose.NumericInputField
import net.taler.wallet.compose.SelectionChip
import net.taler.wallet.compose.TalerSurface
+import net.taler.wallet.transactions.TransactionInfoComposable
+
+/**
+ * When a peer payment link (purse) expires: until then the other party can
+ * accept/pay it, afterwards the money goes back. Nothing is shown for "never".
+ */
+@Composable
+fun PeerExpirationComposable(expiration: Timestamp?) {
+ if (expiration == null || expiration.ms < 0) return
+ TransactionInfoComposable(
+ label = stringResource(R.string.peer_expiration),
+ info = expiration.ms.toAbsoluteTime(LocalContext.current).toString(),
+ )
+}
enum class ExpirationOption(val hours: Long) {
DAYS_1(24),
diff --git a/wallet/src/main/java/net/taler/wallet/peer/IncomingComposable.kt b/wallet/src/main/java/net/taler/wallet/peer/IncomingComposable.kt
index 2171f445..fbc0ec17 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/IncomingComposable.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/IncomingComposable.kt
@@ -125,6 +125,7 @@ fun ColumnScope.PeerPullTermsComposable(
text = terms.contractTerms.summary,
style = MaterialTheme.typography.headlineSmall,
)
+ PeerExpirationComposable(terms.contractTerms.purseExpiration)
Spacer(modifier = Modifier.weight(1f))
Card(modifier = Modifier.fillMaxWidth()) {
Column(
diff --git a/wallet/src/main/java/net/taler/wallet/peer/IncomingState.kt b/wallet/src/main/java/net/taler/wallet/peer/IncomingState.kt
index 6d0ae065..0e3eff51 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/IncomingState.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/IncomingState.kt
@@ -16,8 +16,10 @@
package net.taler.wallet.peer
+import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable
import net.taler.common.Amount
+import net.taler.common.Timestamp
import net.taler.wallet.backend.TalerErrorInfo
sealed class IncomingState
@@ -59,6 +61,8 @@ data class IncomingError(
data class PeerContractTerms(
val summary: String,
val amount: Amount,
+ @SerialName("purse_expiration")
+ val purseExpiration: Timestamp? = null,
)
@Serializable
diff --git a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullCredit.kt b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullCredit.kt
index b14d4f5d..a5675889 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullCredit.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullCredit.kt
@@ -38,6 +38,7 @@ import net.taler.wallet.transactions.TransactionAction.Suspend
import net.taler.wallet.transactions.TransactionAmountComposable
import net.taler.wallet.transactions.TransactionInfoComposable
import net.taler.wallet.transactions.TransactionMajorState.Done
+import net.taler.wallet.transactions.TransactionMajorState.Dialog
import net.taler.wallet.transactions.TransactionMajorState.Pending
import net.taler.wallet.transactions.TransactionMinorState.CreatePurse
import net.taler.wallet.transactions.TransactionMinorState.Ready
@@ -92,6 +93,10 @@ fun ColumnScope.TransactionPeerPullCreditComposable(
label = stringResource(id = R.string.send_peer_purpose),
info = t.info.summary ?: "",
)
+
+ if (t.txState.major == Pending || t.txState.major == Dialog) {
+ PeerExpirationComposable(t.info.expiration)
+ }
}
@Preview
diff --git a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullDebit.kt b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullDebit.kt
index ecc0377e..21ddc4b7 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullDebit.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPullDebit.kt
@@ -33,6 +33,7 @@ import net.taler.wallet.transactions.TransactionAction.Retry
import net.taler.wallet.transactions.TransactionAction.Suspend
import net.taler.wallet.transactions.TransactionAmountComposable
import net.taler.wallet.transactions.TransactionInfoComposable
+import net.taler.wallet.transactions.TransactionMajorState.Dialog
import net.taler.wallet.transactions.TransactionMajorState.Pending
import net.taler.wallet.transactions.TransactionPeerComposable
import net.taler.wallet.transactions.TransactionPeerPullDebit
@@ -65,6 +66,10 @@ fun TransactionPeerPullDebitComposable(t: TransactionPeerPullDebit) {
label = stringResource(id = R.string.send_peer_purpose),
info = t.info.summary ?: "",
)
+
+ if (t.txState.major == Pending || t.txState.major == Dialog) {
+ PeerExpirationComposable(t.info.expiration)
+ }
}
@Preview
diff --git a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushCredit.kt b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushCredit.kt
index aa7659a6..813707e2 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushCredit.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushCredit.kt
@@ -36,6 +36,7 @@ import net.taler.wallet.transactions.TransactionAction.Retry
import net.taler.wallet.transactions.TransactionAction.Suspend
import net.taler.wallet.transactions.TransactionAmountComposable
import net.taler.wallet.transactions.TransactionInfoComposable
+import net.taler.wallet.transactions.TransactionMajorState.Dialog
import net.taler.wallet.transactions.TransactionMajorState.Pending
import net.taler.wallet.transactions.TransactionPeerComposable
import net.taler.wallet.transactions.TransactionPeerPushCredit
@@ -73,6 +74,10 @@ fun ColumnScope.TransactionPeerPushCreditComposable(
label = stringResource(id = R.string.send_peer_purpose),
info = t.info.summary ?: "",
)
+
+ if (t.txState.major == Pending || t.txState.major == Dialog) {
+ PeerExpirationComposable(t.info.expiration)
+ }
}
@Preview
diff --git a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushDebit.kt b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushDebit.kt
index 4dc712b5..cc1f35fa 100644
--- a/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushDebit.kt
+++ b/wallet/src/main/java/net/taler/wallet/peer/TransactionPeerPushDebit.kt
@@ -47,6 +47,7 @@ import net.taler.wallet.transactions.TransactionAction.Suspend
import net.taler.wallet.transactions.TransactionAmountComposable
import net.taler.wallet.transactions.TransactionInfoComposable
import net.taler.wallet.transactions.TransactionMajorState.Done
+import net.taler.wallet.transactions.TransactionMajorState.Dialog
import net.taler.wallet.transactions.TransactionMajorState.Pending
import net.taler.wallet.transactions.TransactionMinorState.CreatePurse
import net.taler.wallet.transactions.TransactionMinorState.KycRequired
@@ -99,6 +100,10 @@ fun ColumnScope.TransactionPeerPushDebitComposable(
label = stringResource(id = R.string.send_peer_purpose),
info = t.info.summary ?: "",
)
+
+ if (t.txState.major == Pending || t.txState.major == Dialog) {
+ PeerExpirationComposable(t.info.expiration)
+ }
}
@Composable
diff --git a/wallet/src/main/res/values/strings.xml b/wallet/src/main/res/values/strings.xml
index 89750709..ff02094e 100644
--- a/wallet/src/main/res/values/strings.xml
+++ b/wallet/src/main/res/values/strings.xml
@@ -347,6 +347,7 @@ GNU Taler is immune to many types of fraud such as credit card data theft, phish
Days
Hours
Expires in
+ Expires
Scan this QR code to receive %1$s
Purpose
Send money to another wallet