Skip to content

Commit

Permalink
Add a test case for slackapi#631 with possible solutions for it
Browse files Browse the repository at this point in the history
  • Loading branch information
seratch committed Apr 21, 2020
1 parent 087051a commit e85efe9
Showing 1 changed file with 138 additions and 0 deletions.
138 changes: 138 additions & 0 deletions integration_tests/rtm/test_rtm_client.py
Expand Up @@ -4,6 +4,7 @@
import os
import threading
import time
import traceback
import unittest

import psutil
Expand Down Expand Up @@ -199,3 +200,140 @@ async def send_reply_async(**payload):
await asyncio.sleep(5)
self.assertLess(TestRTMClient.cpu_usage, 30, "Too high CPU usage detected")
self.assertEqual(self.call_count, 3, "The RTM handler failed")

# -----------------------
# Issue #631
# https://github.com/slackapi/python-slackclient/issues/631
# -----------------------

@pytest.mark.skip() # TODO: this issue needs to be fixed
def test_issue_631_sharing_event_loop(self):
self.success = None
self.text = "This message was sent to verify issue #631"

self.loop = asyncio.get_event_loop()
self.rtm_client = RTMClient(
token=self.bot_token,
run_async=False, # even though run_async=False, handlers for RTM events can be a coroutine
loop=self.loop,
)

# @RTMClient.run_on(event="message")
# def send_reply(**payload):
# self.logger.debug(payload)
# data = payload['data']
# web_client = payload['web_client']
# web_client._event_loop = self.loop
# # Maybe you will also need the following line uncommented
# # web_client.run_async = True
#
# if self.text in data['text']:
# channel_id = data['channel']
# thread_ts = data['ts']
# try:
# self.success = web_client.chat_postMessage(
# channel=channel_id,
# text="Thanks!",
# thread_ts=thread_ts
# )
# except Exception as e:
# # slack.rtm.client:client.py:446 When calling '#send_reply()'
# # in the 'test_rtm_client' module the following error was raised: This event loop is already running
# self.logger.error(traceback.format_exc())
# raise e

# Solution (1) for #631
@RTMClient.run_on(event="message")
# even though run_async=False, handlers for RTM events can be a coroutine
async def send_reply(**payload):
self.logger.debug(payload)
data = payload['data']
web_client = payload['web_client']
web_client._event_loop = self.loop

try:
if "text" in data and self.text in data["text"]:
channel_id = data['channel']
thread_ts = data['ts']
self.success = await web_client.chat_postMessage(
channel=channel_id,
text="Thanks!",
thread_ts=thread_ts
)
except Exception as e:
self.logger.error(traceback.format_exc())
raise e

def connect():
self.logger.debug("Starting RTM Client...")
self.rtm_client.start()

t = threading.Thread(target=connect)
t.setDaemon(True)
t.start()

try:
self.assertIsNone(self.success)
time.sleep(5)

self.web_client = WebClient(
token=self.bot_token,
run_async=False,
loop=asyncio.new_event_loop(), # TODO: this doesn't work without this
)
new_message = self.web_client.chat_postMessage(channel=self.channel_id, text=self.text)
self.assertFalse("error" in new_message)

time.sleep(5)
self.assertIsNotNone(self.success)
finally:
t.join(.3)

# Solution (2) for #631
@pytest.mark.skip("this is just for your reference")
@async_test
async def test_issue_631_sharing_event_loop_async(self):
self.loop = asyncio.get_event_loop()
self.success = None
self.text = "This message was sent to verify issue #631"

self.rtm_client = RTMClient(
token=self.bot_token,
run_async=True, # To turn this on, the test method needs to be an async function + @async_test decorator
)

@RTMClient.run_on(event="message")
async def send_reply(**payload):
self.logger.debug(payload)
data = payload['data']
web_client = payload['web_client']
web_client._event_loop = self.loop

try:
if "text" in data and self.text in data["text"]:
channel_id = data['channel']
thread_ts = data['ts']
self.success = await web_client.chat_postMessage(
channel=channel_id,
text="Thanks!",
thread_ts=thread_ts
)
except Exception as e:
self.logger.error(traceback.format_exc())
raise e

# intentionally not waiting here
self.rtm_client.start()

self.assertIsNone(self.success)
await asyncio.sleep(5)

self.web_client = WebClient(
token=self.bot_token,
run_async=True, # all need to be async here
)
new_message = await self.web_client.chat_postMessage(channel=self.channel_id, text=self.text)
self.assertFalse("error" in new_message)

await asyncio.sleep(5)
self.assertIsNotNone(self.success)

0 comments on commit e85efe9

Please sign in to comment.