feat(crypto): Add get_all_rooms_pending_key_bundle to store trait

Signed-off-by: Skye Elliot <actuallyori@gmail.com>
This commit is contained in:
Skye Elliot
2026-02-25 14:11:50 +00:00
parent 640fa4854f
commit fadfd98bee
4 changed files with 55 additions and 0 deletions
@@ -782,6 +782,10 @@ impl CryptoStore for MemoryStore {
Ok(self.rooms_pending_key_bundle.read().get(room_id).cloned())
}
async fn get_all_rooms_pending_key_bundles(&self) -> Result<Vec<RoomPendingKeyBundleDetails>> {
Ok(self.rooms_pending_key_bundle.read().values().cloned().collect())
}
async fn has_downloaded_all_room_keys(&self, room_id: &RoomId) -> Result<bool> {
let guard = self.room_key_backups_fully_downloaded.read();
Ok(guard.contains(room_id))
@@ -1629,6 +1633,12 @@ mod integration_tests {
self.0.get_pending_key_bundle_details_for_room(room_id).await
}
async fn get_all_rooms_pending_key_bundles(
&self,
) -> Result<Vec<RoomPendingKeyBundleDetails>, Self::Error> {
self.0.get_all_rooms_pending_key_bundles().await
}
async fn get_custom_value(&self, key: &str) -> Result<Option<Vec<u8>>, Self::Error> {
self.0.get_custom_value(key).await
}
@@ -363,6 +363,12 @@ pub trait CryptoStore: AsyncTraitDeps {
room_id: &RoomId,
) -> Result<Option<RoomPendingKeyBundleDetails>, Self::Error>;
/// Retrieve a list of details for all rooms where we are currently awaiting
/// key bundles to be received.
async fn get_all_rooms_pending_key_bundles(
&self,
) -> Result<Vec<RoomPendingKeyBundleDetails>, Self::Error>;
/// Get whether we have previously downloaded all room keys for a particular
/// room from the key backup in advance of building a room key bundle.
async fn has_downloaded_all_room_keys(&self, room_id: &RoomId) -> Result<bool, Self::Error>;
@@ -649,6 +655,12 @@ impl<T: CryptoStore> CryptoStore for EraseCryptoStoreError<T> {
self.0.get_pending_key_bundle_details_for_room(room_id).await.map_err(Into::into)
}
async fn get_all_rooms_pending_key_bundles(
&self,
) -> Result<Vec<RoomPendingKeyBundleDetails>, Self::Error> {
self.0.get_all_rooms_pending_key_bundles().await.map_err(Into::into)
}
async fn get_custom_value(&self, key: &str) -> Result<Option<Vec<u8>>, Self::Error> {
self.0.get_custom_value(key).await.map_err(Into::into)
}
@@ -1608,6 +1608,24 @@ impl_crypto_store! {
Ok(result)
}
async fn get_all_rooms_pending_key_bundles(&self) -> Result<Vec<RoomPendingKeyBundleDetails>> {
let result = self
.inner
.transaction(keys::ROOMS_PENDING_KEY_BUNDLE)
.with_mode(TransactionMode::Readonly)
.build()?
.object_store(keys::ROOMS_PENDING_KEY_BUNDLE)?
.get_all()
.await?
.map(|result| {
result
.map_err(Into::into)
.and_then(|v| self.serializer.deserialize_value(v).map_err(Into::into))
})
.collect::<Result<Vec<_>>>()?;
Ok(result)
}
async fn get_custom_value(&self, key: &str) -> Result<Option<Vec<u8>>> {
self.inner
.transaction(keys::CORE)
@@ -903,6 +903,12 @@ trait SqliteObjectCryptoStoreExt: SqliteAsyncConnExt {
.optional()?)
}
async fn get_all_rooms_pending_key_bundle(&self) -> Result<Vec<Vec<u8>>> {
Ok(self
.query_many("SELECT data FROM rooms_pending_key_bundle", (), |row| row.get(0))
.await?)
}
async fn has_downloaded_all_room_keys(&self, room_id: Key) -> Result<bool> {
Ok(self
.query_row(
@@ -1581,6 +1587,15 @@ impl CryptoStore for SqliteCryptoStore {
Ok(Some(details))
}
async fn get_all_rooms_pending_key_bundles(&self) -> Result<Vec<RoomPendingKeyBundleDetails>> {
let details = self.read().await?.get_all_rooms_pending_key_bundle().await?;
let room_ids = details
.into_iter()
.map(|value| self.deserialize_value(&value))
.collect::<Result<_, _>>()?;
Ok(room_ids)
}
async fn get_custom_value(&self, key: &str) -> Result<Option<Vec<u8>>> {
let Some(serialized) = self.read().await?.get_kv(key).await? else {
return Ok(None);