remember any room avatars set on matrix-side
This commit is contained in:
parent
bfe9efe62e
commit
92cd628a6c
5 changed files with 40 additions and 7 deletions
|
@ -61,11 +61,16 @@ async function channelToKState(channel, guild) {
|
||||||
const spaceID = db.prepare("SELECT space_id FROM guild_space WHERE guild_id = ?").pluck().get(guild.id)
|
const spaceID = db.prepare("SELECT space_id FROM guild_space WHERE guild_id = ?").pluck().get(guild.id)
|
||||||
assert.ok(typeof spaceID === "string")
|
assert.ok(typeof spaceID === "string")
|
||||||
|
|
||||||
const customName = db.prepare("SELECT nick FROM channel_room WHERE channel_id = ?").pluck().get(channel.id)
|
const row = db.prepare("SELECT nick, custom_avatar FROM channel_room WHERE channel_id = ?").get(channel.id)
|
||||||
|
assert(row)
|
||||||
|
const customName = row.nick
|
||||||
|
const customAvatar = row.custom_avatar
|
||||||
const [convertedName, convertedTopic] = convertNameAndTopic(channel, guild, customName)
|
const [convertedName, convertedTopic] = convertNameAndTopic(channel, guild, customName)
|
||||||
|
|
||||||
const avatarEventContent = {}
|
const avatarEventContent = {}
|
||||||
if (guild.icon) {
|
if (customAvatar) {
|
||||||
|
avatarEventContent.url = customAvatar
|
||||||
|
} else if (guild.icon) {
|
||||||
avatarEventContent.discord_path = file.guildIcon(guild)
|
avatarEventContent.discord_path = file.guildIcon(guild)
|
||||||
avatarEventContent.url = await file.uploadDiscordFileToMxc(avatarEventContent.discord_path) // TODO: somehow represent future values in kstate (callbacks?), while still allowing for diffing, so test cases don't need to touch the media API
|
avatarEventContent.url = await file.uploadDiscordFileToMxc(avatarEventContent.discord_path) // TODO: somehow represent future values in kstate (callbacks?), while still allowing for diffing, so test cases don't need to touch the media API
|
||||||
}
|
}
|
||||||
|
@ -183,6 +188,8 @@ async function _syncRoom(channelID, shouldActuallySync) {
|
||||||
return creation // Naturally, the newly created room is already up to date, so we can always skip syncing here.
|
return creation // Naturally, the newly created room is already up to date, so we can always skip syncing here.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const roomID = existing.room_id
|
||||||
|
|
||||||
if (!shouldActuallySync) {
|
if (!shouldActuallySync) {
|
||||||
return existing.room_id // only need to ensure room exists, and it does. return the room ID
|
return existing.room_id // only need to ensure room exists, and it does. return the room ID
|
||||||
}
|
}
|
||||||
|
@ -192,15 +199,16 @@ async function _syncRoom(channelID, shouldActuallySync) {
|
||||||
const {spaceID, channelKState} = await channelToKState(channel, guild)
|
const {spaceID, channelKState} = await channelToKState(channel, guild)
|
||||||
|
|
||||||
// sync channel state to room
|
// sync channel state to room
|
||||||
const roomKState = await roomToKState(existing.room_id)
|
const roomKState = await roomToKState(roomID)
|
||||||
const roomDiff = ks.diffKState(roomKState, channelKState)
|
const roomDiff = ks.diffKState(roomKState, channelKState)
|
||||||
const roomApply = applyKStateDiffToRoom(existing.room_id, roomDiff)
|
const roomApply = applyKStateDiffToRoom(roomID, roomDiff)
|
||||||
|
db.prepare("UPDATE channel_room SET name = ? WHERE room_id = ?").run(channel.name, roomID)
|
||||||
|
|
||||||
// sync room as space member
|
// sync room as space member
|
||||||
const spaceApply = _syncSpaceMember(channel, spaceID, existing.room_id)
|
const spaceApply = _syncSpaceMember(channel, spaceID, roomID)
|
||||||
await Promise.all([roomApply, spaceApply])
|
await Promise.all([roomApply, spaceApply])
|
||||||
|
|
||||||
return existing.room_id
|
return roomID
|
||||||
}
|
}
|
||||||
|
|
||||||
async function _unbridgeRoom(channelID) {
|
async function _unbridgeRoom(channelID) {
|
||||||
|
@ -279,5 +287,7 @@ module.exports.ensureRoom = ensureRoom
|
||||||
module.exports.syncRoom = syncRoom
|
module.exports.syncRoom = syncRoom
|
||||||
module.exports.createAllForGuild = createAllForGuild
|
module.exports.createAllForGuild = createAllForGuild
|
||||||
module.exports.channelToKState = channelToKState
|
module.exports.channelToKState = channelToKState
|
||||||
|
module.exports.roomToKState = roomToKState
|
||||||
|
module.exports.applyKStateDiffToRoom = applyKStateDiffToRoom
|
||||||
module.exports._convertNameAndTopic = convertNameAndTopic
|
module.exports._convertNameAndTopic = convertNameAndTopic
|
||||||
module.exports._unbridgeRoom = _unbridgeRoom
|
module.exports._unbridgeRoom = _unbridgeRoom
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
|
|
||||||
const util = require("util")
|
const util = require("util")
|
||||||
const Ty = require("../types")
|
const Ty = require("../types")
|
||||||
const {sync, as} = require("../passthrough")
|
const {db, sync, as} = require("../passthrough")
|
||||||
|
|
||||||
/** @type {import("./actions/send-event")} */
|
/** @type {import("./actions/send-event")} */
|
||||||
const sendEvent = sync.require("./actions/send-event")
|
const sendEvent = sync.require("./actions/send-event")
|
||||||
|
@ -69,3 +69,14 @@ async event => {
|
||||||
if (utils.eventSenderIsFromDiscord(event.sender)) return
|
if (utils.eventSenderIsFromDiscord(event.sender)) return
|
||||||
await addReaction.addReaction(event)
|
await addReaction.addReaction(event)
|
||||||
}))
|
}))
|
||||||
|
|
||||||
|
sync.addTemporaryListener(as, "type:m.room.avatar", guard("m.room.avatar",
|
||||||
|
/**
|
||||||
|
* @param {Ty.Event.StateOuter<Ty.Event.M_Room_Avatar>} event
|
||||||
|
*/
|
||||||
|
async event => {
|
||||||
|
if (event.state_key !== "") return
|
||||||
|
if (utils.eventSenderIsFromDiscord(event.sender)) return
|
||||||
|
const url = event.content.url || null
|
||||||
|
db.prepare("UPDATE channel_room SET custom_avatar = ? WHERE room_id = ?").run(url, event.room_id)
|
||||||
|
}))
|
||||||
|
|
|
@ -167,6 +167,8 @@ async function profileSetAvatarUrl(mxid, avatar_url) {
|
||||||
* @param {number} power
|
* @param {number} power
|
||||||
*/
|
*/
|
||||||
async function setUserPower(roomID, mxid, power) {
|
async function setUserPower(roomID, mxid, power) {
|
||||||
|
assert(roomID[0] === "!")
|
||||||
|
assert(mxid[0] === "@")
|
||||||
// Yes it's this hard https://github.com/matrix-org/matrix-appservice-bridge/blob/2334b0bae28a285a767fe7244dad59f5a5963037/src/components/intent.ts#L352
|
// Yes it's this hard https://github.com/matrix-org/matrix-appservice-bridge/blob/2334b0bae28a285a767fe7244dad59f5a5963037/src/components/intent.ts#L352
|
||||||
const powerLevels = await getStateEvent(roomID, "m.room.power_levels", "")
|
const powerLevels = await getStateEvent(roomID, "m.room.power_levels", "")
|
||||||
const users = powerLevels.users || {}
|
const users = powerLevels.users || {}
|
||||||
|
|
|
@ -42,6 +42,7 @@ function diffKState(actual, target) {
|
||||||
const diff = {}
|
const diff = {}
|
||||||
// go through each key that it should have
|
// go through each key that it should have
|
||||||
for (const key of Object.keys(target)) {
|
for (const key of Object.keys(target)) {
|
||||||
|
if (!key.includes("/")) throw new Error(`target kstate's key "${key}" does not contain a slash separator; if a blank state_key was intended, add a trailing slash to the kstate key.`)
|
||||||
if (key in actual) {
|
if (key in actual) {
|
||||||
// diff
|
// diff
|
||||||
try {
|
try {
|
||||||
|
|
9
types.d.ts
vendored
9
types.d.ts
vendored
|
@ -38,6 +38,10 @@ namespace Event {
|
||||||
event_id: string
|
event_id: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export type StateOuter<T> = Outer<T> & {
|
||||||
|
state_key: string
|
||||||
|
}
|
||||||
|
|
||||||
export type ReplacementContent<T> = T & {
|
export type ReplacementContent<T> = T & {
|
||||||
"m.new_content": T
|
"m.new_content": T
|
||||||
"m.relates_to": {
|
"m.relates_to": {
|
||||||
|
@ -74,6 +78,11 @@ namespace Event {
|
||||||
avatar_url?: string
|
avatar_url?: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export type M_Room_Avatar = {
|
||||||
|
discord_path?: string
|
||||||
|
url?: string
|
||||||
|
}
|
||||||
|
|
||||||
export type M_Reaction = {
|
export type M_Reaction = {
|
||||||
"m.relates_to": {
|
"m.relates_to": {
|
||||||
rel_type: "m.annotation"
|
rel_type: "m.annotation"
|
||||||
|
|
Loading…
Reference in a new issue