diff options
-rw-r--r-- | slack/commands.py | 47 | ||||
-rw-r--r-- | slack/slack_message.py | 39 | ||||
-rw-r--r-- | tests/test_slackts.py | 87 |
3 files changed, 163 insertions, 10 deletions
diff --git a/slack/commands.py b/slack/commands.py index 8e807e1..a08799a 100644 --- a/slack/commands.py +++ b/slack/commands.py @@ -271,7 +271,7 @@ def command_slack_workspace_del( ) -@weechat_command(min_args=1) +@weechat_command("%(threads)", min_args=1) def command_slack_thread( buffer: str, args: List[str], options: Dict[str, Optional[str]] ): @@ -392,9 +392,13 @@ def command_cb(data: str, buffer: str, args: str) -> int: return weechat.WEECHAT_RC_OK -def completion_list_add(completion: str, word: str, nick_completion: int, where: str): +def completion_list_add( + completion: str, word: str, nick_completion: int, where: str, buffer: str +): if word == "%(slack_workspaces)": - completion_slack_workspaces_cb("", "slack_workspaces", "", completion) + completion_slack_workspaces_cb("", "slack_workspaces", buffer, completion) + elif word == "%(threads)": + completion_thread_hashes_cb("", "threads", buffer, completion) else: # TODO: Consider WeeChat verison support, in < 2.9 one must use hook_completion_list_add weechat.completion_list_add(completion, word, nick_completion, where) @@ -421,11 +425,13 @@ def completion_slack_workspace_commands_cb( for match in matching_cmds: cmd_arg = match.split(" ") completion_list_add( - completion, cmd_arg[0], 0, weechat.WEECHAT_LIST_POS_SORT + completion, cmd_arg[0], 0, weechat.WEECHAT_LIST_POS_SORT, buffer ) else: for arg in command.completion.split("|"): - completion_list_add(completion, arg, 0, weechat.WEECHAT_LIST_POS_SORT) + completion_list_add( + completion, arg, 0, weechat.WEECHAT_LIST_POS_SORT, buffer + ) return weechat.WEECHAT_RC_OK @@ -440,6 +446,31 @@ def completion_irc_channels_cb( return weechat.WEECHAT_RC_OK +def completion_thread_hashes_cb( + data: str, completion_item: str, buffer: str, completion: str +) -> int: + slack_buffer = shared.buffers.get(buffer) + if not isinstance(slack_buffer, SlackConversation): + return weechat.WEECHAT_RC_OK + + message_tss = sorted(slack_buffer.message_hashes.keys()) + messages = [slack_buffer.messages.get(ts) for ts in message_tss] + thread_messages = [ + message + for message in messages + if message is not None and message.is_thread_parent + ] + for message in thread_messages: + weechat.completion_list_add( + completion, message.hash, 0, weechat.WEECHAT_LIST_POS_BEGINNING + ) + for message in thread_messages: + weechat.completion_list_add( + completion, f"${message.hash}", 0, weechat.WEECHAT_LIST_POS_BEGINNING + ) + return weechat.WEECHAT_RC_OK + + def complete_input(slack_buffer: SlackBuffer, query: str): if ( slack_buffer.completion_context == "ACTIVE_COMPLETION" @@ -543,6 +574,12 @@ def register_commands(): get_callback_name(completion_irc_channels_cb), "", ) + weechat.hook_completion( + "threads", + "complete thread ids for slack", + get_callback_name(completion_thread_hashes_cb), + "", + ) for cmd, command in commands.items(): if command.top_level: diff --git a/slack/slack_message.py b/slack/slack_message.py index 6728038..c36e052 100644 --- a/slack/slack_message.py +++ b/slack/slack_message.py @@ -90,17 +90,46 @@ class SlackTs(str): def __init__(self, ts: str): self.major, self.minor = [int(x) for x in ts.split(".", 1)] - def __eq__(self, other: object) -> bool: - if not isinstance(other, SlackTs): - return False - return self.major == other.major and self.minor == other.minor - def __hash__(self) -> int: return hash((self.major, self.minor)) def __repr__(self) -> str: return f"SlackTs('{self}')" + def _cmp(self, other: object) -> int: + if isinstance(other, str): + other = SlackTs(other) + if not isinstance(other, SlackTs): + return NotImplemented + elif self.major > other.major: + return 1 + elif self.major < other.major: + return -1 + elif self.minor > other.minor: + return 1 + elif self.minor < other.minor: + return -1 + else: + return 0 + + def __eq__(self, other: object) -> bool: + return self._cmp(other) == 0 + + def __ne__(self, other: object) -> bool: + return self._cmp(other) != 0 + + def __gt__(self, other: object) -> bool: + return self._cmp(other) == 1 + + def __ge__(self, other: object) -> bool: + return self._cmp(other) >= 0 + + def __lt__(self, other: object) -> bool: + return self._cmp(other) == -1 + + def __le__(self, other: object) -> bool: + return self._cmp(other) <= 0 + class SlackMessage: def __init__(self, conversation: SlackConversation, message_json: SlackMessageDict): diff --git a/tests/test_slackts.py b/tests/test_slackts.py new file mode 100644 index 0000000..ab60d03 --- /dev/null +++ b/tests/test_slackts.py @@ -0,0 +1,87 @@ +from slack.slack_message import SlackTs + +str_base = "1234567890.012345" +str_base_not_padded = "1234567890.12345" +str_different_minor = "1234567890.012346" +str_different_major = "1234567891.012345" + +ts_base = SlackTs(str_base) +ts_base_not_padded = SlackTs(str_base_not_padded) +ts_different_minor = SlackTs(str_different_minor) +ts_different_major = SlackTs(str_different_major) + + +def test_slackts_eq(): + assert ts_base == ts_base + assert ts_base == ts_base_not_padded + assert ts_base == str_base + assert not ts_base == ts_different_minor + assert not ts_base == ts_different_major + assert not ts_base == str_different_minor + assert not ts_base == str_different_major + + +def test_slackts_ne(): + assert ts_base != ts_different_minor + assert ts_base != ts_different_major + assert ts_base != str_different_minor + assert ts_base != str_different_major + assert not ts_base != ts_base + assert not ts_base != ts_base_not_padded + assert not ts_base != str_base + + +def test_slackts_gt(): + assert ts_different_minor > ts_base + assert ts_different_major > ts_base + assert str_different_minor > ts_base + assert str_different_major > ts_base + assert not ts_base > ts_base + assert not ts_base > ts_base_not_padded + assert not ts_base > ts_different_minor + assert not ts_base > ts_different_major + assert not ts_base > str_base + assert not ts_base > str_different_minor + assert not ts_base > str_different_major + + +def test_slackts_ge(): + assert ts_base >= ts_base + assert ts_base >= ts_base_not_padded + assert ts_different_minor >= ts_base + assert ts_different_major >= ts_base + assert ts_base >= str_base + assert str_different_minor >= ts_base + assert str_different_major >= ts_base + assert not ts_base >= ts_different_minor + assert not ts_base >= ts_different_major + assert not ts_base >= str_different_minor + assert not ts_base >= str_different_major + + +def test_slackts_lt(): + assert ts_base < ts_different_minor + assert ts_base < ts_different_major + assert ts_base < str_different_minor + assert ts_base < str_different_major + assert not ts_base < ts_base + assert not ts_base < ts_base_not_padded + assert not ts_different_minor < ts_base + assert not ts_different_major < ts_base + assert not ts_base < str_base + assert not str_different_minor < ts_base + assert not str_different_major < ts_base + + +def test_slackts_le(): + assert ts_base <= ts_base + assert ts_base <= ts_base_not_padded + assert ts_base <= ts_different_minor + assert ts_base <= ts_different_major + assert ts_base <= str_base + assert ts_base <= str_different_minor + assert ts_base <= str_different_major + assert not ts_different_minor <= ts_base + assert not ts_different_major <= ts_base + assert not str_different_minor <= ts_base + assert not str_different_major <= ts_base |