SQLAlchemy 和 pylint
SQLAlchemy and pylint
SQLAlchemy 似乎给了我很多我无法解决的 pylint 错误。
第一个问题是每个table必须定义为一个新的class。
示例:
class Person(BASE):
"""Person Table Definition"""
__tablename__ = 'person'
id = Column(Integer, primary_key=True)
name = Column(String(30))
...导致这些错误 对于每个 table 我定义:
W: 20, 0: Class has no __init__ method (no-init)
R: 20, 0: Too few public methods (0/2) (too-few-public-methods)
第二个问题是为 SQLAlchemy engine
和 BASE
构造使用全局变量。我不确定如何重构此代码以使这些变量不是全局变量,因为必须将参数 BASE
传递到上面的 table class 定义中。
BASE = sqlalchemy.ext.declarative.declarative_base()
global engine
...
def create_sqla_engine():
"""Create the SQLA engine"""
global engine
engine = create_engine('mysql+mysqlconnector://root:@127.0.0.1:3306/sqlalchemy_example')
我是 python 的新手,但这看起来很难看。 pylint 也抱怨它:
C: 51, 0: Invalid constant name "engine" (invalid-name)
最后,pylint 认为我没有使用我在这段代码中明确使用的导入。
W: 15, 0: Unused declarative_base imported from sqlalchemy.ext.declarative (unused-import)
W: 16, 0: Unused sessionmaker imported from sqlalchemy.orm (unused-import)
...为什么? pylint 与 python3 不兼容吗?我应该在使用的方法中导入我需要的模块,而不是在文件顶部吗?
SQLAlchemy 对 pylint 不是很友好。
你的问题有几点。
1。 public 方法太少
这个错误经常出错,看这里:What does pylint's "Too few public methods" message mean
2。未使用的导入
Pylint 在这种情况下是正确的!如果您导入 declarative_base
,您可以直接使用它:declarative_base(...)
,而不是通过 sqlalchemy.ext.declarative.declarative_base()
。
通常 - 如果未使用导入,请尝试将其删除并检查您的代码(和单元测试,注意 doctests!)是否仍然有效。如果是这样,则导入确实未被使用。
TL;DR - 是的,您使用的是 code,但没有使用导入的 names.
3。无效常量名称
Pylint 在这种情况下是错误的,但原则上是正确的。
(我花了很多时间说服甚至体面的程序员只覆盖 Pylint 的 const-rgx
设置...)。
基本上,Pylint 认为每个全局变量都是常量。在你的情况下它不是。因此,pylint 试图阻止您使用全局变量。
此外,您不应该在函数之外(在全局范围内)编写 global engine
。它应该是这样的:
engine = None
Pylint 仍然会抱怨错误的常量名称。您可以明确地使此警告静音。 (我不建议将其重命名为 ENGINE
)
4。 (额外)SQLAlchemy 查询构建
我发现了这个问题,因为我想看看 pylint 在 SQLAlchemy 条件下的建议。
与 Django 模型不同,SQLAlchemy 使用比较 ==
来获得相等条件(Django 的 field_gt=5
实际上很笨拙,随着时间的推移我不得不喜欢 SQLAlchemy 的方式)。但是Pylint会抱怨:
session.query(AlarmState).filter(AlarmState.is_default == True).one()
给予
C0121: comparison to True should be just 'expr' or 'expr is True'
一切都很好 - 在这种情况下我们真的可以写:
session.query(AlarmState).filter(AlarmState.is_default).one()
而且很好。
但是,怎么样:
session.query(AlarmState).filter(AlarmState.is_default == False).all()
好吧,我们得到:
C0121: comparison to False should be just 'not expr' or 'expr is False'
现在怎么办?这不起作用:session.query(AlarmState).filter(not AlarmState.is_default .all()
!!! - 它似乎按 False
条件和 returns 空集过滤。同样在这里:sess.query(AlarmState).filter(AlarmState.is_default is False).all()
.
我找到了解决方法 - 你实际上可以写:
session.query(AlarmState).filter(AlarmState.is_default.__eq__(False)).all()
两者兼而有之:
- 给出正确的结果
- 不引发 Pylint 通知
我对此感觉不太好。这是在用这个愚蠢的工具玩猫捉老鼠的游戏。
我想知道其他人对此做了什么,这就是我来到这里的原因。
编辑 - 好的,我找到了 "right" 的方法...
如何将列与 False
进行比较(没有投诉)?
from sqlalchemy import not_
session.query(AlarmState).filter(not_(AlarmState.is_default)).all()
这就是 not_
可能用于...
SQLAlchemy 似乎给了我很多我无法解决的 pylint 错误。
第一个问题是每个table必须定义为一个新的class。
示例:
class Person(BASE):
"""Person Table Definition"""
__tablename__ = 'person'
id = Column(Integer, primary_key=True)
name = Column(String(30))
...导致这些错误 对于每个 table 我定义:
W: 20, 0: Class has no __init__ method (no-init)
R: 20, 0: Too few public methods (0/2) (too-few-public-methods)
第二个问题是为 SQLAlchemy engine
和 BASE
构造使用全局变量。我不确定如何重构此代码以使这些变量不是全局变量,因为必须将参数 BASE
传递到上面的 table class 定义中。
BASE = sqlalchemy.ext.declarative.declarative_base()
global engine
...
def create_sqla_engine():
"""Create the SQLA engine"""
global engine
engine = create_engine('mysql+mysqlconnector://root:@127.0.0.1:3306/sqlalchemy_example')
我是 python 的新手,但这看起来很难看。 pylint 也抱怨它:
C: 51, 0: Invalid constant name "engine" (invalid-name)
最后,pylint 认为我没有使用我在这段代码中明确使用的导入。
W: 15, 0: Unused declarative_base imported from sqlalchemy.ext.declarative (unused-import)
W: 16, 0: Unused sessionmaker imported from sqlalchemy.orm (unused-import)
...为什么? pylint 与 python3 不兼容吗?我应该在使用的方法中导入我需要的模块,而不是在文件顶部吗?
SQLAlchemy 对 pylint 不是很友好。
你的问题有几点。
1。 public 方法太少
这个错误经常出错,看这里:What does pylint's "Too few public methods" message mean
2。未使用的导入
Pylint 在这种情况下是正确的!如果您导入 declarative_base
,您可以直接使用它:declarative_base(...)
,而不是通过 sqlalchemy.ext.declarative.declarative_base()
。
通常 - 如果未使用导入,请尝试将其删除并检查您的代码(和单元测试,注意 doctests!)是否仍然有效。如果是这样,则导入确实未被使用。
TL;DR - 是的,您使用的是 code,但没有使用导入的 names.
3。无效常量名称
Pylint 在这种情况下是错误的,但原则上是正确的。
(我花了很多时间说服甚至体面的程序员只覆盖 Pylint 的 const-rgx
设置...)。
基本上,Pylint 认为每个全局变量都是常量。在你的情况下它不是。因此,pylint 试图阻止您使用全局变量。
此外,您不应该在函数之外(在全局范围内)编写 global engine
。它应该是这样的:
engine = None
Pylint 仍然会抱怨错误的常量名称。您可以明确地使此警告静音。 (我不建议将其重命名为 ENGINE
)
4。 (额外)SQLAlchemy 查询构建
我发现了这个问题,因为我想看看 pylint 在 SQLAlchemy 条件下的建议。
与 Django 模型不同,SQLAlchemy 使用比较 ==
来获得相等条件(Django 的 field_gt=5
实际上很笨拙,随着时间的推移我不得不喜欢 SQLAlchemy 的方式)。但是Pylint会抱怨:
session.query(AlarmState).filter(AlarmState.is_default == True).one()
给予
C0121: comparison to True should be just 'expr' or 'expr is True'
一切都很好 - 在这种情况下我们真的可以写:
session.query(AlarmState).filter(AlarmState.is_default).one()
而且很好。
但是,怎么样:
session.query(AlarmState).filter(AlarmState.is_default == False).all()
好吧,我们得到:
C0121: comparison to False should be just 'not expr' or 'expr is False'
现在怎么办?这不起作用:session.query(AlarmState).filter(not AlarmState.is_default .all()
!!! - 它似乎按 False
条件和 returns 空集过滤。同样在这里:sess.query(AlarmState).filter(AlarmState.is_default is False).all()
.
我找到了解决方法 - 你实际上可以写:
session.query(AlarmState).filter(AlarmState.is_default.__eq__(False)).all()
两者兼而有之:
- 给出正确的结果
- 不引发 Pylint 通知
我对此感觉不太好。这是在用这个愚蠢的工具玩猫捉老鼠的游戏。 我想知道其他人对此做了什么,这就是我来到这里的原因。
编辑 - 好的,我找到了 "right" 的方法...
如何将列与 False
进行比较(没有投诉)?
from sqlalchemy import not_
session.query(AlarmState).filter(not_(AlarmState.is_default)).all()
这就是 not_
可能用于...