Fix missing creators support using via (#2431)
authorAjay Bura <32841439+ajbura@users.noreply.github.com>
Sat, 16 Aug 2025 11:30:02 +0000 (17:00 +0530)
committerGitHub <noreply@github.com>
Sat, 16 Aug 2025 11:30:02 +0000 (21:30 +1000)
* add additional_creators in IRoomCreateContent type

* use creators in getViaServers

* consider creators in guessing perfect parent

src/app/plugins/via-servers.ts
src/app/utils/room.ts
src/types/matrix/room.ts

index 75470999f3fb3e76a2b7548a3e189181abff8ca5..d825a1fd985e7220bcdad95188c5193717c208a2 100644 (file)
@@ -1,11 +1,19 @@
 import { Room } from 'matrix-js-sdk';
 import { IPowerLevels } from '../hooks/usePowerLevels';
-import { getMxIdServer } from '../utils/matrix';
-import { StateEvent } from '../../types/matrix/room';
+import { creatorsSupported, getMxIdServer } from '../utils/matrix';
+import { IRoomCreateContent, StateEvent } from '../../types/matrix/room';
 import { getStateEvent } from '../utils/room';
 
 export const getViaServers = (room: Room): string[] => {
   const getHighestPowerUserId = (): string | undefined => {
+    const creatorEvent = getStateEvent(room, StateEvent.RoomCreate);
+    if (
+      creatorEvent &&
+      creatorsSupported(creatorEvent.getContent<IRoomCreateContent>().room_version)
+    ) {
+      return creatorEvent.getSender();
+    }
+
     const powerLevels = getStateEvent(room, StateEvent.RoomPowerLevels)?.getContent<IPowerLevels>();
 
     if (!powerLevels) return undefined;
index a962c45ddc05c78520b6546f0e21b91942629516..b4bba2adfdc668256eb5282c3806ba0796c08324 100644 (file)
@@ -20,6 +20,7 @@ import {
 import { CryptoBackend } from 'matrix-js-sdk/lib/common-crypto/CryptoBackend';
 import { AccountDataEvent } from '../../types/matrix/accountData';
 import {
+  IRoomCreateContent,
   Membership,
   MessageEvent,
   NotificationType,
@@ -43,7 +44,7 @@ export const getStateEvents = (room: Room, eventType: StateEvent): MatrixEvent[]
 export const getAccountData = (
   mx: MatrixClient,
   eventType: AccountDataEvent
-): MatrixEvent | undefined => mx.getAccountData(eventType);
+): MatrixEvent | undefined => mx.getAccountData(eventType as any);
 
 export const getMDirects = (mDirectEvent: MatrixEvent): Set<string> => {
   const roomIds = new Set<string>();
@@ -480,6 +481,23 @@ export const bannedInRooms = (mx: MatrixClient, rooms: string[], otherUserId: st
     return banned;
   });
 
+export const getAllVersionsRoomCreator = (room: Room): Set<string> => {
+  const creators = new Set<string>();
+
+  const createEvent = getStateEvent(room, StateEvent.RoomCreate);
+  const createContent = createEvent?.getContent<IRoomCreateContent>();
+  const creator = createEvent?.getSender();
+  if (typeof creator === 'string') creators.add(creator);
+
+  if (createContent && Array.isArray(createContent.additional_creators)) {
+    createContent.additional_creators.forEach((c) => {
+      if (typeof c === 'string') creators.add(c);
+    });
+  }
+
+  return creators;
+};
+
 export const guessPerfectParent = (
   mx: MatrixClient,
   roomId: string,
@@ -490,15 +508,29 @@ export const guessPerfectParent = (
   }
 
   const getSpecialUsers = (rId: string): string[] => {
+    const specialUsers: Set<string> = new Set();
+
     const r = mx.getRoom(rId);
-    const powerLevels =
-      r && getStateEvent(r, StateEvent.RoomPowerLevels)?.getContent<IPowerLevelsContent>();
+    if (!r) return [];
 
-    const { users_default: usersDefault, users } = powerLevels ?? {};
-    if (typeof users !== 'object') return [];
+    getAllVersionsRoomCreator(r).forEach((c) => specialUsers.add(c));
+
+    const powerLevels = getStateEvent(
+      r,
+      StateEvent.RoomPowerLevels
+    )?.getContent<IPowerLevelsContent>();
 
+    const { users_default: usersDefault, users } = powerLevels ?? {};
     const defaultPower = typeof usersDefault === 'number' ? usersDefault : 0;
-    return Object.keys(users).filter((userId) => users[userId] > defaultPower);
+
+    if (typeof users === 'object')
+      Object.keys(users).forEach((userId) => {
+        if (users[userId] > defaultPower) {
+          specialUsers.add(userId);
+        }
+      });
+
+    return Array.from(specialUsers);
   };
 
   let perfectParent: string | undefined;
index f0927b3cf4b5ec8741a381398cca65f0a3221040..b866fd77fcd93130ba918273b16c900555e1192c 100644 (file)
@@ -70,6 +70,7 @@ export type IRoomCreateContent = {
   ['m.federate']?: boolean;
   room_version: string;
   type?: string;
+  additional_creators?: string[];
   predecessor?: {
     event_id?: string;
     room_id: string;