From eb4ccd1880373bd5fa0b451f7288c86ad69d77e1 Mon Sep 17 00:00:00 2001 From: Donjuanplatinum Date: Sun, 15 Mar 2026 00:13:46 +0800 Subject: [PATCH] impl MSC4380 --- crates/ruma-client-api/CHANGELOG.md | 5 ++ crates/ruma-client-api/Cargo.toml | 1 + crates/ruma-client-api/src/error.rs | 19 ++++++ .../ruma-client-api/src/error/kind_serde.rs | 2 + crates/ruma-client-api/src/lib.rs | 2 +- .../src/membership/invite_user.rs | 1 - crates/ruma-common/CHANGELOG.md | 4 ++ crates/ruma-common/Cargo.toml | 1 + crates/ruma-common/src/api/metadata.rs | 9 +++ crates/ruma-events/CHANGELOG.md | 3 + crates/ruma-events/Cargo.toml | 1 + crates/ruma-events/src/enums.rs | 3 + .../src/invite_permission_config.rs | 67 +++++++++++++++++++ crates/ruma-events/src/lib.rs | 2 + crates/ruma/Cargo.toml | 6 ++ 15 files changed, 124 insertions(+), 2 deletions(-) create mode 100644 crates/ruma-events/src/invite_permission_config.rs diff --git a/crates/ruma-client-api/CHANGELOG.md b/crates/ruma-client-api/CHANGELOG.md index 195e1f0bf0..b022f42856 100644 --- a/crates/ruma-client-api/CHANGELOG.md +++ b/crates/ruma-client-api/CHANGELOG.md @@ -54,6 +54,11 @@ Breaking changes: Improvements: +- Add `M_INVITE_BLOCKED` candidate error code proposed by + [MSC4380](https://github.com/matrix-org/matrix-spec-proposals/pull/4380) + sharing an unstable prefix with the preceding + [MSC4155](https://github.com/matrix-org/matrix-spec-proposals/pull/4155). + - Added support for the sliding sync extension for thread subscriptions, as well as the accompanying endpoint, both from experimental MSC4308. - Added support for the experiment MSC4306 thread subscription endpoints. diff --git a/crates/ruma-client-api/Cargo.toml b/crates/ruma-client-api/Cargo.toml index a203eaa027..0392809589 100644 --- a/crates/ruma-client-api/Cargo.toml +++ b/crates/ruma-client-api/Cargo.toml @@ -57,6 +57,7 @@ unstable-msc4222 = [] # Thread subscription support. unstable-msc4306 = [] unstable-msc4308 = [] +unstable-msc4380 = ["ruma-common/unstable-msc4380", "ruma-events/unstable-msc4380"] [dependencies] as_variant = { workspace = true } diff --git a/crates/ruma-client-api/src/error.rs b/crates/ruma-client-api/src/error.rs index 6ba66b0563..68627929ab 100644 --- a/crates/ruma-client-api/src/error.rs +++ b/crates/ruma-client-api/src/error.rs @@ -169,6 +169,13 @@ pub enum ErrorKind { /// The desired user name is not valid. InvalidUsername, + /// `M_INVITE_BLOCKED` + /// + /// The invite was interdicted by moderation tools or configured access controls without having + /// been witnessed by the invitee. + #[cfg(feature = "unstable-msc4380")] + InviteBlocked, + /// `M_LIMIT_EXCEEDED` /// /// The request has been refused due to [rate limiting]: too many requests have been sent in a @@ -453,6 +460,8 @@ impl ErrorKind { ErrorKind::InvalidParam => ErrorCode::InvalidParam, ErrorKind::InvalidRoomState => ErrorCode::InvalidRoomState, ErrorKind::InvalidUsername => ErrorCode::InvalidUsername, + #[cfg(feature = "unstable-msc4380")] + ErrorKind::InviteBlocked => ErrorCode::InviteBlocked, ErrorKind::LimitExceeded { .. } => ErrorCode::LimitExceeded, ErrorKind::MissingParam => ErrorCode::MissingParam, ErrorKind::MissingToken => ErrorCode::MissingToken, @@ -633,6 +642,16 @@ pub enum ErrorCode { /// The desired user name is not valid. InvalidUsername, + /// `M_INVITE_BLOCKED` + /// + /// The invite was interdicted by moderation tools or configured access controls without having + /// been witnessed by the invitee. + /// + /// Unstable prefix intentionally shared with MSC4155 for compatibility. + #[cfg(feature = "unstable-msc4380")] + #[ruma_enum(rename = "ORG.MATRIX.MSC4155.INVITE_BLOCKED")] + InviteBlocked, + /// `M_LIMIT_EXCEEDED` /// /// The request has been refused due to [rate limiting]: too many requests have been sent in a diff --git a/crates/ruma-client-api/src/error/kind_serde.rs b/crates/ruma-client-api/src/error/kind_serde.rs index 5b31faeccd..c0b6052101 100644 --- a/crates/ruma-client-api/src/error/kind_serde.rs +++ b/crates/ruma-client-api/src/error/kind_serde.rs @@ -199,6 +199,8 @@ impl<'de> Visitor<'de> for ErrorKindVisitor { ErrorCode::InvalidParam => ErrorKind::InvalidParam, ErrorCode::InvalidRoomState => ErrorKind::InvalidRoomState, ErrorCode::InvalidUsername => ErrorKind::InvalidUsername, + #[cfg(feature = "unstable-msc4380")] + ErrorCode::InviteBlocked => ErrorKind::InviteBlocked, ErrorCode::LimitExceeded => ErrorKind::LimitExceeded { retry_after: retry_after_ms .map(from_json_value::) diff --git a/crates/ruma-client-api/src/lib.rs b/crates/ruma-client-api/src/lib.rs index 341eb1dac9..19e94b46f3 100644 --- a/crates/ruma-client-api/src/lib.rs +++ b/crates/ruma-client-api/src/lib.rs @@ -6,7 +6,7 @@ //! [client-api]: https://spec.matrix.org/latest/client-server-api/ #![cfg(any(feature = "client", feature = "server"))] -#![cfg_attr(docsrs, feature(doc_cfg))] +#![cfg_attr(docsrs, feature(doc_auto_cfg))] #![warn(missing_docs)] pub mod account; diff --git a/crates/ruma-client-api/src/membership/invite_user.rs b/crates/ruma-client-api/src/membership/invite_user.rs index a96b1937e1..4b59bf7f7a 100644 --- a/crates/ruma-client-api/src/membership/invite_user.rs +++ b/crates/ruma-client-api/src/membership/invite_user.rs @@ -5,7 +5,6 @@ pub mod v3 { //! `/v3/` ([spec (MXID)][spec-mxid], [spec (3PID)][spec-3pid]) //! - //! This endpoint has two forms: one to invite a user //! [by their Matrix identifier][spec-mxid], and one to invite a user //! [by their third party identifier][spec-3pid]. //! diff --git a/crates/ruma-common/CHANGELOG.md b/crates/ruma-common/CHANGELOG.md index 030377badc..ab44915ba0 100644 --- a/crates/ruma-common/CHANGELOG.md +++ b/crates/ruma-common/CHANGELOG.md @@ -2,6 +2,8 @@ Improvements: +- Add `M_INVITE_BLOCKED` candidate error code proposed by + [MSC4380](https://github.com/matrix-org/matrix-spec-proposals/pull/4380). - Add `MatrixVersion::V1_16` - Remove support for the `org.matrix.hydra.11` room version and the corresponding `unstable-hydra` cargo feature. It should only have been used @@ -87,6 +89,8 @@ Bug fix: Improvements: +- Add `org.matrix.msc4380` unstable feature support to `/versions`. + - Implement the `Zeroize` trait for the `Base64` type. - `ProtocolInstance` has an `instance_id` field, due to a clarification in the spec. diff --git a/crates/ruma-common/Cargo.toml b/crates/ruma-common/Cargo.toml index f76f3679df..82b76c1dff 100644 --- a/crates/ruma-common/Cargo.toml +++ b/crates/ruma-common/Cargo.toml @@ -38,6 +38,7 @@ unstable-msc4186 = [] # Thread subscriptions. unstable-msc4306 = [] unstable-msc4361 = [] +unstable-msc4380 = [] # Allow IDs to exceed 255 bytes. compat-arbitrary-length-ids = [ diff --git a/crates/ruma-common/src/api/metadata.rs b/crates/ruma-common/src/api/metadata.rs index 1e125da0df..2f94b31c5a 100644 --- a/crates/ruma-common/src/api/metadata.rs +++ b/crates/ruma-common/src/api/metadata.rs @@ -1265,6 +1265,15 @@ pub enum FeatureFlag { #[ruma_enum(rename = "org.matrix.simplified_msc3575")] Msc4186, + /// `org.matrix.msc4380_invite_permission_config` ([MSC]) + /// + /// Invite Blocking. + /// + /// [MSC]: https://github.com/matrix-org/matrix-spec-proposals/pull/4380 + #[cfg(feature = "unstable-msc4380")] + #[ruma_enum(rename = "org.matrix.msc4380")] + Msc4380, + #[doc(hidden)] _Custom(PrivOwnedStr), } diff --git a/crates/ruma-events/CHANGELOG.md b/crates/ruma-events/CHANGELOG.md index f816f76cb9..438f2c7f4b 100644 --- a/crates/ruma-events/CHANGELOG.md +++ b/crates/ruma-events/CHANGELOG.md @@ -16,6 +16,9 @@ Breaking changes: Improvements: +- Add unstable support for the `m.invite_permission_config` account data event which blocks + invites to a user, wholesale: ([MSC4380](https://github.com/matrix-org/matrix-spec-proposals/pull/4380)). + - Add support for the room account data `m.space_order` event which powers top level space ordering as per [MSC3230](https://github.com/matrix-org/matrix-spec-proposals/pull/3230). - Add `m.rtc.notification` event support and deprecate the (non MSC conformant) diff --git a/crates/ruma-events/Cargo.toml b/crates/ruma-events/Cargo.toml index 2e19dede75..9e17ba7627 100644 --- a/crates/ruma-events/Cargo.toml +++ b/crates/ruma-events/Cargo.toml @@ -53,6 +53,7 @@ unstable-msc4319 = [] unstable-msc4310 = [] unstable-msc4334 = ["dep:language-tags"] unstable-msc4359 = [] +unstable-msc4380 = ["ruma-common/unstable-msc4380"] unstable-msc3230 = [] # Allow some mandatory fields to be missing, defaulting them to an empty string diff --git a/crates/ruma-events/src/enums.rs b/crates/ruma-events/src/enums.rs index 3f7885c755..904548f290 100644 --- a/crates/ruma-events/src/enums.rs +++ b/crates/ruma-events/src/enums.rs @@ -39,6 +39,9 @@ event_enum! { "m.push_rules" => super::push_rules, "m.secret_storage.default_key" => super::secret_storage::default_key, "m.secret_storage.key.*" => super::secret_storage::key, + #[cfg(feature = "unstable-msc4380")] + #[ruma_enum(ident = InvitePermissionConfig, alias = "m.invite_permission_config")] + "org.matrix.msc4380.invite_permission_config" => super::invite_permission_config, #[cfg(feature = "unstable-msc4278")] "m.media_preview_config" => super::media_preview_config, #[cfg(feature = "unstable-msc4278")] diff --git a/crates/ruma-events/src/invite_permission_config.rs b/crates/ruma-events/src/invite_permission_config.rs new file mode 100644 index 0000000000..ef56871661 --- /dev/null +++ b/crates/ruma-events/src/invite_permission_config.rs @@ -0,0 +1,67 @@ +//! Types for the [`m.invite_permission_config`] account data event. +//! +//! [`m.invite_permission_config`]: https://github.com/matrix-org/matrix-spec-proposals/pull/4380 + +use ruma_macros::EventContent; +use serde::{Deserialize, Serialize}; + +/// The content of an `m.invite_permission_config` event. +/// +/// A single property: `block_all`. +#[derive(Clone, Debug, Default, Deserialize, Serialize, EventContent)] +#[cfg_attr(not(ruma_unstable_exhaustive_types), non_exhaustive)] +#[ruma_event( + kind = GlobalAccountData, + type = "org.matrix.msc4380.invite_permission_config", + alias = "m.invite_permission_config", +)] +pub struct InvitePermissionConfigEventContent { + /// When set to true, indicates that the user does not wish to receive *any* room invites, and + /// they should be blocked. + #[serde(default)] + #[serde(deserialize_with = "ruma_common::serde::default_on_error")] + pub block_all: bool, +} + +impl InvitePermissionConfigEventContent { + /// Creates a new `InvitePermissionConfigEventContent` from the desired boolean state. + pub fn new(block_all: bool) -> Self { + Self { block_all } + } +} + +#[cfg(test)] +mod tests { + use assert_matches2::assert_matches; + use serde_json::{from_value as from_json_value, json, to_value as to_json_value}; + + use super::InvitePermissionConfigEventContent; + use crate::AnyGlobalAccountDataEvent; + + #[test] + fn serialization() { + let invite_permission_config = InvitePermissionConfigEventContent::new(true); + + let json = json!({ + "block_all": true + }); + + assert_eq!(to_json_value(invite_permission_config).unwrap(), json); + } + + #[test] + fn deserialization() { + let json = json!({ + "content": { + "block_all": true + }, + "type": "m.invite_permission_config" + }); + + assert_matches!( + from_json_value::(json), + Ok(AnyGlobalAccountDataEvent::InvitePermissionConfig(ev)) + ); + assert!(ev.content.block_all); + } +} diff --git a/crates/ruma-events/src/lib.rs b/crates/ruma-events/src/lib.rs index 854899c99a..d18f294879 100644 --- a/crates/ruma-events/src/lib.rs +++ b/crates/ruma-events/src/lib.rs @@ -165,6 +165,8 @@ pub mod image_pack; pub mod key; #[cfg(feature = "unstable-msc3488")] pub mod location; +#[cfg(feature = "unstable-msc4380")] +pub mod invite_permission_config; pub mod marked_unread; #[cfg(feature = "unstable-msc4278")] pub mod media_preview_config; diff --git a/crates/ruma/Cargo.toml b/crates/ruma/Cargo.toml index a96a0e8a8b..eff9952c0b 100644 --- a/crates/ruma/Cargo.toml +++ b/crates/ruma/Cargo.toml @@ -244,6 +244,11 @@ unstable-msc4310 = ["ruma-events?/unstable-msc4310"] unstable-msc4334 = ["ruma-events?/unstable-msc4334", "dep:language-tags"] unstable-msc4359 = ["ruma-events?/unstable-msc4359"] unstable-msc4361 = ["ruma-common/unstable-msc4361"] +unstable-msc4380 = [ + "ruma-client-api?/unstable-msc4380", + "ruma-common/unstable-msc4380", + "ruma-events?/unstable-msc4380", +] unstable-msc3230 = ["ruma-events?/unstable-msc3230"] # Private features, only used in test / benchmarking code @@ -310,6 +315,7 @@ __unstable-mscs = [ "unstable-msc4319", "unstable-msc4334", "unstable-msc4359", + "unstable-msc4380", "unstable-msc3230", ] __ci = ["full", "compat-upload-signatures", "__unstable-mscs"]