Open
Description
I have been trying to find out why I am having some flask-sqlalchemy session handling issues while using bpython. Here is the issue in action:
(sockets) test@test~/checkouts/test$ bpython
bpython version 0.16 on top of Python 3.5.2 /home/test/virtualenvs/sockets/bin/python3
>>> from app import db, models
>>> db
<SQLAlchemy engine=postgresql://test:***@localhost/testdb>
>>> user = models.User(nickname='joe', email='joe@localhost')
>>> user in db.session
False
>>> db.session.add(user)
>>> user in db.session
False
>>>
Upon further inspection, it seems that the db.session.add()
call in bpython is creating a new session entirely and placing the user instance in that one:
>>> from app import db, models
>>> db
<SQLAlchemy engine=postgresql://test:***@localhost/testdb>
>>> user = models.User(nickname='Joe', email='joe@localhost')
>>> user._sa_instance_state.transient
True
>>> user._sa_instance_state.session is None
True
>>> db.session
<sqlalchemy.orm.scoping.scoped_session object at 0x7f3532200a58>
>>> db.session.add(user)
>>> user in db.session
False
>>> user._sa_instance_state.pending
True
>>> user._sa_instance_state.session
<sqlalchemy.orm.session.SignallingSession object at 0x7f35336b1940>
>>> user._sa_instance_state.session.hash_key
1
and attempting to again add the instance to the db.session results in a conflict:
>>> db.session.add(user)
Traceback (most recent call last):
File "<input>", line 1, in <module>
db.session.add(user)
File "/home/test/virtualenvs/sockets/lib/python3.5/site-packages/sqlalchemy/orm/scoping.py
", line 157, in do
return getattr(self.registry(), name)(*args, **kwargs)
File "/home/test/virtualenvs/sockets/lib/python3.5/site-packages/sqlalchemy/orm/session.py
", line 1679, in add
self._save_or_update_state(state)
File "/home/test/virtualenvs/sockets/lib/python3.5/site-packages/sqlalchemy/orm/session.py
", line 1691, in _save_or_update_state
self._save_or_update_impl(state)
File "/home/test/virtualenvs/sockets/lib/python3.5/site-packages/sqlalchemy/orm/session.py
", line 1995, in _save_or_update_impl
self._save_impl(state)
File "/home/test/virtualenvs/sockets/lib/python3.5/site-packages/sqlalchemy/orm/session.py
", line 1947, in _save_impl
to_attach = self._before_attach(state, obj)
File "/home/test/virtualenvs/sockets/lib/python3.5/site-packages/sqlalchemy/orm/session.py
", line 2064, in _before_attach
state.session_id, self.hash_key))
sqlalchemy.exc.InvalidRequestError: Object '<User at 0x7f3532055400>' is already attached to
session '1' (this is '3')
Any idea why this seems to only happen in bpython and not python/ipython?