检测Python+1中的查询
nplusone-TrialSpark的Python项目详细描述
nplusone是一个用于检测pythonorms中n+1查询问题的库,包括SQLAlchemy、Peewee和Django ORM。在
问题
许多对象关系映射(ORM)库默认为延迟加载关系。当很少访问相关行时,此模式可能是高效的,但是随着关系访问的频繁,这种模式很快就会变得低效。在这些情况下,使用JOIN急切地加载相关行的性能会大大提高。不幸的是,理解何时使用延迟加载和急切加载可能是一个挑战:你可能不会注意到这个问题,直到你的应用程序慢到爬行。在
nplusone是一个ORM分析工具,用于帮助诊断和改进由于不适当的延迟加载而导致的性能低下。nplusone使用Django或SQLAlchemy监视应用程序,并在发出可能代价高昂的延迟加载时发送通知。它可以识别有问题的关系属性和问题背后的特定代码行,并建议修复以获得更好的性能。在
nplusone还检测到Flask SQLAlchemy和Django ORM的不适当的急切加载,当相关数据迫不及待地加载但从未在当前请求中访问时发出警告。在
安装
pip install -U nplusone
nplusone支持Python>;=2.7或>;=3.3。在
使用
注意:nplusone只应用于开发,不应部署到生产环境中。在
Django
注意:nplusone支持Django>;=1.8。在
将nplusone添加到INSTALLED_APPS:
^{pr2}$添加NPlusOneMiddleware:
MIDDLEWARE = ( 'nplusone.ext.django.NPlusOneMiddleware', ... )
可选地配置日志记录设置:
NPLUSONE_LOGGER = logging.getLogger('nplusone') NPLUSONE_LOG_LEVEL = logging.WARN
配置日志处理程序:
LOGGING = { 'version': 1, 'handlers': { 'console': { 'class': 'logging.StreamHandler', }, }, 'loggers': { 'nplusone': { 'handlers': ['console'], 'level': 'WARN', }, }, }
当应用程序延迟加载数据时,nplusone将发出一条日志消息:
Potential n+1 query detected on `<model>.<field>`
在这种情况下,请考虑使用select_related或prefetch_related。在
当你的应用程序迫不及待地加载相关数据而不访问它时,nplusone将记录一条警告:
Potential unnecessary eager load detected on `<model>.<field>`
烧瓶炼金术
用NPlusOne包装应用程序:
from flask import Flask from nplusone.ext.flask_sqlalchemy import NPlusOne app = Flask(__name__) NPlusOne(app)
可选地配置日志记录设置:
app = Flask(__name__) app.config['NPLUSONE_LOGGER'] = logging.getLogger('app.nplusone') app.config['NPLUSONE_LOG_LEVEL'] = logging.ERROR NPlusOne(app)
当应用程序延迟加载数据时,nplusone将发出一条日志消息:
Potential n+1 query detected on `<model>.<field>`
在本例中,请考虑使用subqueryload或joinedload;有关完整的文档,请参阅SQLAlchemy的relationship loading指南。在
当你的应用程序迫不及待地加载相关数据而不访问它时,nplusone将记录一条警告:
Potential unnecessary eager load detected on `<model>.<field>`
WSGI
对于遵循WSGI规范的其他框架,请使用NPlusOneMiddleware包装应用程序。您还必须为您的ORM导入相关的nplusone扩展名:
import bottle from nplusone.ext.wsgi import NPlusOneMiddleware import nplusone.ext.sqlalchemy app = NPlusOneMiddleware(bottle.app())
通用
上面的集成与请求-响应周期耦合。要在HTTP请求的上下文之外使用nplusone,请使用Profiler上下文管理器:还必须为ORM导入相关的nplusone扩展名:
from nplusone.core import profiler import nplusone.ext.sqlalchemy with profiler.Profiler(): ...
自定义通知
默认情况下,nplusone使用名为“nplusone”的记录器记录所有可能不必要的查询。设置NPLUSONE\u RAISE配置选项时,nplusone也将引发NPlusOneError。这可以用来强制所有涉及不必要查询的自动化测试失败。在
# Django config NPLUSONE_RAISE = True # Flask config app.config['NPLUSONE_RAISE'] = True
如果需要,也可以使用NPLUSONE_ERROR选项指定异常类型。在
忽略通知
要全局忽略来自nplusone的通知,请使用NPLUSONE\u whitelist选项配置白名单:
# Django config NPLUSONE_WHITELIST = [ {'label': 'n_plus_one', 'model': 'myapp.MyModel'} ] # Flask-SQLAlchemy config app.config['NPLUSONE_WHITELIST'] = [ {'label': 'unused_eager_load', 'model': 'MyModel', 'field': 'my_field'} ]
您可以按确切名称或按fnmatch模式列出模型:
# Django config NPLUSONE_WHITELIST = [ {'model': 'myapp.*'} ]
要在本地禁止通知,请使用ignore上下文管理器:
from nplusone.core import signals with signals.ignore(signals.lazy_load): # lazy-load rows # ...
许可证
麻省理工学院授权。有关详细信息,请参阅捆绑的LICENSE文件。在
- 项目
标签: