Skip to content

Commit d4bbca7

Browse files
committed
test: add the start of an integration test for room history sharing
This is only a partial test, since we haven't yet implemented the receiver side of the history-sharing messages.
1 parent a38ea0f commit d4bbca7

File tree

2 files changed

+120
-8
lines changed

2 files changed

+120
-8
lines changed

Diff for: testing/matrix-sdk-integration-testing/src/helpers.rs

+4-3
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ use matrix_sdk::{
1616
RoomId,
1717
},
1818
sliding_sync::VersionBuilder,
19+
sync::SyncResponse,
1920
Client, ClientBuilder, Room,
2021
};
2122
use once_cell::sync::Lazy;
@@ -185,7 +186,7 @@ impl SyncTokenAwareClient {
185186
Self { client, token: Arc::new(None.into()) }
186187
}
187188

188-
pub async fn sync_once(&self) -> Result<()> {
189+
pub async fn sync_once(&self) -> Result<SyncResponse> {
189190
let mut settings = SyncSettings::default().timeout(Duration::from_secs(1));
190191

191192
let token = { self.token.lock().unwrap().clone() };
@@ -197,9 +198,9 @@ impl SyncTokenAwareClient {
197198

198199
let mut prev_token = self.token.lock().unwrap();
199200
if prev_token.as_ref() != Some(&response.next_batch) {
200-
*prev_token = Some(response.next_batch);
201+
*prev_token = Some(response.next_batch.clone());
201202
}
202-
Ok(())
203+
Ok(response)
203204
}
204205
}
205206

Diff for: testing/matrix-sdk-integration-testing/src/tests/e2ee.rs

+116-5
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ use assert_matches2::assert_let;
99
use assign::assign;
1010
use matrix_sdk::{
1111
assert_next_eq_with_timeout,
12-
crypto::{format_emojis, SasState},
12+
crypto::{format_emojis, SasState, UserDevices},
1313
encryption::{
1414
backups::BackupState,
1515
recovery::{Recovery, RecoveryState},
@@ -19,17 +19,21 @@ use matrix_sdk::{
1919
BackupDownloadStrategy, EncryptionSettings, LocalTrust,
2020
},
2121
ruma::{
22-
api::client::room::create_room::v3::Request as CreateRoomRequest,
22+
api::client::{
23+
message::send_message_event,
24+
room::create_room::v3::{Request as CreateRoomRequest, RoomPreset},
25+
},
2326
events::{
2427
key::verification::{request::ToDeviceKeyVerificationRequestEvent, VerificationMethod},
2528
room::message::{
2629
MessageType, OriginalSyncRoomMessageEvent, RoomMessageEventContent,
2730
SyncRoomMessageEvent,
2831
},
2932
secret_storage::secret::SecretEventContent,
30-
GlobalAccountDataEventType, OriginalSyncMessageLikeEvent,
33+
GlobalAccountDataEventType, MessageLikeEventType, OriginalSyncMessageLikeEvent,
3134
},
32-
OwnedEventId,
35+
serde::Raw,
36+
OwnedEventId, TransactionId, UserId,
3337
},
3438
timeout::timeout,
3539
Client,
@@ -39,7 +43,7 @@ use matrix_sdk_ui::{
3943
sync_service::SyncService,
4044
};
4145
use similar_asserts::assert_eq;
42-
use tracing::{debug, warn};
46+
use tracing::{debug, info, warn};
4347

4448
use crate::helpers::{SyncTokenAwareClient, TestClientBuilder};
4549

@@ -1175,3 +1179,110 @@ async fn test_recovery_disabling_deletes_secret_storage_secrets() -> Result<()>
11751179

11761180
Ok(())
11771181
}
1182+
1183+
/// When we invite another user to a room with "joined" history visibility, we
1184+
/// share the encryption history.
1185+
#[tokio::test(flavor = "multi_thread", worker_threads = 4)]
1186+
async fn test_history_share_on_invite() -> Result<()> {
1187+
let encryption_settings =
1188+
EncryptionSettings { auto_enable_cross_signing: true, ..Default::default() };
1189+
1190+
let alice = TestClientBuilder::new("alice")
1191+
.use_sqlite()
1192+
.encryption_settings(encryption_settings)
1193+
.build()
1194+
.await?;
1195+
1196+
let alice_sync_service = Arc::new(
1197+
SyncService::builder(alice.clone())
1198+
.build()
1199+
.await
1200+
.expect("Could not build alice sync service"),
1201+
);
1202+
1203+
alice.encryption().wait_for_e2ee_initialization_tasks().await;
1204+
alice_sync_service.start().await;
1205+
1206+
let bob = SyncTokenAwareClient::new(
1207+
TestClientBuilder::new("bob").encryption_settings(encryption_settings).build().await?,
1208+
);
1209+
1210+
{
1211+
// Alice and Bob share an encrypted room
1212+
// TODO: get rid of all of this: history sharing should work even if Bob and
1213+
// Alice do not share a room
1214+
let alice_shared_room = alice
1215+
.create_room(assign!(CreateRoomRequest::new(), {preset: Some(RoomPreset::PublicChat)}))
1216+
.await?;
1217+
let shared_room_id = alice_shared_room.room_id();
1218+
alice_shared_room.enable_encryption().await?;
1219+
bob.join_room_by_id(shared_room_id).await.expect("Bob should have joined the room");
1220+
1221+
// Bob sends a message to trigger another sync from Alice, which causes her to
1222+
// send out the outgoing requests
1223+
//
1224+
// FIXME: this appears to be needed due to a bug in the sliding sync client,
1225+
// which means it does not send out outgoing requests caused by a
1226+
// /sync response
1227+
let request = send_message_event::v3::Request::new_raw(
1228+
shared_room_id.to_owned(),
1229+
TransactionId::new(),
1230+
MessageLikeEventType::Message,
1231+
Raw::new(&RoomMessageEventContent::text_plain("")).unwrap().cast(),
1232+
);
1233+
bob.send(request).await?;
1234+
1235+
// Sanity check: Both users see the others' device
1236+
async fn devices_seen(client: &Client, other: &UserId) -> UserDevices {
1237+
client
1238+
.olm_machine_for_testing()
1239+
.await
1240+
.as_ref()
1241+
.unwrap()
1242+
.get_user_devices(other, Some(Duration::from_secs(1)))
1243+
.await
1244+
.unwrap()
1245+
}
1246+
1247+
let bob_devices = devices_seen(&alice, bob.user_id().unwrap()).await;
1248+
assert_eq!(bob_devices.devices().count(), 1, "Alice did not see bob's device");
1249+
1250+
bob.sync_once().await?;
1251+
let alice_devices = devices_seen(&bob, alice.user_id().unwrap()).await;
1252+
assert_eq!(alice_devices.devices().count(), 1, "Bob did not see Alice's device");
1253+
}
1254+
1255+
// Alice creates a room ...
1256+
let alice_room = alice
1257+
.create_room(assign!(CreateRoomRequest::new(), {
1258+
preset: Some(RoomPreset::PublicChat),
1259+
}))
1260+
.await?;
1261+
alice_room.enable_encryption().await?;
1262+
1263+
info!(room_id = ?alice_room.room_id(), "Alice has created and enabled encryption in the room");
1264+
1265+
// ... and sends a message
1266+
alice_room
1267+
.send(RoomMessageEventContent::text_plain("Hello Bob"))
1268+
.await
1269+
.expect("We should be able to send a message to the room");
1270+
1271+
// Alice invites Bob to the room
1272+
// TODO: invite Bob rather than just call `share_history`
1273+
alice_room.share_history(bob.user_id().unwrap()).await?;
1274+
1275+
let bob_response = bob.sync_once().await?;
1276+
1277+
// Bob should have received a to-device event with the payload
1278+
assert_eq!(bob_response.to_device.len(), 1);
1279+
let to_device_event = &bob_response.to_device[0];
1280+
assert_eq!(
1281+
to_device_event.get_field::<String>("type").unwrap().unwrap(),
1282+
"io.element.msc4268.room_key_bundle"
1283+
);
1284+
1285+
// TODO: ensure Bob can decrypt the content
1286+
1287+
Ok(())
1288+
}

0 commit comments

Comments
 (0)