add verify msg relay
This commit is contained in:
@@ -348,7 +348,7 @@ class Nostr {
|
||||
is RelayMessageEnum.EndOfStoredEvents -> {
|
||||
val subscriptionId = message.subscriptionId
|
||||
|
||||
if (subscriptionId == "messages") {
|
||||
if (subscriptionId == "all-gift-wraps" || subscriptionId == "newest-gift-wraps") {
|
||||
onSubscriptionClose()
|
||||
}
|
||||
}
|
||||
@@ -471,7 +471,7 @@ class Nostr {
|
||||
return relayList
|
||||
}
|
||||
|
||||
private suspend fun getMsgRelayList(): List<RelayUrl> {
|
||||
suspend fun getDefaultMsgRelayList(): List<RelayUrl> {
|
||||
// Construct a list of messaging relays
|
||||
val msgRelayList = listOf(
|
||||
RelayUrl.parse("wss://relay.0xchat.com"),
|
||||
@@ -500,7 +500,7 @@ class Nostr {
|
||||
)
|
||||
|
||||
// Send messaging relay list event
|
||||
val msgRelayList = getMsgRelayList()
|
||||
val msgRelayList = getDefaultMsgRelayList()
|
||||
val msgRelayListEvent = EventBuilder.nip17RelayList(msgRelayList).signWithKeys(keys)
|
||||
|
||||
client?.sendEvent(
|
||||
@@ -578,6 +578,39 @@ class Nostr {
|
||||
}
|
||||
}
|
||||
|
||||
suspend fun setMsgRelays(urls: List<RelayUrl>) {
|
||||
try {
|
||||
val event = EventBuilder.nip17RelayList(urls).signAsync(signer)
|
||||
|
||||
client?.sendEvent(
|
||||
event = event,
|
||||
target = SendEventTarget.toNip65(),
|
||||
ackPolicy = AckPolicy.none(),
|
||||
)
|
||||
|
||||
val kind = Kind.fromStd(KindStandard.INBOX_RELAYS);
|
||||
val filter = Filter().kind(kind).author(signer.currentUser!!).limit(1u)
|
||||
val target = ReqTarget.auto(listOf(filter))
|
||||
val opts = SubscribeAutoCloseOptions().exitPolicy(ReqExitPolicy.ExitOnEose)
|
||||
|
||||
client?.subscribe(target = target, closeOn = opts)
|
||||
} catch (e: Exception) {
|
||||
throw IllegalStateException("Failed to set msg relays: ${e.message}", e)
|
||||
}
|
||||
}
|
||||
|
||||
suspend fun getMsgRelays(publicKey: PublicKey): List<RelayUrl> {
|
||||
try {
|
||||
val kind = Kind.fromStd(KindStandard.INBOX_RELAYS)
|
||||
val filter = Filter().kind(kind).author(publicKey).limit(1u)
|
||||
val events = client?.database()?.query(filter)
|
||||
|
||||
return nip17ExtractRelayList(events?.toVec()?.firstOrNull() ?: return emptyList())
|
||||
} catch (e: Exception) {
|
||||
throw IllegalStateException("Failed to get msg relays: ${e.message}", e)
|
||||
}
|
||||
}
|
||||
|
||||
suspend fun getChatRooms(): Set<Room>? {
|
||||
try {
|
||||
val userPubkey = signer.currentUser ?: throw IllegalStateException("User not signed in")
|
||||
|
||||
@@ -7,6 +7,7 @@ import io.ktor.client.plugins.contentnegotiation.ContentNegotiation
|
||||
import io.ktor.serialization.kotlinx.json.json
|
||||
import kotlinx.coroutines.NonCancellable
|
||||
import kotlinx.coroutines.channels.Channel
|
||||
import kotlinx.coroutines.delay
|
||||
import kotlinx.coroutines.flow.MutableSharedFlow
|
||||
import kotlinx.coroutines.flow.MutableStateFlow
|
||||
import kotlinx.coroutines.flow.StateFlow
|
||||
@@ -51,6 +52,9 @@ class NostrViewModel(
|
||||
private val _isPartialProcessedGiftWrap = MutableStateFlow(false)
|
||||
val isPartialProcessedGiftWrap = _isPartialProcessedGiftWrap.asStateFlow()
|
||||
|
||||
private val _isRelayListEmpty = MutableStateFlow(false)
|
||||
val isRelayListEmpty = _isRelayListEmpty.asStateFlow()
|
||||
|
||||
private val _newEvents = MutableSharedFlow<UnsignedEvent>(extraBufferCapacity = 100)
|
||||
val newEvents = _newEvents.asSharedFlow()
|
||||
|
||||
@@ -69,6 +73,7 @@ class NostrViewModel(
|
||||
startMetadataBatchHandler()
|
||||
getCacheMetadata()
|
||||
login()
|
||||
observeSignerAndCheckRelays()
|
||||
}
|
||||
|
||||
override fun onCleared() {
|
||||
@@ -202,6 +207,25 @@ class NostrViewModel(
|
||||
}
|
||||
}
|
||||
|
||||
private fun observeSignerAndCheckRelays() {
|
||||
viewModelScope.launch {
|
||||
while (true) {
|
||||
val pubkey = nostr.signer.currentUser
|
||||
|
||||
if (pubkey != null) {
|
||||
delay(3000)
|
||||
val relays = nostr.getMsgRelays(pubkey)
|
||||
if (relays.isEmpty()) {
|
||||
_isRelayListEmpty.value = true
|
||||
}
|
||||
break
|
||||
}
|
||||
|
||||
delay(1000)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun requestMetadata(pubkey: PublicKey) {
|
||||
if (seenPublicKeys.add(pubkey)) {
|
||||
viewModelScope.launch {
|
||||
@@ -234,6 +258,10 @@ class NostrViewModel(
|
||||
}
|
||||
}
|
||||
|
||||
fun dismissRelayWarning() {
|
||||
_isRelayListEmpty.value = false
|
||||
}
|
||||
|
||||
private suspend fun getOrInitAppKeys(): Keys {
|
||||
val secret = secretStore.get("app_keys")
|
||||
|
||||
@@ -349,6 +377,15 @@ class NostrViewModel(
|
||||
}
|
||||
}
|
||||
|
||||
suspend fun useDefaultMsgRelayList() {
|
||||
try {
|
||||
val defaultRelays = nostr.getDefaultMsgRelayList()
|
||||
nostr.setMsgRelays(defaultRelays)
|
||||
} catch (e: Exception) {
|
||||
showError("Error: ${e.message}")
|
||||
}
|
||||
}
|
||||
|
||||
fun createChatRoom(to: List<PublicKey>): Long {
|
||||
if (nostr.signer.currentUser == null) throw IllegalStateException("User not signed in")
|
||||
if (to.isEmpty()) throw IllegalArgumentException("At least one recipient is required")
|
||||
|
||||
Reference in New Issue
Block a user