Add membership handling to the room events.

This commit is contained in:
poljar (Damir Jelić) 2018-02-23 15:17:12 +01:00
parent f98efe1ab9
commit e1723c528c
4 changed files with 142 additions and 56 deletions

View file

@ -443,13 +443,3 @@ class MatrixInviteMessage(MatrixMessage):
self.room_id, self.user_id) self.room_id, self.user_id)
return self._decode(server, object_hook) return self._decode(server, object_hook)
class MatrixUser:
def __init__(self, name, display_name):
self.name = name # type: str
self.display_name = display_name # type: str
self.power_level = 0 # type: int
self.nick_color = "" # type: str
self.prefix = "" # type: str

View file

@ -28,12 +28,14 @@ from matrix.colors import Formatted
from matrix.globals import W, OPTIONS from matrix.globals import W, OPTIONS
from matrix.api import (MessageType, MatrixUser) from matrix.api import MessageType
from matrix.rooms import MatrixUser
from matrix.rooms import MatrixRoom from matrix.rooms import MatrixRoom
from matrix.utils import (server_buffer_prnt, tags_from_line_data, prnt_debug, from matrix.utils import (server_buffer_prnt, tags_from_line_data, prnt_debug,
color_for_tags) color_for_tags, add_user_to_nicklist,
get_prefix_for_level)
from matrix.plugin_options import RedactType, DebugType from matrix.plugin_options import RedactType, DebugType
@ -42,22 +44,6 @@ def strip_matrix_server(string):
return string.rsplit(":", 1)[0] return string.rsplit(":", 1)[0]
def add_user_to_nicklist(buf, user):
group_name = "999|..."
if user.power_level >= 100:
group_name = "000|o"
elif user.power_level >= 50:
group_name = "001|h"
elif user.power_level > 0:
group_name = "002|v"
group = W.nicklist_search_group(buf, "", group_name)
# TODO make it configurable so we can use a display name or user_id here
W.nicklist_add_nick(buf, group, user.display_name, user.nick_color,
user.prefix, get_prefix_color(user.prefix), 1)
def matrix_create_room_buffer(server, room_id): def matrix_create_room_buffer(server, room_id):
# type: (MatrixServer, str) -> None # type: (MatrixServer, str) -> None
buf = W.buffer_new(room_id, "room_input_cb", server.name, "room_close_cb", buf = W.buffer_new(room_id, "room_input_cb", server.name, "room_close_cb",
@ -133,7 +119,7 @@ def matrix_handle_room_members(server, room_id, event):
nick_pointer = W.nicklist_search_nick(buf, "", user.display_name) nick_pointer = W.nicklist_search_nick(buf, "", user.display_name)
if not nick_pointer: if not nick_pointer:
add_user_to_nicklist(buf, user) add_user_to_nicklist(buf, full_name, user)
else: else:
# TODO we can get duplicate display names # TODO we can get duplicate display names
pass pass
@ -364,29 +350,6 @@ def matrix_handle_room_redaction(server, room_id, event):
return W.WEECHAT_RC_OK return W.WEECHAT_RC_OK
def get_prefix_for_level(level):
# type: (int) -> str
if level >= 100:
return "&"
elif level >= 50:
return "@"
elif level > 0:
return "+"
return ""
# TODO make this configurable
def get_prefix_color(prefix):
# type: (str) -> str
if prefix == "&":
return "lightgreen"
elif prefix == "@":
return "lightgreen"
elif prefix == "+":
return "yellow"
return ""
def matrix_handle_room_power_levels(server, room_id, event): def matrix_handle_room_power_levels(server, room_id, event):
if not event['content']['users']: if not event['content']['users']:
return return

View file

@ -23,7 +23,7 @@ from matrix.colors import Formatted
from matrix.utils import (strip_matrix_server, color_for_tags, date_from_age, from matrix.utils import (strip_matrix_server, color_for_tags, date_from_age,
sender_to_nick_and_color, tags_for_message, sender_to_nick_and_color, tags_for_message,
add_event_tags, sanitize_id, sanitize_age, add_event_tags, sanitize_id, sanitize_age,
sanitize_text) sanitize_text, shorten_sender, add_user_to_nicklist)
class MatrixRoom: class MatrixRoom:
@ -43,6 +43,18 @@ class MatrixRoom:
# yapf: enable # yapf: enable
class MatrixUser:
def __init__(self, name, display_name):
# yapf: disable
self.name = name # type: str
self.display_name = display_name # type: str
self.power_level = 0 # type: int
self.nick_color = "" # type: str
self.prefix = "" # type: str
# yapf: enable
def matrix_create_room_buffer(server, room_id): def matrix_create_room_buffer(server, room_id):
# type: (MatrixServer, str) -> None # type: (MatrixServer, str) -> None
buf = W.buffer_new(room_id, "room_input_cb", server.name, "room_close_cb", buf = W.buffer_new(room_id, "room_input_cb", server.name, "room_close_cb",
@ -95,10 +107,28 @@ class RoomInfo():
return RoomMessageEvent.from_dict(event) return RoomMessageEvent.from_dict(event)
@staticmethod
def _membership_from_dict(event_dict):
if (event_dict["membership"] not in [
"invite", "join", "knock", "leave", "ban"
]):
raise ValueError
if event_dict["membership"] == "join":
return RoomMemberJoin.from_dict(event_dict)
elif event_dict["membership"] == "leave":
return RoomMemberLeave.from_dict(event_dict)
return None
@staticmethod @staticmethod
def _event_from_dict(event): def _event_from_dict(event):
if event['type'] == 'm.room.message': if event["type"] == "m.room.message":
return RoomInfo._message_from_event(event) return RoomInfo._message_from_event(event)
elif event["type"] == "m.room.member":
return RoomInfo._membership_from_dict(event)
else:
return None
@classmethod @classmethod
def from_dict(cls, room_id, parsed_dict): def from_dict(cls, room_id, parsed_dict):
@ -147,7 +177,7 @@ class RoomRedactedMessageEvent(RoomEvent):
return cls(event_id, sender, age, censor, reason) return cls(event_id, sender, age, censor, reason)
def execute(self, room, buff, tags): def execute(self, server, room, buff, tags):
nick, color_name = sender_to_nick_and_color(room, self.sender) nick, color_name = sender_to_nick_and_color(room, self.sender)
color = color_for_tags(color_name) color = color_for_tags(color_name)
date = date_from_age(self.age) date = date_from_age(self.age)
@ -203,7 +233,7 @@ class RoomMessageEvent(RoomEvent):
return cls(event_id, sender, age, msg, formatted_msg) return cls(event_id, sender, age, msg, formatted_msg)
def execute(self, room, buff, tags): def execute(self, server, room, buff, tags):
msg = (self.formatted_message.to_weechat() msg = (self.formatted_message.to_weechat()
if self.formatted_message else self.message) if self.formatted_message else self.message)
@ -218,3 +248,67 @@ class RoomMessageEvent(RoomEvent):
date = date_from_age(self.age) date = date_from_age(self.age)
W.prnt_date_tags(buff, date, tags_string, data) W.prnt_date_tags(buff, date, tags_string, data)
class RoomMemberJoin(RoomEvent):
def __init__(self, event_id, sender, age, display_name):
self.display_name = display_name
RoomEvent.__init__(self, event_id, sender, age)
@classmethod
def from_dict(cls, event_dict):
event_id = sanitize_id(event_dict["event_id"])
sender = sanitize_id(event_dict["sender"])
age = sanitize_age(event_dict["unsigned"]["age"])
display_name = sanitize_text(event_dict["content"]["displayname"])
return cls(event_id, sender, age, display_name)
def execute(self, server, room, buff, tags):
short_name = shorten_sender(self.sender)
if self.sender in room.users:
user = room.users[self.sender]
if self.display_name:
user.display_name = self.display_name
else:
user = MatrixUser(short_name, self.display_name)
if not user.nick_color:
if self.sender == server.user_id:
user.nick_color = "weechat.color.chat_nick_self"
W.buffer_set(buff, "highlight_words", ",".join(
[self.sender, user.name, user.display_name]))
else:
user.nick_color = W.info_get("nick_color_name", user.name)
room.users[self.sender] = user
nick_pointer = W.nicklist_search_nick(buff, "", self.sender)
if not nick_pointer:
add_user_to_nicklist(buff, self.sender, user)
class RoomMemberLeave(RoomEvent):
def __init__(self, event_id, sender, age):
RoomEvent.__init__(self, event_id, sender, age)
@classmethod
def from_dict(cls, event_dict):
event_id = sanitize_id(event_dict["event_id"])
sender = sanitize_id(event_dict["sender"])
age = sanitize_age(event_dict["unsigned"]["age"])
return cls(event_id, sender, age)
def execute(self, server, room, buff, tags):
if self.sender in room.users:
nick_pointer = W.nicklist_search_nick(buff, "", self.sender)
if nick_pointer:
W.nicklist_remove_nick(buff, nick_pointer)
del room.users[self.sender]

View file

@ -236,3 +236,42 @@ def sanitize_text(string):
# yapf: enable # yapf: enable
return string.translate(remap) return string.translate(remap)
def add_user_to_nicklist(buf, user_id, user):
group_name = "999|..."
if user.power_level >= 100:
group_name = "000|o"
elif user.power_level >= 50:
group_name = "001|h"
elif user.power_level > 0:
group_name = "002|v"
group = W.nicklist_search_group(buf, "", group_name)
# TODO make it configurable so we can use a display name or user_id here
W.nicklist_add_nick(buf, group, user_id, user.nick_color, user.prefix,
get_prefix_color(user.prefix), 1)
def get_prefix_for_level(level):
# type: (int) -> str
if level >= 100:
return "&"
elif level >= 50:
return "@"
elif level > 0:
return "+"
return ""
# TODO make this configurable
def get_prefix_color(prefix):
# type: (str) -> str
if prefix == "&":
return "lightgreen"
elif prefix == "@":
return "lightgreen"
elif prefix == "+":
return "yellow"
return ""