mirror of
https://github.com/vitorpamplona/amethyst.git
synced 2026-10-06 03:38:23 +00:00
fix(relay-auth): two copy defects the prompt only shows once it can fire
Both found on device once prompts started appearing again. An unloaded counterparty rendered as a shortened npub: "It won't serve posts from npub1j9hlsge8...kqy003h0 unless you log in." `User.toBestDisplayName()` falls back to `pubkeyDisplayHex()`, so the sentence presented an unrecognizable key as if it were a person's name — the one thing the reason line exists to supply. The counterparty now falls back to the generic "someone you haven't loaded yet", which says exactly as much and reads as language. The dialog *title* deliberately keeps the npub: it names the account whose identity is about to be revealed, and there an exact key beats a generic phrase. "It's also holding back 1 other thing(s)." was a `<string>` with a parenthesised plural, which res/CLAUDE.md rules out — the noun declines on count in the Slavic and Semitic locales we ship. Now a `<plurals>`. It exists only in values/, so no other locale needed converting. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
0bddb64abc
commit
bc3ce1139b
+32
-2
@@ -51,6 +51,7 @@ import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.draw.clip
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.res.pluralStringResource
|
||||
import androidx.compose.ui.text.AnnotatedString
|
||||
import androidx.compose.ui.text.Placeholder
|
||||
import androidx.compose.ui.text.PlaceholderVerticalAlign
|
||||
@@ -399,7 +400,7 @@ private fun secondaryLine(
|
||||
): String? {
|
||||
val others = purposes.filter { it !== primary }
|
||||
if (others.isEmpty()) return null
|
||||
return stringRes(R.string.relay_auth_also_holding_back, others.size)
|
||||
return pluralStringResource(R.plurals.relay_auth_also_holding_back, others.size, others.size)
|
||||
}
|
||||
|
||||
/** A short label for a set of counterparties: the first person's name, or "Alice and 4 others". */
|
||||
@@ -409,10 +410,39 @@ private fun counterpartyLabel(
|
||||
accountViewModel: AccountViewModel,
|
||||
): String {
|
||||
val first = pubkeys.firstOrNull() ?: return ""
|
||||
val name = rememberDisplayName(first, accountViewModel)
|
||||
val name = rememberCounterpartyName(first, accountViewModel)
|
||||
return if (pubkeys.size > 1) stringRes(R.string.relay_auth_name_and_n_others, name, (pubkeys.size - 1).toString()) else name
|
||||
}
|
||||
|
||||
/**
|
||||
* Like [rememberDisplayName], but never renders a bare npub.
|
||||
*
|
||||
* The reason sentence exists to name *a person* — "it won't serve posts from Alice". A pubkey we
|
||||
* have no metadata for has no name to give, and [User.toBestDisplayName] falls back to the shortened
|
||||
* npub, so the sentence became "it won't serve posts from npub1j9hlsge8…kqy003h0 unless you log in":
|
||||
* a string the reader cannot recognize, dressed up as if it were a name. Falling back to the generic
|
||||
* phrase says the same amount and reads as language.
|
||||
*
|
||||
* The dialog *title* deliberately keeps the npub ([rememberDisplayName]): it names the account whose
|
||||
* identity is about to be revealed, where an unrecognizable-but-exact key still beats "someone you
|
||||
* haven't loaded yet" — the user can at least match it against the account they are logged in as.
|
||||
*/
|
||||
@Composable
|
||||
private fun rememberCounterpartyName(
|
||||
pubkey: HexKey,
|
||||
accountViewModel: AccountViewModel,
|
||||
): String {
|
||||
var user by remember(pubkey) { mutableStateOf(accountViewModel.getUserIfExists(pubkey)) }
|
||||
if (user == null) {
|
||||
LaunchedEffect(pubkey) { user = accountViewModel.checkGetOrCreateUser(pubkey) }
|
||||
}
|
||||
val loaded = user ?: return stringRes(R.string.relay_auth_someone_unloaded)
|
||||
val metadata by observeUserInfo(loaded, accountViewModel)
|
||||
return metadata?.info?.bestName()
|
||||
?: loaded.metadataOrNull()?.bestName()
|
||||
?: stringRes(R.string.relay_auth_someone_unloaded)
|
||||
}
|
||||
|
||||
/**
|
||||
* A display name for a venue id — a public chat channel (64-hex event id), a NIP-53 live activity,
|
||||
* or a NIP-72 community.
|
||||
|
||||
@@ -1165,7 +1165,10 @@
|
||||
<string name="relay_auth_why_other">It asks everyone to log in. Amethyst can\'t tell what it\'s holding back.</string>
|
||||
<string name="relay_auth_someone_unloaded">someone you haven\'t loaded yet</string>
|
||||
<string name="relay_auth_name_and_n_others">%1$s and %2$s others</string>
|
||||
<string name="relay_auth_also_holding_back">It\'s also holding back %1$d other thing(s).</string>
|
||||
<plurals name="relay_auth_also_holding_back">
|
||||
<item quantity="one">It\'s also holding back %1$d other thing.</item>
|
||||
<item quantity="other">It\'s also holding back %1$d other things.</item>
|
||||
</plurals>
|
||||
<string name="relay_auth_remember_relay">Remember for this relay</string>
|
||||
<string name="relay_auth_log_in">Log in</string>
|
||||
<string name="relay_auth_not_now">Not now</string>
|
||||
|
||||
Reference in New Issue
Block a user