我正在使用Tornado
和aioredis
。我想测试aioredis
类中我的set
实例的一些get
调用(aioredis.create_redis_pool
,tornado.testing.AsyncHTTPTestCase
等)。
我试图通过Internet进行访问,但是我还没有找到该怎么做的方法。
在我的aioredis
测试中,有没有一种方法可以模拟Redis
对临时Tornado
数据库的调用。
预先感谢
答案 0 :(得分:2)
我遇到了同样的问题,增加了在Application
实例之前创建我的Redis连接池的麻烦,以便可以在请求之间共享它。我成功使用了testig.redis,它在一个临时目录中创建了一个Redis实例。该图书馆很旧,多年来没有发生太多事情,但是似乎可以正常工作。无论如何,测试看起来像这样:
import functools
import aioredis
import testing.redis
import redis
from tornado.testing import AsyncHTTPTestCase
from tornado.web import Application
from myapp.base import MyApplication
class TestHandler(AsyncHTTPTestCase):
def setUp(self) -> None:
self.redis_server = testing.redis.RedisServer()
self.redis_client = redis.Redis(**self.redis_server.dsn())
super().setUp()
def tearDown(self) -> None:
self.redis_server.stop()
def get_app(self) -> Application:
redis_dsn = self.redis_server.dsn()
redis = self.io_loop.run_sync(functools.partial(
aioredis.create_redis_pool, f'redis://{redis_dsn["host"]}:{redis_dsn["port"]}/{redis_dsn["db"]}'
))
return MyApplication(redis)
def test_client_handler_should_return_200(self):
self.redis_client.set('val', 'a')
response = self.fetch('/get-some-redis-data/')
self.assertEqual(response.code, 200)
self.assertEqual(response.body, 'a')
为了完成,通常的(非测试)应用程序初始化如下所示:
class MyApplication(Application):
def __init__(self, redis_connection, *args, **kwargs):
self.redis_connection = redis_connection
super().__init__(url_patterns, *args, **kwargs)
async def main():
redis_connection = await aioredis.create_redis_pool(
f'redis://{options.redis_host}:{options.redis_port}/{options.redis_db}'
)
app = MyApplication(redis_connection)
http_server = tornado.httpserver.HTTPServer(app)
http_server.listen(options.port, address=options.listen_ips)
event = tornado.locks.Event()
await event.wait()
if __name__ == "__main__":
asyncio.run(main())
答案 1 :(得分:0)
我使用的库mockaioredis
在我的情况下效果很好。
要使用它,首先我将aioredis
文件中的sys.modules['aioredis'] = mockaioredis
与<project>/tests/__ini__.py
“模拟”。
第二,我扩展了tornado.web.Application
并设置了一种初始化Redis池的方法:
class Application(tornado.web.Application):
async def _conf_redis(self) -> None:
loop = asyncio.get_event_loop()
self.redis = await aioredis.create_redis_pool(address='address',
password='password',
loop=loop)
然后我按如下所示设置测试类:
import my.web
class TestHandler(AsyncHTTPTestCase):
@tornado.testing.gen_test
async def get_app(self):
app = my.web.Application([...])
await app._conf_redis()
self.redis = app.redis
return app
现在,可以在任何测试中通过使用self.redis._redis.set(...)
或self.redis._redis.delete(...)
或self.redis._redis.hsetnx(...)
或self.redis._redis.flushdb()
正常使用Redis。