SQLAlchemy

时间:2015-10-02 11:57:49

标签: sqlalchemy

从用户的角度来看,SQLAlchemy的查询记录似乎有点过于冗长,有时甚至有点神秘:

2015-10-02 13:51:39,500 INFO sqlalchemy.engine.base.Engine BEGIN (implicit)
2015-10-02 13:51:39,502 INFO sqlalchemy.engine.base.Engine SELECT anon_1.shelves_title AS anon_1_shelves_title, ..., anon_1.shelves_created_at AS anon_1_shelves_created_at, anon_1.shelves_updated_at AS anon_1_shelves_updated_at, products_1.id AS products_1_id, products_1.title AS products_1_title
FROM (SELECT shelves.title AS shelves_title, ..., shelves.created_at AS shelves_created_at, shelves.updated_at AS shelves_updated_at
FROM shelves
WHERE shelves.title = ?
 LIMIT ? OFFSET ?) AS anon_1 LEFT OUTER JOIN products AS products_1 ON anon_1.shelves_title = products_1.shelf_title
2015-10-02 13:51:39,502 INFO sqlalchemy.engine.base.Engine ('sample', 1, 0)
2015-10-02 13:51:39,503 INFO sqlalchemy.engine.base.Engine ROLLBACK

(不一定具有代表性,但希望足以说明问题)

可以说Ruby on Rails是一个很好的参考,提供了实际数据库查询的简洁和彩色输出:

Rails SQL logging

(通过https://code.google.com/p/pylonsquerybar/#What_Others_Have_Done

是否有一种简单的方法可以获得SQLAlchemy的类似输出? (前面提到的Pylons查询栏似乎不是为了框架无关的重用而设计的。)

2 个答案:

答案 0 :(得分:2)

你可以设置任何格式的记录器,你可以得到记录器:

import logging
logging.basicConfig(filename='db.log')
logging.getLogger('sqlalchemy.engine').setLevel(logging.INFO)

如何设置颜色和格式请参见此处:
How can I color Python logging output?

答案 1 :(得分:0)

FWIW,低于我们想出的结果。它增加了交替着色,这并没有解决噪音问题,但至少提供了一些视觉上的区别。

import logging

import colorama


def configure_sql_logging():
    sqla_logger = logging.getLogger("sqlalchemy.engine.base.Engine")
    sqla_logger.propagate = False
    sqla_logger.addHandler(SQLLogger(colors=["MAGENTA", "CYAN"]))


class SQLLogger(logging.StreamHandler):

    def __init__(self, *args, colors, **kwargs):
        super().__init__(*args, **kwargs)
        self.colors = colors
        self.colorizer = Colorizer(self.stream, colors[0])

    def emit(self, *args, **kwargs):
        with self.colorizer:
            super().emit(*args, **kwargs)

        # cycle colors
        if self.colorizer.active:
            self.colors.append(self.colors.pop(0))
            self.colorizer.color = self.colors[0]


class Colorizer:

    def __init__(self, stream, color):
        self.stream = stream
        self.active = stream.isatty()
        if self.active:
            colorama.init()
            self.color = color

    def __enter__(self):
        if self.active:
            self.stream.write(getattr(colorama.Fore, self.color))

    def __exit__(self, type, value, traceback):
        if self.active:
            self.stream.write(colorama.Fore.RESET)