Skip to content

Commit e0feebd

Browse files
zecakehstefanceriu
authored andcommitted
fix(sdk): Support unauthenticated media endpoint in Client::load_or_fetch_max_upload_size
Signed-off-by: Kévin Commaille <[email protected]>
1 parent 0fee716 commit e0feebd

File tree

2 files changed

+90
-8
lines changed

2 files changed

+90
-8
lines changed

crates/matrix-sdk/src/client/mod.rs

Lines changed: 69 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ use ruma::{
4545
client::{
4646
account::whoami,
4747
alias::{create_alias, delete_alias, get_alias},
48+
authenticated_media,
4849
device::{delete_devices, get_devices, update_device},
4950
directory::{get_public_rooms, get_public_rooms_filtered},
5051
discovery::{
@@ -55,6 +56,7 @@ use ruma::{
5556
error::ErrorKind,
5657
filter::{create_filter::v3::Request as FilterUploadRequest, FilterDefinition},
5758
knock::knock_room,
59+
media,
5860
membership::{join_room_by_id, join_room_by_id_or_alias},
5961
room::create_room,
6062
session::login::v3::DiscoveryInfo,
@@ -2792,12 +2794,22 @@ impl Client {
27922794
return Ok(data.to_owned());
27932795
}
27942796

2795-
let response = self
2796-
.send(ruma::api::client::authenticated_media::get_media_config::v1::Request::default())
2797-
.await?;
2797+
// Use the authenticated endpoint when the server supports it.
2798+
let supported_versions = self.supported_versions().await?;
2799+
let use_auth =
2800+
authenticated_media::get_media_config::v1::Request::is_supported(&supported_versions);
27982801

2799-
match max_upload_size_lock.set(response.upload_size) {
2800-
Ok(_) => Ok(response.upload_size),
2802+
let upload_size = if use_auth {
2803+
self.send(authenticated_media::get_media_config::v1::Request::default())
2804+
.await?
2805+
.upload_size
2806+
} else {
2807+
#[allow(deprecated)]
2808+
self.send(media::get_media_config::v3::Request::default()).await?.upload_size
2809+
};
2810+
2811+
match max_upload_size_lock.set(upload_size) {
2812+
Ok(_) => Ok(upload_size),
28012813
Err(error) => {
28022814
Err(Error::Media(MediaError::FetchMaxUploadSizeFailed(error.to_string())))
28032815
}
@@ -3803,7 +3815,9 @@ pub(crate) mod tests {
38033815
}
38043816

38053817
#[async_test]
3806-
async fn test_load_or_fetch_max_upload_size() {
3818+
async fn test_load_or_fetch_max_upload_size_with_auth_matrix_version() {
3819+
// The default Matrix version we use is 1.11 or higher, so authenticated media
3820+
// is supported.
38073821
let server = MatrixMockServer::new().await;
38083822
let client = server.client_builder().build().await;
38093823

@@ -3815,6 +3829,55 @@ pub(crate) mod tests {
38153829
assert_eq!(*client.inner.server_max_upload_size.lock().await.get().unwrap(), uint!(2));
38163830
}
38173831

3832+
#[async_test]
3833+
async fn test_load_or_fetch_max_upload_size_with_auth_stable_feature() {
3834+
// The server must advertise support for the stable feature for authenticated
3835+
// media support, so we mock the `GET /versions` response.
3836+
let server = MatrixMockServer::new().await;
3837+
let client = server.client_builder().no_server_versions().build().await;
3838+
3839+
server
3840+
.mock_versions()
3841+
.ok_custom(
3842+
&["v1.7", "v1.8", "v1.9", "v1.10"],
3843+
&[("org.matrix.msc3916.stable", true)].into(),
3844+
)
3845+
.named("versions")
3846+
.expect(1)
3847+
.mount()
3848+
.await;
3849+
3850+
assert!(!client.inner.server_max_upload_size.lock().await.initialized());
3851+
3852+
server.mock_authenticated_media_config().ok(uint!(2)).mock_once().mount().await;
3853+
client.load_or_fetch_max_upload_size().await.unwrap();
3854+
3855+
assert_eq!(*client.inner.server_max_upload_size.lock().await.get().unwrap(), uint!(2));
3856+
}
3857+
3858+
#[async_test]
3859+
async fn test_load_or_fetch_max_upload_size_no_auth() {
3860+
// The server must not support Matrix 1.11 or higher for unauthenticated
3861+
// media requests, so we mock the `GET /versions` response.
3862+
let server = MatrixMockServer::new().await;
3863+
let client = server.client_builder().no_server_versions().build().await;
3864+
3865+
server
3866+
.mock_versions()
3867+
.ok_custom(&["v1.1"], &Default::default())
3868+
.named("versions")
3869+
.expect(1)
3870+
.mount()
3871+
.await;
3872+
3873+
assert!(!client.inner.server_max_upload_size.lock().await.initialized());
3874+
3875+
server.mock_media_config().ok(uint!(2)).mock_once().mount().await;
3876+
client.load_or_fetch_max_upload_size().await.unwrap();
3877+
3878+
assert_eq!(*client.inner.server_max_upload_size.lock().await.get().unwrap(), uint!(2));
3879+
}
3880+
38183881
#[async_test]
38193882
async fn test_uploading_a_too_large_media_file() {
38203883
let server = MatrixMockServer::new().await;

crates/matrix-sdk/src/test_utils/mocks/mod.rs

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1226,12 +1226,19 @@ impl MatrixMockServer {
12261226
}
12271227

12281228
/// Create a prebuilt mock for the endpoint used to get the media config of
1229-
/// the homeserver.
1229+
/// the homeserver that requires authentication.
12301230
pub fn mock_authenticated_media_config(
12311231
&self,
12321232
) -> MockEndpoint<'_, AuthenticatedMediaConfigEndpoint> {
12331233
let mock = Mock::given(method("GET")).and(path("/_matrix/client/v1/media/config"));
1234-
self.mock_endpoint(mock, AuthenticatedMediaConfigEndpoint)
1234+
self.mock_endpoint(mock, AuthenticatedMediaConfigEndpoint).expect_default_access_token()
1235+
}
1236+
1237+
/// Create a prebuilt mock for the endpoint used to get the media config of
1238+
/// the homeserver without requiring authentication.
1239+
pub fn mock_media_config(&self) -> MockEndpoint<'_, MediaConfigEndpoint> {
1240+
let mock = Mock::given(method("GET")).and(path("/_matrix/media/v3/config"));
1241+
self.mock_endpoint(mock, MediaConfigEndpoint)
12351242
}
12361243

12371244
/// Create a prebuilt mock for the endpoint used to log into a session.
@@ -3495,6 +3502,18 @@ impl<'a> MockEndpoint<'a, AuthenticatedMediaConfigEndpoint> {
34953502
}
34963503
}
34973504

3505+
/// A prebuilt mock for `GET /_matrix/media/v3/config` request.
3506+
pub struct MediaConfigEndpoint;
3507+
3508+
impl<'a> MockEndpoint<'a, MediaConfigEndpoint> {
3509+
/// Returns a successful response with the provided max upload size.
3510+
pub fn ok(self, max_upload_size: UInt) -> MatrixMock<'a> {
3511+
self.respond_with(ResponseTemplate::new(200).set_body_json(json!({
3512+
"m.upload.size": max_upload_size,
3513+
})))
3514+
}
3515+
}
3516+
34983517
/// A prebuilt mock for `POST /login` requests.
34993518
pub struct LoginEndpoint;
35003519

0 commit comments

Comments
 (0)