Move room classes to rooms.py.
This commit is contained in:
parent
80545dd776
commit
f98efe1ab9
3 changed files with 233 additions and 223 deletions
226
matrix/events.py
226
matrix/events.py
|
@ -18,83 +18,13 @@ from __future__ import unicode_literals
|
|||
from builtins import str
|
||||
|
||||
import time
|
||||
import math
|
||||
from functools import partial
|
||||
|
||||
from matrix.globals import W, OPTIONS
|
||||
from matrix.utils import (
|
||||
color_for_tags,
|
||||
date_from_age,
|
||||
sender_to_nick_and_color,
|
||||
tags_for_message,
|
||||
add_event_tags,
|
||||
)
|
||||
from matrix.colors import Formatted
|
||||
from matrix.rooms import matrix_create_room_buffer
|
||||
|
||||
|
||||
def sanitize_token(string):
|
||||
# type: (str) -> str
|
||||
string = sanitize_string(string)
|
||||
|
||||
if len(string) > 512:
|
||||
raise ValueError
|
||||
|
||||
return string
|
||||
|
||||
|
||||
def sanitize_string(string):
|
||||
# type: (str) -> str
|
||||
if not isinstance(string, str):
|
||||
raise TypeError
|
||||
|
||||
remap = {
|
||||
ord('\b'): None,
|
||||
ord('\f'): None,
|
||||
ord('\n'): None,
|
||||
ord('\r'): None,
|
||||
ord('\t'): None,
|
||||
ord('\0'): None
|
||||
}
|
||||
|
||||
return string.translate(remap)
|
||||
|
||||
|
||||
def sanitize_id(string):
|
||||
# type: (str) -> str
|
||||
string = sanitize_string(string)
|
||||
|
||||
if len(string) > 128:
|
||||
raise ValueError
|
||||
|
||||
return string
|
||||
|
||||
|
||||
def sanitize_age(age):
|
||||
# type: (int) -> int
|
||||
if not isinstance(age, int):
|
||||
raise TypeError
|
||||
|
||||
if math.isnan(age):
|
||||
raise ValueError
|
||||
|
||||
if math.isinf(age):
|
||||
raise ValueError
|
||||
|
||||
if age < 0:
|
||||
raise ValueError
|
||||
|
||||
return age
|
||||
|
||||
|
||||
def sanitize_text(string):
|
||||
# type: (str) -> str
|
||||
if not isinstance(string, str):
|
||||
raise TypeError
|
||||
|
||||
remap = {ord('\b'): None, ord('\f'): None, ord('\r'): None, ord('\0'): None}
|
||||
|
||||
return string.translate(remap)
|
||||
from matrix.utils import (color_for_tags, tags_for_message, sanitize_id,
|
||||
sanitize_token, sanitize_text)
|
||||
from matrix.rooms import (matrix_create_room_buffer, RoomInfo, RoomMessageEvent,
|
||||
RoomRedactedMessageEvent)
|
||||
|
||||
|
||||
class MatrixEvent():
|
||||
|
@ -411,151 +341,3 @@ class MatrixSyncEvent(MatrixEvent):
|
|||
|
||||
server.next_batch = self.next_batch
|
||||
server.sync()
|
||||
|
||||
|
||||
class RoomInfo():
|
||||
|
||||
def __init__(self, room_id, prev_batch, events):
|
||||
# type: (str, str, List[Any]) -> None
|
||||
self.room_id = room_id
|
||||
self.prev_batch = prev_batch
|
||||
self.events = events
|
||||
|
||||
@staticmethod
|
||||
def _message_from_event(event):
|
||||
# The transaction id will only be present for events that are send out
|
||||
# from this client, since we print out our own messages as soon as we
|
||||
# get a receive confirmation from the server we don't care about our
|
||||
# own messages in a sync event. More info under:
|
||||
# https://github.com/matrix-org/matrix-doc/blob/master/api/client-server/definitions/event.yaml#L53
|
||||
if "transaction_id" in event["unsigned"]:
|
||||
return None
|
||||
|
||||
if "redacted_by" in event["unsigned"]:
|
||||
return RoomRedactedMessageEvent.from_dict(event)
|
||||
|
||||
return RoomMessageEvent.from_dict(event)
|
||||
|
||||
@staticmethod
|
||||
def _event_from_dict(event):
|
||||
if event['type'] == 'm.room.message':
|
||||
return RoomInfo._message_from_event(event)
|
||||
|
||||
@classmethod
|
||||
def from_dict(cls, room_id, parsed_dict):
|
||||
prev_batch = sanitize_id(parsed_dict['timeline']['prev_batch'])
|
||||
|
||||
events = []
|
||||
|
||||
state_dict = parsed_dict['state']['events']
|
||||
timeline_dict = parsed_dict['timeline']['events']
|
||||
|
||||
for event in timeline_dict:
|
||||
events.append(RoomInfo._event_from_dict(event))
|
||||
|
||||
filtered_events = list(filter(None, events))
|
||||
|
||||
return cls(room_id, prev_batch, filtered_events)
|
||||
|
||||
|
||||
class RoomEvent():
|
||||
|
||||
def __init__(self, event_id, sender, age):
|
||||
self.event_id = event_id
|
||||
self.sender = sender
|
||||
self.age = age
|
||||
|
||||
|
||||
class RoomRedactedMessageEvent(RoomEvent):
|
||||
|
||||
def __init__(self, event_id, sender, age, censor, reason=None):
|
||||
self.censor = censor
|
||||
self.reason = reason
|
||||
RoomEvent.__init__(self, event_id, sender, age)
|
||||
|
||||
@classmethod
|
||||
def from_dict(cls, event):
|
||||
event_id = sanitize_id(event["event_id"])
|
||||
sender = sanitize_id(event["sender"])
|
||||
age = sanitize_age(event["unsigned"]["age"])
|
||||
|
||||
censor = sanitize_id(event['unsigned']['redacted_because']['sender'])
|
||||
reason = None
|
||||
|
||||
if 'reason' in event['unsigned']['redacted_because']['content']:
|
||||
reason = sanitize_text(
|
||||
event['unsigned']['redacted_because']['content']['reason'])
|
||||
|
||||
return cls(event_id, sender, age, censor, reason)
|
||||
|
||||
def execute(self, room, buff, tags):
|
||||
nick, color_name = sender_to_nick_and_color(room, self.sender)
|
||||
color = color_for_tags(color_name)
|
||||
date = date_from_age(self.age)
|
||||
|
||||
event_tags = add_event_tags(self.event_id, nick, color, tags)
|
||||
|
||||
reason = (", reason: \"{reason}\"".format(reason=self.reason)
|
||||
if self.reason else "")
|
||||
|
||||
censor, _ = sender_to_nick_and_color(room, self.censor)
|
||||
|
||||
msg = ("{del_color}<{log_color}Message redacted by: "
|
||||
"{censor}{log_color}{reason}{del_color}>{ncolor}").format(
|
||||
del_color=W.color("chat_delimiters"),
|
||||
ncolor=W.color("reset"),
|
||||
log_color=W.color("logger.color.backlog_line"),
|
||||
censor=censor,
|
||||
reason=reason)
|
||||
|
||||
event_tags.append("matrix_redacted")
|
||||
|
||||
tags_string = ",".join(event_tags)
|
||||
|
||||
data = "{author}\t{msg}".format(author=nick, msg=msg)
|
||||
|
||||
W.prnt_date_tags(buff, date, tags_string, data)
|
||||
|
||||
|
||||
class RoomMessageEvent(RoomEvent):
|
||||
|
||||
def __init__(self, event_id, sender, age, message, formatted_message=None):
|
||||
self.message = message
|
||||
self.formatted_message = formatted_message
|
||||
RoomEvent.__init__(self, event_id, sender, age)
|
||||
|
||||
@classmethod
|
||||
def from_dict(cls, event):
|
||||
event_id = sanitize_id(event["event_id"])
|
||||
sender = sanitize_id(event["sender"])
|
||||
age = sanitize_age(event["unsigned"]["age"])
|
||||
|
||||
msg = ""
|
||||
formatted_msg = None
|
||||
|
||||
if event['content']['msgtype'] == 'm.text':
|
||||
msg = sanitize_text(event['content']['body'])
|
||||
|
||||
if ('format' in event['content'] and
|
||||
'formatted_body' in event['content']):
|
||||
if event['content']['format'] == "org.matrix.custom.html":
|
||||
formatted_msg = Formatted.from_html(
|
||||
sanitize_text(event['content']['formatted_body']))
|
||||
|
||||
return cls(event_id, sender, age, msg, formatted_msg)
|
||||
|
||||
def execute(self, room, buff, tags):
|
||||
msg = (self.formatted_message.to_weechat()
|
||||
if self.formatted_message else self.message)
|
||||
|
||||
nick, color_name = sender_to_nick_and_color(room, self.sender)
|
||||
color = color_for_tags(color_name)
|
||||
|
||||
event_tags = add_event_tags(self.event_id, nick, color, tags)
|
||||
|
||||
tags_string = ",".join(event_tags)
|
||||
|
||||
data = "{author}\t{msg}".format(author=nick, msg=msg)
|
||||
|
||||
date = date_from_age(self.age)
|
||||
W.prnt_date_tags(buff, date, tags_string, data)
|
||||
|
|
156
matrix/rooms.py
156
matrix/rooms.py
|
@ -15,9 +15,15 @@
|
|||
# CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
from __future__ import unicode_literals
|
||||
from builtins import str
|
||||
|
||||
from matrix.globals import W
|
||||
from matrix.utils import strip_matrix_server
|
||||
|
||||
from matrix.colors import Formatted
|
||||
from matrix.utils import (strip_matrix_server, color_for_tags, date_from_age,
|
||||
sender_to_nick_and_color, tags_for_message,
|
||||
add_event_tags, sanitize_id, sanitize_age,
|
||||
sanitize_text)
|
||||
|
||||
|
||||
class MatrixRoom:
|
||||
|
@ -64,3 +70,151 @@ def matrix_create_room_buffer(server, room_id):
|
|||
|
||||
server.buffers[room_id] = buf
|
||||
server.rooms[room_id] = MatrixRoom(room_id)
|
||||
|
||||
|
||||
class RoomInfo():
|
||||
|
||||
def __init__(self, room_id, prev_batch, events):
|
||||
# type: (str, str, List[Any]) -> None
|
||||
self.room_id = room_id
|
||||
self.prev_batch = prev_batch
|
||||
self.events = events
|
||||
|
||||
@staticmethod
|
||||
def _message_from_event(event):
|
||||
# The transaction id will only be present for events that are send out
|
||||
# from this client, since we print out our own messages as soon as we
|
||||
# get a receive confirmation from the server we don't care about our
|
||||
# own messages in a sync event. More info under:
|
||||
# https://github.com/matrix-org/matrix-doc/blob/master/api/client-server/definitions/event.yaml#L53
|
||||
if "transaction_id" in event["unsigned"]:
|
||||
return None
|
||||
|
||||
if "redacted_by" in event["unsigned"]:
|
||||
return RoomRedactedMessageEvent.from_dict(event)
|
||||
|
||||
return RoomMessageEvent.from_dict(event)
|
||||
|
||||
@staticmethod
|
||||
def _event_from_dict(event):
|
||||
if event['type'] == 'm.room.message':
|
||||
return RoomInfo._message_from_event(event)
|
||||
|
||||
@classmethod
|
||||
def from_dict(cls, room_id, parsed_dict):
|
||||
prev_batch = sanitize_id(parsed_dict['timeline']['prev_batch'])
|
||||
|
||||
events = []
|
||||
|
||||
state_dict = parsed_dict['state']['events']
|
||||
timeline_dict = parsed_dict['timeline']['events']
|
||||
|
||||
for event in timeline_dict:
|
||||
events.append(RoomInfo._event_from_dict(event))
|
||||
|
||||
filtered_events = list(filter(None, events))
|
||||
|
||||
return cls(room_id, prev_batch, filtered_events)
|
||||
|
||||
|
||||
class RoomEvent():
|
||||
|
||||
def __init__(self, event_id, sender, age):
|
||||
self.event_id = event_id
|
||||
self.sender = sender
|
||||
self.age = age
|
||||
|
||||
|
||||
class RoomRedactedMessageEvent(RoomEvent):
|
||||
|
||||
def __init__(self, event_id, sender, age, censor, reason=None):
|
||||
self.censor = censor
|
||||
self.reason = reason
|
||||
RoomEvent.__init__(self, event_id, sender, age)
|
||||
|
||||
@classmethod
|
||||
def from_dict(cls, event):
|
||||
event_id = sanitize_id(event["event_id"])
|
||||
sender = sanitize_id(event["sender"])
|
||||
age = sanitize_age(event["unsigned"]["age"])
|
||||
|
||||
censor = sanitize_id(event['unsigned']['redacted_because']['sender'])
|
||||
reason = None
|
||||
|
||||
if 'reason' in event['unsigned']['redacted_because']['content']:
|
||||
reason = sanitize_text(
|
||||
event['unsigned']['redacted_because']['content']['reason'])
|
||||
|
||||
return cls(event_id, sender, age, censor, reason)
|
||||
|
||||
def execute(self, room, buff, tags):
|
||||
nick, color_name = sender_to_nick_and_color(room, self.sender)
|
||||
color = color_for_tags(color_name)
|
||||
date = date_from_age(self.age)
|
||||
|
||||
event_tags = add_event_tags(self.event_id, nick, color, tags)
|
||||
|
||||
reason = (", reason: \"{reason}\"".format(reason=self.reason)
|
||||
if self.reason else "")
|
||||
|
||||
censor, _ = sender_to_nick_and_color(room, self.censor)
|
||||
|
||||
msg = ("{del_color}<{log_color}Message redacted by: "
|
||||
"{censor}{log_color}{reason}{del_color}>{ncolor}").format(
|
||||
del_color=W.color("chat_delimiters"),
|
||||
ncolor=W.color("reset"),
|
||||
log_color=W.color("logger.color.backlog_line"),
|
||||
censor=censor,
|
||||
reason=reason)
|
||||
|
||||
event_tags.append("matrix_redacted")
|
||||
|
||||
tags_string = ",".join(event_tags)
|
||||
|
||||
data = "{author}\t{msg}".format(author=nick, msg=msg)
|
||||
|
||||
W.prnt_date_tags(buff, date, tags_string, data)
|
||||
|
||||
|
||||
class RoomMessageEvent(RoomEvent):
|
||||
|
||||
def __init__(self, event_id, sender, age, message, formatted_message=None):
|
||||
self.message = message
|
||||
self.formatted_message = formatted_message
|
||||
RoomEvent.__init__(self, event_id, sender, age)
|
||||
|
||||
@classmethod
|
||||
def from_dict(cls, event):
|
||||
event_id = sanitize_id(event["event_id"])
|
||||
sender = sanitize_id(event["sender"])
|
||||
age = sanitize_age(event["unsigned"]["age"])
|
||||
|
||||
msg = ""
|
||||
formatted_msg = None
|
||||
|
||||
if event['content']['msgtype'] == 'm.text':
|
||||
msg = sanitize_text(event['content']['body'])
|
||||
|
||||
if ('format' in event['content'] and
|
||||
'formatted_body' in event['content']):
|
||||
if event['content']['format'] == "org.matrix.custom.html":
|
||||
formatted_msg = Formatted.from_html(
|
||||
sanitize_text(event['content']['formatted_body']))
|
||||
|
||||
return cls(event_id, sender, age, msg, formatted_msg)
|
||||
|
||||
def execute(self, room, buff, tags):
|
||||
msg = (self.formatted_message.to_weechat()
|
||||
if self.formatted_message else self.message)
|
||||
|
||||
nick, color_name = sender_to_nick_and_color(room, self.sender)
|
||||
color = color_for_tags(color_name)
|
||||
|
||||
event_tags = add_event_tags(self.event_id, nick, color, tags)
|
||||
|
||||
tags_string = ",".join(event_tags)
|
||||
|
||||
data = "{author}\t{msg}".format(author=nick, msg=msg)
|
||||
|
||||
date = date_from_age(self.age)
|
||||
W.prnt_date_tags(buff, date, tags_string, data)
|
||||
|
|
|
@ -15,8 +15,10 @@
|
|||
# CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
from __future__ import unicode_literals
|
||||
from builtins import str
|
||||
|
||||
import time
|
||||
import math
|
||||
|
||||
from matrix.globals import W, SERVERS, OPTIONS
|
||||
|
||||
|
@ -162,3 +164,75 @@ def add_event_tags(event_id, nick, color, tags):
|
|||
tags.append("matrix_id_{event_id}".format(event_id=event_id))
|
||||
|
||||
return tags
|
||||
|
||||
|
||||
def sanitize_token(string):
|
||||
# type: (str) -> str
|
||||
string = sanitize_string(string)
|
||||
|
||||
if len(string) > 512:
|
||||
raise ValueError
|
||||
|
||||
return string
|
||||
|
||||
|
||||
def sanitize_string(string):
|
||||
# type: (str) -> str
|
||||
if not isinstance(string, str):
|
||||
raise TypeError
|
||||
|
||||
remap = {
|
||||
ord('\b'): None,
|
||||
ord('\f'): None,
|
||||
ord('\n'): None,
|
||||
ord('\r'): None,
|
||||
ord('\t'): None,
|
||||
ord('\0'): None
|
||||
}
|
||||
|
||||
return string.translate(remap)
|
||||
|
||||
|
||||
def sanitize_id(string):
|
||||
# type: (str) -> str
|
||||
|
||||
string = sanitize_string(string)
|
||||
|
||||
if len(string) > 128:
|
||||
raise ValueError
|
||||
|
||||
return string
|
||||
|
||||
|
||||
def sanitize_age(age):
|
||||
# type: (int) -> int
|
||||
if not isinstance(age, int):
|
||||
raise TypeError
|
||||
|
||||
if math.isnan(age):
|
||||
raise ValueError
|
||||
|
||||
if math.isinf(age):
|
||||
raise ValueError
|
||||
|
||||
if age < 0:
|
||||
raise ValueError
|
||||
|
||||
return age
|
||||
|
||||
|
||||
def sanitize_text(string):
|
||||
# type: (str) -> str
|
||||
if not isinstance(string, str):
|
||||
raise TypeError
|
||||
|
||||
# yapf: disable
|
||||
remap = {
|
||||
ord('\b'): None,
|
||||
ord('\f'): None,
|
||||
ord('\r'): None,
|
||||
ord('\0'): None
|
||||
}
|
||||
# yapf: enable
|
||||
|
||||
return string.translate(remap)
|
||||
|
|
Loading…
Reference in a new issue