我想使用 Selenium 进行集成测试。我的应用在用户注册时发送确认消息(使用 Flask-User 扩展)。我想截获一条消息,提取一个链接并在我的测试中“点击”它。
但是如何拦截已发送的电子邮件?我已经尝试过文档中的方法:
with mail_engine.record_messages() as outbox:
assert len(outbox) > 0
但是,它没有用。
我想使用 Selenium 进行集成测试。我的应用在用户注册时发送确认消息(使用 Flask-User 扩展)。我想截获一条消息,提取一个链接并在我的测试中“点击”它。
但是如何拦截已发送的电子邮件?我已经尝试过文档中的方法:
with mail_engine.record_messages() as outbox:
assert len(outbox) > 0
但是,它没有用。
事实证明,这种方法不起作用,因为我使用的是 Flask-Testing 的 LiveServerTestCase。
您可以订阅信号,但 LiveServerTestCase 比分叉进程(因此应用程序在一个进程中运行,并在另一个进程中测试代码),因此(取决于订阅时间)订阅者代码根本不会被调用或将被调用在单独的过程中。无论哪种方式,这都不是我想要的。
我找到了一个不是很优雅但有效的解决方案:创建一个 multiprocessing.Queue,订阅信号,然后通过队列将所有消息传回测试代码。
这是代码:
class MyTest(LiveServerTestCase):
def create_app(self): # this is called before fork
app = create_test_app()
with app.app_context():
db.create_all()
self.email_q = multiprocessing.Queue()
email_dispatched.connect(self.message_sent)
return app
def message_sent(self, message, app):
self.email_q.put(message) # simply put it into the queue, will be run in the "app" process
def test_all(self):
# here you can do testing, this will be run in the "testing" process
# and when you need messages do this:
message = self.email_q.get(timeout=5) # get email from queue. 5 seconds is reasonable timeout, after it we can assume that the mail wasn't sent at all