[Sqlalchemy-tickets] Issue #3965: Bug with hybrid property ? (zzzeek/sqlalchemy)
Brought to you by:
zzzeek
From: Olivier Le M. <iss...@bi...> - 2017-04-13 13:23:13
|
New issue 3965: Bug with hybrid property ? https://bitbucket.org/zzzeek/sqlalchemy/issues/3965/bug-with-hybrid-property Olivier Le Moign: I use SQLALchemy ORM with a declarative base and SQLITE. I use hybrid properties to encrypt TOTP secrets as follows: ``` #!python class FactorsTOTP(Model): app_secret = 'foobar' user_id = Column(Integer, ForeignKey('user.id'), nullable=False) _key = Column('key', String, nullable=False) @hybrid_property def key(self): cipher_key = urlsafe_b64encode(self.app_secret.ljust(32, b'0')) f = Fernet(cipher_key) return f.decrypt(self._key.encode('utf-8')) @key.setter def key(self, value): cipher_key = urlsafe_b64encode(self.app_secret.ljust(32, b'0')) f = Fernet(cipher_key) self._key = f.encrypt(value.encode('utf-8')).decode('ascii') ``` My problem is, when creating a row: factors_totp = models.FactorsTOTP(key=totp_key) I'm not sure why, but the key getter is being called after the setter and fails on self._key.encode('utf-8'). Simple Python operations work (self._key + 'suffix'), but not calling a function (bytes(self.key, encoding='utf-8) fails as well). ``` #!python Traceback (most recent call last): File "/Users/olemoign/.pyenv/versions/rta/bin/rta_add_admin", line 11, in <module> load_entry_point('rta', 'console_scripts', 'rta_add_admin')() File "/Users/olemoign/Developer/Parsys/rta/rta/scripts/add_admin.py", line 27, in main password, totp_key = _command_line_add_user(env['request'], admin) File "/Users/olemoign/Developer/Parsys/rta/rta/services/users.py", line 363, in _command_line_add_user factors_totp = models.FactorsTOTP(key=totp_key) File "<string>", line 4, in __init__ File "/Users/olemoign/.pyenv/versions/3.5.2/envs/rta/lib/python3.5/site-packages/sqlalchemy/orm/state.py", line 414, in _initialize_instance manager.dispatch.init_failure(self, args, kwargs) File "/Users/olemoign/.pyenv/versions/3.5.2/envs/rta/lib/python3.5/site-packages/sqlalchemy/util/langhelpers.py", line 66, in __exit__ compat.reraise(exc_type, exc_value, exc_tb) File "/Users/olemoign/.pyenv/versions/3.5.2/envs/rta/lib/python3.5/site-packages/sqlalchemy/util/compat.py", line 187, in reraise raise value File "/Users/olemoign/.pyenv/versions/3.5.2/envs/rta/lib/python3.5/site-packages/sqlalchemy/orm/state.py", line 411, in _initialize_instance return manager.original_init(*mixed[1:], **kwargs) File "/Users/olemoign/.pyenv/versions/3.5.2/envs/rta/lib/python3.5/site-packages/sqlalchemy/ext/declarative/base.py", line 653, in _declarative_constructor (k, cls_.__name__)) TypeError: 'key' is an invalid keyword argument for FactorsTOTP ``` This isn't so bad, as I can do factors_totp = models.FactorsTOTP() factors_totp.key = totp_key but I just wanted to raise the issue. Thank you for your great library. |