Skip to content

Conversation

DonPrus
Copy link

@DonPrus DonPrus commented Sep 15, 2025

This PR adds an experimental client-side implementation for MSC4352 to help it move through the spec process. It demonstrates:

  1. Discovery: Reads org.matrix.msc4352.permalink_base_url (or stable m.permalink_base_url) from /.well-known/matrix/client for the user's homeserver domain (HTTPS-only). Also supports IAMB_MSC4352_PERMALINK_BASE for local testing.

  2. Generation: New command :permalink generates HTTPS permalinks for outside-of-Matrix contexts using the matrix.to navigation grammar but with the discovered custom base URL (fallback https://matrix.to). Supports both room permalinks and event permalinks (:permalink event $eventId).

  3. In-app safety: No in-app links/mentions are rewritten to HTTPS; iamb's in-app navigation remains intact.

  4. Send-time conversion: When a user pastes a resolver-style HTTPS permalink in a message, iamb keeps the visible text but emits formatted_body with an equivalent matrix: URI (matrix:r/..., matrix:roomid/.../e/..., preserving via=), ensuring cross-client interoperability.

Feature flag

Set IAMB_MSC4352=1 to enable the feature. You can optionally set IAMB_MSC4352_PERMALINK_BASE for testing without editing well-known.

Testing

  • Send conversion: Paste https://links.example.org/#/%23room%3Aexample.org/%24event?via=example.org and send - the message should have an anchor with href="matrix:r/room:example.org/e/$event?via=example.org" in formatted_body, while body preserves the original text.
  • Permalink generation: Run :permalink in a room to get an HTTPS permalink based on discovered or env-provided base.
  • Fallback: Without well-known and without the env var, :permalink falls back to https://matrix.to.

Implementation notes

  • Prefers canonical room alias over room ID when generating permalinks
  • Validates HTTPS-only for discovered base URLs
  • Includes comprehensive unit tests
  • Documented in MSC4352.md

This is intentionally a small, low-risk change to qualify MSC4352 with a client implementation.

  - Add discovery of custom permalink base from .well-known/matrix/client
  - Implement :permalink command for generating room/event permalinks
  - Add send-time conversion of HTTPS permalinks to matrix: URIs
  - Support both stable (m.permalink_base_url) and unstable keys
  - Feature-gated behind IAMB_MSC4352=1 environment variable
  - Include comprehensive tests and documentation

Signed-off-by: Igor Somov <[email protected]>
@VAWVAW
Copy link
Contributor

VAWVAW commented Sep 16, 2025

Is there a reason this PR needs to reimplement existing types like MatrixID, MatrixUri and MatrixToUri?

I think it makes more sense to implement most of this in matrix-rust-sdk and maybe just do a string replace in the output of MatrixToUri::to_string.

Also I couldn't get this to build (unresolved import url::percent_encoding and modalkit::clipboard) but this looks like it breaks markdown formatting in messages with matrix.to links.

Signed-off-by: Igor Somov <[email protected]>
@DonPrus
Copy link
Author

DonPrus commented Sep 16, 2025

Is there a reason this PR needs to reimplement existing types like MatrixID, MatrixUri and MatrixToUri?

I think it makes more sense to implement most of this in matrix-rust-sdk and maybe just do a string replace in the output of MatrixToUri::to_string.

Also I couldn't get this to build (unresolved import url::percent_encoding and modalkit::clipboard) but this looks like it breaks markdown formatting in messages with matrix.to links.

Thanks, I fix this:

  • Use existing ruma types (MatrixUri, MatrixToUri) instead of reimplementing them
  • Fix the import issues with percent_encoding
  • Preserve markdown formatting by applying MSC4352 conversion after markdown processing
  • Simplify the code by leveraging existing matrix-sdk functionality

@VAWVAW
Copy link
Contributor

VAWVAW commented Sep 16, 2025

Do you have some local changes you have not pushed or are you using AI to write this code? When I check out your changes locally and run cargo c, I get multiple error about non-existing functions and attributes.

Signed-off-by: Igor Somov <[email protected]>
@DonPrus
Copy link
Author

DonPrus commented Sep 16, 2025

Apologies for the confusion. The issue is that main doesn’t build for me on macOS 26. To get a local build, I’ve been temporarily tweaking build.rs and a few other files, and adding some helper/stub files to work around platform-specific errors. I didn’t commit those local changes, which is why a clean checkout hits the “non-existing functions/attributes” errors you’re seeing. I’ll sort out my macOS setup closer to the weekend, push the minimal required changes (or guard the macOS-specific bits), and re-test with a clean cargo c run.

Signed-off-by: Igor Somov <[email protected]>
@VAWVAW
Copy link
Contributor

VAWVAW commented Sep 16, 2025

For me 28acbaa complies while 1d266fd complains about modalkit::clipboard not existing.

@DonPrus DonPrus force-pushed the msc4352-permalink-resolver branch from 9d94a6d to 88de844 Compare September 19, 2025 12:15
@DonPrus
Copy link
Author

DonPrus commented Sep 19, 2025

Now I fix all problems, and add some more tests for this feature :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants