Merge pull request #5615 from matrix-org/jryans/pill-room-via

Fix permalink via parsing for rooms
This commit is contained in:
J. Ryan Stinnett 2021-02-03 16:30:48 +00:00 committed by GitHub
commit 7489011ab7
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 54 additions and 19 deletions

View file

@ -75,15 +75,28 @@ export default class ElementPermalinkConstructor extends PermalinkConstructor {
throw new Error("Does not appear to be a permalink");
}
const parts = fullUrl.substring(`${this._elementUrl}/#/`.length).split("/");
return ElementPermalinkConstructor.parseLinkParts(parts);
const parts = fullUrl.substring(`${this._elementUrl}/#/`.length);
return ElementPermalinkConstructor.parseAppRoute(parts);
}
static parseLinkParts(parts: string[]): PermalinkParts {
/**
* Parses an app route (`(user|room|group)/identifer`) to a Matrix entity
* (room, user, group).
* @param {string} route The app route
* @returns {PermalinkParts}
*/
static parseAppRoute(route: string): PermalinkParts {
const parts = route.split("/");
if (parts.length < 2) { // we're expecting an entity and an ID of some kind at least
throw new Error("URL is missing parts");
}
// Split optional query out of last part
const [lastPartMaybeWithQuery] = parts.splice(-1, 1);
const [lastPart, query = ""] = lastPartMaybeWithQuery.split("?");
parts.push(lastPart);
const entityType = parts[0];
const entity = parts[1];
if (entityType === 'user') {
@ -93,20 +106,9 @@ export default class ElementPermalinkConstructor extends PermalinkConstructor {
// Probably a group, no further parsing needed.
return PermalinkParts.forGroup(entity);
} else if (entityType === 'room') {
if (parts.length === 2) {
return PermalinkParts.forRoom(entity, []);
}
// rejoin the rest because v3 events can have slashes (annoyingly)
const eventIdAndQuery = parts.length > 2 ? parts.slice(2).join('/') : "";
const secondaryParts = eventIdAndQuery.split("?");
const eventId = secondaryParts[0];
const query = secondaryParts.length > 1 ? secondaryParts[1] : "";
// TODO: Verify Element works with via args
const via = query.split("via=").filter(p => !!p);
// Rejoin the rest because v3 events can have slashes (annoyingly)
const eventId = parts.length > 2 ? parts.slice(2).join('/') : "";
const via = query.split(/&?via=/).filter(p => !!p);
return PermalinkParts.forEvent(entity, eventId, via);
} else {
throw new Error("Unknown entity type in permalink");

View file

@ -414,8 +414,8 @@ export function parsePermalink(fullUrl: string): PermalinkParts {
*/
export function parseAppLocalLink(localLink: string): PermalinkParts {
try {
const segments = localLink.replace("#/", "").split("/");
return ElementPermalinkConstructor.parseLinkParts(segments);
const segments = localLink.replace("#/", "");
return ElementPermalinkConstructor.parseAppRoute(segments);
} catch (e) {
// Ignore failures
}

View file

@ -242,6 +242,38 @@ describe("<TextualBody />", () => {
'rel="noreferrer noopener">event link</a> with text</span>',
);
});
it("pills appear for room links with vias", () => {
const ev = mkEvent({
type: "m.room.message",
room: "room_id",
user: "sender",
content: {
body:
"A [room link](https://matrix.to/#/!ZxbRYPQXDXKGmDnJNg:example.com" +
"?via=example.com&via=bob.com) with vias",
msgtype: "m.text",
format: "org.matrix.custom.html",
formatted_body:
"A <a href=\"https://matrix.to/#/!ZxbRYPQXDXKGmDnJNg:example.com" +
"?via=example.com&amp;via=bob.com\">room link</a> with vias",
},
event: true,
});
const wrapper = mount(<TextualBody mxEvent={ev} />);
expect(wrapper.text()).toBe("A !ZxbRYPQXDXKGmDnJNg:example.com with vias");
const content = wrapper.find(".mx_EventTile_body");
expect(content.html()).toBe(
'<span class="mx_EventTile_body markdown-body" dir="auto">' +
'A <span><a class="mx_Pill mx_RoomPill" href="#/room/!ZxbRYPQXDXKGmDnJNg:example.com' +
'?via=example.com&amp;via=bob.com" ' +
'title="!ZxbRYPQXDXKGmDnJNg:example.com"><img class="mx_BaseAvatar mx_BaseAvatar_image" ' +
'src="mxc://avatar.url/room.png" ' +
'style="width: 16px; height: 16px;" alt="" aria-hidden="true">' +
'!ZxbRYPQXDXKGmDnJNg:example.com</a></span> with vias</span>',
);
});
});
it("renders url previews correctly", () => {

View file

@ -243,6 +243,7 @@ export function mkStubRoom(roomId = null) {
on: jest.fn(),
removeListener: jest.fn(),
getDMInviter: jest.fn(),
getAvatarUrl: () => 'mxc://avatar.url/room.png',
};
}