Re: [sqlalchemy] Injecting User info into _history table to track who performed the change
Yup, makes perfect sense. So what the code/fix is achieving, in effect, is what is described here: https://docs.sqlalchemy.org/en/13/faq/ormconfiguration.html#i-m-getting-a-warning-or-error-about-implicitly-combining-column-x-under-attribute-y Just using a different approach because of the inheritance. Cheers, JP On Wednesday, March 24, 2021 at 3:49:12 p.m. UTC-4 Simon King wrote: > I'm not 100% confident here (the history_meta code does some pretty > complicated stuff to deal with inheritance), but I'll give it a go: > > 1. You've adapted history_meta to add an extra column to history > tables, called "accountable". > 2. You've got an inheritance hierarchy (CompoundAdministration > inherits from Process) > 3. Both CompoundAdministration and Process use the Versioned mixin > 4. This results in 2 new mapped classes, ProcessHistory and > CompoundAdministrationHistory. > 5. CompoundAdministrationHistory inherits from ProcessHistory > > Step 5 is the problem: CompoundAdministrationHistory inherits from > ProcessHistory, but both tables have an "accountable" column. Normally > that's a problem - when you set the > CompoundAdministrationHistory.accountable attribute, should SQLAlchemy > update the column in the compound_administration_history table, or > process_history, or both? SQLAlchemy defaults to updating both, but > warns you about the ambiguity. > > In this case, you really do want that property to target both columns, > so your fix is correct: > > properties["accountable"] = (table.c.accountable,) + tuple( > super_history_mapper.attrs.accountable.columns > ) > > This says that the "accountable" property should target the column on > the local (inheriting) table as well as whatever columns the parent > class was targeting. > > You should test that when you modify a CompoundAdministration object, > you get a new row in both the compound_administration_history and the > process_history tables, and that the "accountable" column is set > correctly. > > I hope that makes sense, > > Simon > > On Wed, Mar 24, 2021 at 2:25 PM JPLaverdure wrote: > > > > Hi Simon, > > > > Thanks for pointing out the collision, it kinda flew under the radar ! > > I renamed the column from "user" to "accountable" and but still got > > > > SAWarning: > > Implicitly combining column process_history.accountable with column > compound_administration_history.accountable under attribute 'accountable'. > > Please configure one or more attributes for these same-named columns > explicitly. > > > > As mentioned, these tables both also have a "changed" attribute, but did > not throw the warnings... > > Looking a bit further, I spotted this piece of code in history_meta: > > properties["changed"] = (table.c.changed,) + tuple( > > super_history_mapper.attrs.changed.columns > > ) > > So I added: > > properties["accountable"] = (table.c.accountable,) + tuple( > > super_history_mapper.attrs.accountable.columns > > ) > > > > And the warnings have disappeared. > > > > Could you explain what these instructions actually do ? > > > > Thanks > > On Wednesday, March 24, 2021 at 5:18:02 a.m. UTC-4 Simon King wrote: > >> > >> I think the warning message is slightly misleading, probably because > >> of the inheritance, but the fundamental problem is likely that your > >> "process" table already has a "user" column, and you're trying to add > >> a second "user" column in the process_history table, which can't work. > >> > >> If you use a different column name to store the user in the history > >> table, does the warning go away? > >> > >> Simon > >> > >> On Tue, Mar 23, 2021 at 7:17 PM JPLaverdure > wrote: > >> > > >> > It seems I lost my previous email.. Here it is again: > >> > > >> > Sure ! > >> > Here are 2 classes for which the generated _history sister tables > (generated by history_meta.py) throw the warnings: > >> > > >> > The Parent class: > >> > > >> > class Process(Versioned, Base, UtilityMixin): > >> > __tablename__ = 'process' > >> > __table_args__ = {} > >> > > >> > id = Column(Integer, primary_key=True) > >> > discriminator = Column('type', String(64)) > >> > timestamp = Column(DateTime, nullable=False) > >> > start_date = Column(Date, nullable=False) > >> > am_pm = Column(String(8)) > >> > prob
Re: [sqlalchemy] Injecting User info into _history table to track who performed the change
Hi Simon, Thanks for pointing out the collision, it kinda flew under the radar ! I renamed the column from "user" to "accountable" and but still got SAWarning: Implicitly combining column process_history.accountable with column compound_administration_history.accountable under attribute 'accountable'. Please configure one or more attributes for these same-named columns explicitly. As mentioned, these tables both also have a "changed" attribute, but did not throw the warnings... Looking a bit further, I spotted this piece of code in history_meta: properties["changed"] = (table.c.changed,) + tuple( super_history_mapper.attrs.changed.columns ) So I added: properties["accountable"] = (table.c.accountable,) + tuple( super_history_mapper.attrs.accountable.columns ) And the warnings have disappeared. Could you explain what these instructions actually do ? Thanks On Wednesday, March 24, 2021 at 5:18:02 a.m. UTC-4 Simon King wrote: > I think the warning message is slightly misleading, probably because > of the inheritance, but the fundamental problem is likely that your > "process" table already has a "user" column, and you're trying to add > a second "user" column in the process_history table, which can't work. > > If you use a different column name to store the user in the history > table, does the warning go away? > > Simon > > On Tue, Mar 23, 2021 at 7:17 PM JPLaverdure wrote: > > > > It seems I lost my previous email.. Here it is again: > > > > Sure ! > > Here are 2 classes for which the generated _history sister tables > (generated by history_meta.py) throw the warnings: > > > > The Parent class: > > > > class Process(Versioned, Base, UtilityMixin): > > __tablename__ = 'process' > > __table_args__ = {} > > > > id = Column(Integer, primary_key=True) > > discriminator = Column('type', String(64)) > > timestamp = Column(DateTime, nullable=False) > > start_date = Column(Date, nullable=False) > > am_pm = Column(String(8)) > > probable_end_date = Column(Date) > > end_date = Column(Date) > > user = Column(String(128), nullable=False) > > comments = Column(Text) > > > > __mapper_args__ = {'polymorphic_on': discriminator, > 'polymorphic_identity': 'process', > > 'order_by': [start_date.desc(), id.desc()]} > > > > protocol_id = Column(Integer, ForeignKey('protocol.id', > onupdate='cascade', ondelete='restrict')) > > process_type_id = Column(Integer, ForeignKey('process_type.id', > onupdate='cascade', ondelete='restrict')) > > > > protocol = relationship(Protocol, backref='processes', uselist=False) > > process_type = relationship(ProcessType, backref='processes', > uselist=False) > > > > The Child class: > > > > class CompoundAdministration(Process): > > __tablename__ = 'compound_administration' > > __table_args__ = {} > > __mapper_args__ = {'polymorphic_identity': 'compound_admin'} > > > > id = Column(Integer, ForeignKey('process.id', onupdate='cascade', > ondelete='cascade'), primary_key=True) > > dose = Column(String(64)) > > substance = Column(String(128)) > > frequency = Column(String(64)) > > duration = Column(String(64)) > > > > route_id = Column(Integer, ForeignKey('administration_route.id', > onupdate='cascade', ondelete='restrict')) > > route = relationship(AdministrationRoute, uselist=False) > > > > > > As reminder, versioning was implemented using this recipe/example from > SQLA: > > > https://docs.sqlalchemy.org/en/13/_modules/examples/versioned_history/history_meta.html > > > > And here is the associated warning: > > > > SAWarning: > > Implicitly combining column process_history.user with column > compound_administration_history.user under attribute 'user'. > > Please configure one or more attributes for these same-named columns > explicitly. > > > > Thanks for your help resolving this, > > > > JP > > On Tuesday, March 23, 2021 at 6:24:03 a.m. UTC-4 Simon King wrote: > >> > >> Can you show us the mapping definitions that are triggering these > warnings? > >> > >> On Mon, Mar 22, 2021 at 6:29 PM JPLaverdure > wrote: > >> > > >> > Hi, > >> > > >> > Thanks for your support guys. > >> > > >> > I've implemented logging the user's email in the _history tables by > adding this Column definition inside my history_meta.py file: > >> > cols.append( > >> > Column( > >> > "user", > >> > String, &
Re: [sqlalchemy] Injecting User info into _history table to track who performed the change
Sure ! Here's an example. This is the base class class Process(Versioned, Base, UtilityMixin): __tablename__ = 'process' __table_args__ = {} id = Column(Integer, primary_key=True) discriminator = Column('type', String(64)) timestamp = Column(DateTime, nullable=False) start_date = Column(Date, nullable=False) am_pm = Column(String(8)) probable_end_date = Column(Date) end_date = Column(Date) user = Column(String(128), nullable=False) comments = Column(Text) __mapper_args__ = {'polymorphic_on': discriminator, 'polymorphic_identity': 'process', 'order_by': [start_date.desc(), id.desc()]} protocol_id = Column(Integer, ForeignKey('protocol.id', onupdate='cascade', ondelete='restrict')) process_type_id = Column(Integer, ForeignKey('process_type.id', onupdate='cascade', ondelete='restrict')) an one of the child classes: class CompoundAdministration(Process): __tablename__ = 'compound_administration' __table_args__ = {} __mapper_args__ = {'polymorphic_identity': 'compound_admin'} id = Column(Integer, ForeignKey('process.id', onupdate='cascade', ondelete='cascade'), primary_key=True) dose = Column(String(64)) substance = Column(String(128)) frequency = Column(String(64)) duration = Column(String(64)) route_id = Column(Integer, ForeignKey('administration_route.id', onupdate='cascade', ondelete='restrict')) route = relationship(AdministrationRoute, uselist=False) I have many types of processes that derive from the parent class and all of these throws a warning linked to the "user" Column Added in their respective _history. For reference I implemented versioning using this recipe: https://docs.sqlalchemy.org/en/13/_modules/examples/versioned_history/history_meta.html I added my "user" column definition right under the "changed" column in history_meta.py. The "changed" column does not trigger the warnings but my newly added "user" column does. So I'm guessing there is a extra step I forgot to add in the history_meta.py file but I cannot find what or where.. Thanks ! On Tuesday, March 23, 2021 at 6:24:03 a.m. UTC-4 Simon King wrote: > Can you show us the mapping definitions that are triggering these warnings? > > On Mon, Mar 22, 2021 at 6:29 PM JPLaverdure wrote: > > > > Hi, > > > > Thanks for your support guys. > > > > I've implemented logging the user's email in the _history tables by > adding this Column definition inside my history_meta.py file: > > cols.append( > > Column( > > "user", > > String, > > info=version_meta, > > ) > > ) > > but i'm running into a good load of SAWarnings stating that there is an > implicit combining of the "user" column taking place > > (I have multi-table inheritance setup for some entities, those are the > ones throwing the warning) > > I don't get why the column "changed" (which holds the timestamp of the > change) and is defined in exactly the same way does not generate these > warnings ? > > What configuration setting am I missing here ? > > > > I found this > > > https://docs.sqlalchemy.org/en/13/faq/ormconfiguration.html#i-m-getting-a-warning-or-error-about-implicitly-combining-column-x-under-attribute-y > > But it doesn't seem to fit 100% with what I'm seeing inside > history_meta.py > > > > Thanks !! > > On Monday, March 15, 2021 at 4:33:40 p.m. UTC-4 Jonathan Vanasco wrote: > >> > >> Going beyond what Simon did.. > >> > >> I typically make make a table like `user_transaction`, which has all of > the relevant information for the transaction: > >> > >> * User ID > >> * Timestamp > >> * Remote IP > >> > >> Using the sqlalchemy hooks, I'll then do something like: > >> > >> * update the object table with the user_transaction id > >> or > >> * use an association table that tracks a user_transaction_id to an > object id and version > >> > >> FYI, Simon -- as of a few weeks ago, that pattern is now part of the > pyramid sqlalchemy starter template! > >> > >> On Monday, March 15, 2021 at 6:46:02 AM UTC-4 Simon King wrote: > >>> > >>> I use pyramid as a web framework, and when I create the DB session for > >>> each request, I add a reference to the current request object to the > >>> DB session. The session object has an "info" attribute which is > >>> intended for application-specific things like this: > >>> > >>> > https://docs.sqlalchemy.org/en/13/orm/session_api.html#sqlalchemy.orm.session.Session.info > >>> > >>> Then, in the before_flush event handler, I retrieve the request object > >>> from
Re: [sqlalchemy] Injecting User info into _history table to track who performed the change
It seems I lost my previous email.. Here it is again: Sure ! Here are 2 classes for which the generated _history sister tables (generated by history_meta.py) throw the warnings: *The Parent class:* class Process(Versioned, Base, UtilityMixin): __tablename__ = 'process' __table_args__ = {} id = Column(Integer, primary_key=True) discriminator = Column('type', String(64)) timestamp = Column(DateTime, nullable=False) start_date = Column(Date, nullable=False) am_pm = Column(String(8)) probable_end_date = Column(Date) end_date = Column(Date) user = Column(String(128), nullable=False) comments = Column(Text) __mapper_args__ = {'polymorphic_on': discriminator, 'polymorphic_identity': 'process', 'order_by': [start_date.desc(), id.desc()]} protocol_id = Column(Integer, ForeignKey('protocol.id', onupdate='cascade', ondelete='restrict')) process_type_id = Column(Integer, ForeignKey('process_type.id', onupdate='cascade', ondelete='restrict')) protocol = relationship(Protocol, backref='processes', uselist=False) process_type = relationship(ProcessType, backref='processes', uselist=False) *The Child class:* class CompoundAdministration(Process): __tablename__ = 'compound_administration' __table_args__ = {} __mapper_args__ = {'polymorphic_identity': 'compound_admin'} id = Column(Integer, ForeignKey('process.id', onupdate='cascade', ondelete='cascade'), primary_key=True) dose = Column(String(64)) substance = Column(String(128)) frequency = Column(String(64)) duration = Column(String(64)) route_id = Column(Integer, ForeignKey('administration_route.id', onupdate='cascade', ondelete='restrict')) route = relationship(AdministrationRoute, uselist=False) As reminder, versioning was implemented using this recipe/example from SQLA: https://docs.sqlalchemy.org/en/13/_modules/examples/versioned_history/history_meta.html And here is the associated warning: SAWarning: Implicitly combining column process_history.user with column compound_administration_history.user under attribute 'user'. Please configure one or more attributes for these same-named columns explicitly. Thanks for your help resolving this, JP On Tuesday, March 23, 2021 at 6:24:03 a.m. UTC-4 Simon King wrote: > Can you show us the mapping definitions that are triggering these warnings? > > On Mon, Mar 22, 2021 at 6:29 PM JPLaverdure wrote: > > > > Hi, > > > > Thanks for your support guys. > > > > I've implemented logging the user's email in the _history tables by > adding this Column definition inside my history_meta.py file: > > cols.append( > > Column( > > "user", > > String, > > info=version_meta, > > ) > > ) > > but i'm running into a good load of SAWarnings stating that there is an > implicit combining of the "user" column taking place > > (I have multi-table inheritance setup for some entities, those are the > ones throwing the warning) > > I don't get why the column "changed" (which holds the timestamp of the > change) and is defined in exactly the same way does not generate these > warnings ? > > What configuration setting am I missing here ? > > > > I found this > > > https://docs.sqlalchemy.org/en/13/faq/ormconfiguration.html#i-m-getting-a-warning-or-error-about-implicitly-combining-column-x-under-attribute-y > > But it doesn't seem to fit 100% with what I'm seeing inside > history_meta.py > > > > Thanks !! > > On Monday, March 15, 2021 at 4:33:40 p.m. UTC-4 Jonathan Vanasco wrote: > >> > >> Going beyond what Simon did.. > >> > >> I typically make make a table like `user_transaction`, which has all of > the relevant information for the transaction: > >> > >> * User ID > >> * Timestamp > >> * Remote IP > >> > >> Using the sqlalchemy hooks, I'll then do something like: > >> > >> * update the object table with the user_transaction id > >> or > >> * use an association table that tracks a user_transaction_id to an > object id and version > >> > >> FYI, Simon -- as of a few weeks ago, that pattern is now part of the > pyramid sqlalchemy starter template! > >> > >> On Monday, March 15, 2021 at 6:46:02 AM UTC-4 Simon King wrote: > >>> > >>> I use pyramid as a web framework, and when I create the DB session for > >>> each request, I add a reference to the current request object to the > >>> DB session. The session object has an "info" attribute which is > >>> intended for application-specific things like this: > >>> > >>> > https://docs.sqlalchemy.org/en/13/orm/session_api.html#sqlalchemy.orm.session.Session.info > >>> > >>> Then, in the be
Re: [sqlalchemy] Injecting User info into _history table to track who performed the change
Hi, Thanks for your support guys. I've implemented logging the user's email in the _history tables by adding this Column definition inside my history_meta.py file: cols.append( Column( "user", String, info=version_meta, ) ) but i'm running into a good load of SAWarnings stating that there is an implicit combining of the "user" column taking place (I have multi-table inheritance setup for some entities, those are the ones throwing the warning) I don't get why the column "changed" (which holds the timestamp of the change) and is defined in exactly the same way does not generate these warnings ? What configuration setting am I missing here ? I found this https://docs.sqlalchemy.org/en/13/faq/ormconfiguration.html#i-m-getting-a-warning-or-error-about-implicitly-combining-column-x-under-attribute-y But it doesn't seem to fit 100% with what I'm seeing inside history_meta.py Thanks !! On Monday, March 15, 2021 at 4:33:40 p.m. UTC-4 Jonathan Vanasco wrote: > Going beyond what Simon did.. > > I typically make make a table like `user_transaction`, which has all of > the relevant information for the transaction: > > * User ID > * Timestamp > * Remote IP > > Using the sqlalchemy hooks, I'll then do something like: > > * update the object table with the user_transaction id > or > * use an association table that tracks a user_transaction_id to an object > id and version > > FYI, Simon -- as of a few weeks ago, that pattern is now part of the > pyramid sqlalchemy starter template! > > On Monday, March 15, 2021 at 6:46:02 AM UTC-4 Simon King wrote: > >> I use pyramid as a web framework, and when I create the DB session for >> each request, I add a reference to the current request object to the >> DB session. The session object has an "info" attribute which is >> intended for application-specific things like this: >> >> >> https://docs.sqlalchemy.org/en/13/orm/session_api.html#sqlalchemy.orm.session.Session.info >> >> Then, in the before_flush event handler, I retrieve the request object >> from session.info, and then I can add whatever request-specific info I >> want to the DB. >> >> Simon >> >> On Sun, Mar 14, 2021 at 4:05 PM JPLaverdure wrote: >> > >> > Hi Elmer, >> > >> > Thanks for your reply ! >> > My issue is not with obtaining the info I want to inject (the logged in >> users's email), I already have that all ready to go :) >> > >> > My whole database is versioned using the history_meta.py example from >> SQLAlchemy >> > >> https://docs.sqlalchemy.org/en/13/_modules/examples/versioned_history/history_meta.html >> > >> > I was hoping for a simple way to inject the user info into the _history >> row creation steps. >> > >> > The SQLAlchemy example makes use of this event listener: >> > >> > def versioned_session(session): >> > >> > @event.listens_for(session, "before_flush") >> > def before_flush(session, flush_context, instances): >> > for obj in versioned_objects(session.dirty): >> > create_version(obj, session) >> > for obj in versioned_objects(session.deleted): >> > create_version(obj, session, deleted=True) >> > >> > So I'm tempted to follow the same strategy and just override this >> listener to supplement it with the user info but I'm wondering how to pass >> in non SQLAlchemy info into its execution context... >> > >> > So basically, I have the info I want to inject, I'm just not sure how >> to pass it to SQLAlchemy >> > >> > Thanks, >> > >> > JP >> > >> > On Friday, March 12, 2021 at 6:55:19 p.m. UTC-5 elmer@gmail.com >> wrote: >> >> >> >> Hi JP, >> >> >> >> Depending on how you've implemented your history tracking, that >> routine is quite far removed from your web framework and getting a neat, >> clean way of dealing with that might not be within reach. >> >> >> >> However, most web frameworks have some concept of a threadlocal >> request (or function to retrieve it), which you could invoke and if such a >> request exists, you could use that to load whatever user identity you have >> available on there (again, the details differ, but this tends to be a >> shared feature). From there you can store the user either as a foreign key, >> or a unique identifier like email. Which one you pick would depend on how >> you want the history to be affected when you delete a user record for >> example. >&g
Re: [sqlalchemy] Injecting User info into _history table to track who performed the change
Hi Elmer, Thanks for your reply ! My issue is not with obtaining the info I want to inject (the logged in users's email), I already have that all ready to go :) My whole database is versioned using the history_meta.py example from SQLAlchemy https://docs.sqlalchemy.org/en/13/_modules/examples/versioned_history/history_meta.html I was hoping for a simple way to inject the user info into the _history row creation steps. The SQLAlchemy example makes use of this event listener: def versioned_session(session): @event.listens_for(session, "before_flush") def before_flush(session, flush_context, instances): for obj in versioned_objects(session.dirty): create_version(obj, session) for obj in versioned_objects(session.deleted): create_version(obj, session, deleted=True) So I'm tempted to follow the same strategy and just override this listener to supplement it with the user info but I'm wondering how to pass in non SQLAlchemy info into its execution context... So basically, I have the info I want to inject, I'm just not sure how to pass it to SQLAlchemy Thanks, JP On Friday, March 12, 2021 at 6:55:19 p.m. UTC-5 elmer@gmail.com wrote: > Hi JP, > > Depending on how you've implemented your history tracking, that routine is > quite far removed from your web framework and getting a neat, clean way of > dealing with that might not be within reach. > > However, most web frameworks have some concept of a threadlocal request > (or function to retrieve it), which you could invoke and if such a request > exists, you could use that to load whatever user identity you have > available on there (again, the details differ, but this tends to be a > shared feature). From there you can store the user either as a foreign key, > or a unique identifier like email. Which one you pick would depend on how > you want the history to be affected when you delete a user record for > example. > > > > On Fri, Mar 12, 2021 at 11:58 PM JPLaverdure wrote: > >> Hello everyone, >> >> We already have the ability to timestamp the creation of the history row, >> but it would also be interesting to be able to track the user responsible >> for the content update. >> I would like to get suggestions on the best way to achieve this. >> >> I realize this is somewhat outside the scope of sqlalchemy as the notion >> of a "logged in user" is more closely related to the context of the >> app/webapp using SQLAlchemy as its ORM but maybe other people would benefit >> from having a way to inject arbitrary data in the history table. >> >> Ideally, I would like the insert in the _history table to be atomic, so I >> feel like hooking an update statement to an event might not be the way to >> go. >> I'm tempted to modify the signature of before_flush but I'm not sure >> where it gets called. >> >> Any help is welcome ! >> Thanks >> >> JP >> >> -- >> SQLAlchemy - >> The Python SQL Toolkit and Object Relational Mapper >> >> http://www.sqlalchemy.org/ >> >> To post example code, please provide an MCVE: Minimal, Complete, and >> Verifiable Example. See http://stackoverflow.com/help/mcve for a full >> description. >> --- >> You received this message because you are subscribed to the Google Groups >> "sqlalchemy" group. >> To unsubscribe from this group and stop receiving emails from it, send an >> email to sqlalchemy+...@googlegroups.com. >> To view this discussion on the web visit >> https://groups.google.com/d/msgid/sqlalchemy/82a24998-14e1-4ff4-a725-dd25c20a8bf2n%40googlegroups.com >> >> <https://groups.google.com/d/msgid/sqlalchemy/82a24998-14e1-4ff4-a725-dd25c20a8bf2n%40googlegroups.com?utm_medium=email_source=footer> >> . >> > > > -- > > Elmer > -- SQLAlchemy - The Python SQL Toolkit and Object Relational Mapper http://www.sqlalchemy.org/ To post example code, please provide an MCVE: Minimal, Complete, and Verifiable Example. See http://stackoverflow.com/help/mcve for a full description. --- You received this message because you are subscribed to the Google Groups "sqlalchemy" group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/sqlalchemy/58bb6713-18f4-4d69-8d7b-a27772711bd5n%40googlegroups.com.
[sqlalchemy] Injecting User info into _history table to track who performed the change
Hello everyone, We already have the ability to timestamp the creation of the history row, but it would also be interesting to be able to track the user responsible for the content update. I would like to get suggestions on the best way to achieve this. I realize this is somewhat outside the scope of sqlalchemy as the notion of a "logged in user" is more closely related to the context of the app/webapp using SQLAlchemy as its ORM but maybe other people would benefit from having a way to inject arbitrary data in the history table. Ideally, I would like the insert in the _history table to be atomic, so I feel like hooking an update statement to an event might not be the way to go. I'm tempted to modify the signature of before_flush but I'm not sure where it gets called. Any help is welcome ! Thanks JP -- SQLAlchemy - The Python SQL Toolkit and Object Relational Mapper http://www.sqlalchemy.org/ To post example code, please provide an MCVE: Minimal, Complete, and Verifiable Example. See http://stackoverflow.com/help/mcve for a full description. --- You received this message because you are subscribed to the Google Groups "sqlalchemy" group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/sqlalchemy/82a24998-14e1-4ff4-a725-dd25c20a8bf2n%40googlegroups.com.
Re: [sqlalchemy] SAWarnings when using history_meta.py versioning and Inheritance.
Hi Michael, I quite agree that child entities don't need their own copy of the changed attribute, but this is also the way that the version attribute is handled. (ie: both parent and child entities have their own copy of version) Is there any way we can fix the both of them ? As for the option to remove the changed attribute... Well, I'm the one who suggested its addition and submitted the pull request :) Thanks, JP On Friday, 17 October 2014 16:05:15 UTC-4, Michael Bayer wrote: On Oct 17, 2014, at 3:50 PM, JPLaverdure jp.lav...@gmail.com javascript: wrote: Hi Michael, My bad, they do indeed only show up on mapping... which takes place when my pyramid app instantiates. Sorry for the confusion :) Still, they could be unnerving for someone deploying the app. Any way to not have these show up ? I did look into version_meta.py and tried to make some tweaks when I saw anything having to do with the version atribute.. But to no avail. Your help is greatly appreciated ! it’s not clear why a class that inherits from another needs a separate “changed” column in any case. The recipe indicates on line 68 this column is optional so I’d remove it, or just make it conditional if “super_mapper” is not present to have it only on the base table. or maybe just map it differently, or not at all, down where it calls mapper(): m = mapper( versioned_cls, table, inherits=super_history_mapper, polymorphic_on=polymorphic_on, polymorphic_identity=local_mapper.polymorphic_identity, exclude_columns=[‘changed’] ) JP On Friday, 17 October 2014 14:52:22 UTC-4, JPLaverdure wrote: Hello, It seems a number of SAWarnings are being thrown whenever I instantiate Versioned objects which make use of inheritance: SAWarning: Implicitly combining column container_history.changed with column barcoded_container_history.changed under attribute 'changed'. Please configure one or more attributes for these same-named columns explicitly. prop = self._property_from_column(key, prop) Unfortunately, since these objects are instantiated auto-magically by the Versioned mixin class, I can't see a way to make these go away or address the issue. I tried looking into the history_meta.py source and cannot understand why this same warning is not being thrown for the version attribute. Anyone has an idea ? Thanks ! JP -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+...@googlegroups.com javascript:. To post to this group, send email to sqlal...@googlegroups.com javascript:. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/d/optout. -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To post to this group, send email to sqlalchemy@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/d/optout.
Re: [sqlalchemy] SAWarnings when using history_meta.py versioning and Inheritance.
I fully agree with you and had forgotten that version was part of the primary key. I believe I made the appropriate changes to history_meta.py and will submit a pull request shortly As always, thanks for your help ! JP On Tuesday, 21 October 2014 14:41:15 UTC-4, Michael Bayer wrote: “version” is part of the primary key and is FK’ed to the superclass table, so the warning isn’t generated for that one. it wouldn’t be appropriate for a datetime “changed” to have a foreign key. IMO it only needs to be on the base table. On Oct 21, 2014, at 2:35 PM, JPLaverdure jp.lav...@gmail.com javascript: wrote: Hi Michael, I quite agree that child entities don't need their own copy of the changed attribute, but this is also the way that the version attribute is handled. (ie: both parent and child entities have their own copy of version) Is there any way we can fix the both of them ? As for the option to remove the changed attribute... Well, I'm the one who suggested its addition and submitted the pull request :) Thanks, JP On Friday, 17 October 2014 16:05:15 UTC-4, Michael Bayer wrote: On Oct 17, 2014, at 3:50 PM, JPLaverdure jp.lav...@gmail.com wrote: Hi Michael, My bad, they do indeed only show up on mapping... which takes place when my pyramid app instantiates. Sorry for the confusion :) Still, they could be unnerving for someone deploying the app. Any way to not have these show up ? I did look into version_meta.py and tried to make some tweaks when I saw anything having to do with the version atribute.. But to no avail. Your help is greatly appreciated ! it’s not clear why a class that inherits from another needs a separate “changed” column in any case. The recipe indicates on line 68 this column is optional so I’d remove it, or just make it conditional if “super_mapper” is not present to have it only on the base table. or maybe just map it differently, or not at all, down where it calls mapper(): m = mapper( versioned_cls, table, inherits=super_history_mapper, polymorphic_on=polymorphic_on, polymorphic_identity=local_mapper.polymorphic_identity, exclude_columns=[‘changed’] ) JP On Friday, 17 October 2014 14:52:22 UTC-4, JPLaverdure wrote: Hello, It seems a number of SAWarnings are being thrown whenever I instantiate Versioned objects which make use of inheritance: SAWarning: Implicitly combining column container_history.changed with column barcoded_container_history.changed under attribute 'changed'. Please configure one or more attributes for these same-named columns explicitly. prop = self._property_from_column(key, prop) Unfortunately, since these objects are instantiated auto-magically by the Versioned mixin class, I can't see a way to make these go away or address the issue. I tried looking into the history_meta.py source and cannot understand why this same warning is not being thrown for the version attribute. Anyone has an idea ? Thanks ! JP -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+...@googlegroups.com. To post to this group, send email to sqlal...@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/d/optout. -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+...@googlegroups.com javascript:. To post to this group, send email to sqlal...@googlegroups.com javascript:. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/d/optout. -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To post to this group, send email to sqlalchemy@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/d/optout.
Re: [sqlalchemy] Multi-Level inheritance and history_meta versioning issue
Hi Michael, Thanks for your response. Is release 0.9 stable enough to use in a production env ? When you mention that it isn't supported I'm a bit surprised/confused.. As such, the inheritance scheme has worked fine using 0.8 as long as I wan't dipping in the history of the objects. (_history is a necessary evil in my case, and to be frank, I tend to avoid going into it.. it's more of a last ditch security net) This is actually the first time I need to retrieve some data from the history layer of a 3rd inheritance level object. Anyhow, I'll certainly give the latest version a spin but remain nervous of the fact that it's still in beta. Will get back to you shortly. JP On Thursday, November 7, 2013 8:36:53 PM UTC-5, Michael Bayer wrote: try out r29a07fc09a6c11b3e05457e2a from git master or rel_0_9, I have multilevel joined inheritance working there now. On Nov 7, 2013, at 8:23 PM, Michael Bayer mik...@zzzcomputing.comjavascript: wrote: I can’t even get multi-level inheritance to set up the mappers correctly, it’s not supported right now. Would need some fixes. On Nov 7, 2013, at 11:38 AM, JPLaverdure jp.lav...@gmail.comjavascript: wrote: I seem to be having an issue when calling up the history of a versioned SQLAlchemy class. I have the following inheritance structure setup: Node(Versioned, Base) Specimen(Node) Animal(Specimen) If I attempt to fetch the animal history using the query generated by : AnimalHistory = self.__history_mapper__.class_ q = object_session(self).query(AnimalHistory).filter(AnimalHistory.id == self.id).order_by(AnimalHistory.version.desc()) logger.debug(q) I get the following query: SELECT bla bla #trimmed for brevity FROM node_history JOIN specimen_history ON node_history.id = specimen_history.id AND node_history.version = specimen_history.version JOIN animal_history ON specimen_history.id = animal_history.id WHERE animal_history.id = 28 ORDER BY animal_history.version DESC Basically, I seem to be missing the appropriate AND statement on the animal_history JOIN. Because of this, I get an unwanted cartesian product between animal and (specimen, node) Could anyone point out the modification needed inside history_meta.py in order to fix this ? Thanks !! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+...@googlegroups.com javascript:. To post to this group, send email to sqlal...@googlegroups.comjavascript: . Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/groups/opt_out. -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To post to this group, send email to sqlalchemy@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/groups/opt_out.
Re: [sqlalchemy] Multi-Level inheritance and history_meta versioning issue
Hey Michael, Tried out the new version and the _history now functions as it should :) Many thanks ! Also: over time, I had added an extra field to the _history tables corresponding to the modification datetime (as a timestamp), along with an extra param in the table creation call to support the presence of schemas (I mainly work on postgresql). Maybe those could be included in the main distro ? I'll submit a pull request with those changes in case you deem them interesting. Cheers ! JP On Friday, November 8, 2013 9:52:13 AM UTC-5, JPLaverdure wrote: Hi Michael, Thanks for your response. Is release 0.9 stable enough to use in a production env ? When you mention that it isn't supported I'm a bit surprised/confused.. As such, the inheritance scheme has worked fine using 0.8 as long as I wan't dipping in the history of the objects. (_history is a necessary evil in my case, and to be frank, I tend to avoid going into it.. it's more of a last ditch security net) This is actually the first time I need to retrieve some data from the history layer of a 3rd inheritance level object. Anyhow, I'll certainly give the latest version a spin but remain nervous of the fact that it's still in beta. Will get back to you shortly. JP On Thursday, November 7, 2013 8:36:53 PM UTC-5, Michael Bayer wrote: try out r29a07fc09a6c11b3e05457e2a from git master or rel_0_9, I have multilevel joined inheritance working there now. On Nov 7, 2013, at 8:23 PM, Michael Bayer mik...@zzzcomputing.com wrote: I can’t even get multi-level inheritance to set up the mappers correctly, it’s not supported right now. Would need some fixes. On Nov 7, 2013, at 11:38 AM, JPLaverdure jp.lav...@gmail.com wrote: I seem to be having an issue when calling up the history of a versioned SQLAlchemy class. I have the following inheritance structure setup: Node(Versioned, Base) Specimen(Node) Animal(Specimen) If I attempt to fetch the animal history using the query generated by : AnimalHistory = self.__history_mapper__.class_ q = object_session(self).query(AnimalHistory).filter(AnimalHistory.id == self.id).order_by(AnimalHistory.version.desc()) logger.debug(q) I get the following query: SELECT bla bla #trimmed for brevity FROM node_history JOIN specimen_history ON node_history.id = specimen_history.id AND node_history.version = specimen_history.version JOIN animal_history ON specimen_history.id = animal_history.id WHERE animal_history.id = 28 ORDER BY animal_history.version DESC Basically, I seem to be missing the appropriate AND statement on the animal_history JOIN. Because of this, I get an unwanted cartesian product between animal and (specimen, node) Could anyone point out the modification needed inside history_meta.py in order to fix this ? Thanks !! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+...@googlegroups.com. To post to this group, send email to sqlal...@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/groups/opt_out. -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To post to this group, send email to sqlalchemy@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/groups/opt_out.
[sqlalchemy] Multi-Level inheritance and history_meta versioning issue
I seem to be having an issue when calling up the history of a versioned SQLAlchemy class. I have the following inheritance structure setup: Node(Versioned, Base) Specimen(Node) Animal(Specimen) If I attempt to fetch the animal history using the query generated by : AnimalHistory = self.__history_mapper__.class_ q = object_session(self).query(AnimalHistory).filter(AnimalHistory.id == self.id).order_by(AnimalHistory.version.desc()) logger.debug(q) I get the following query: SELECT bla bla #trimmed for brevity FROM node_history JOIN specimen_history ON node_history.id = specimen_history.id AND node_history.version = specimen_history.version JOIN animal_history ON specimen_history.id = animal_history.id WHERE animal_history.id = 28 ORDER BY animal_history.version DESC Basically, I seem to be missing the appropriate AND statement on the animal_history JOIN. Because of this, I get an unwanted cartesian product between animal and (specimen, node) Could anyone point out the modification needed inside history_meta.py in order to fix this ? Thanks !! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To unsubscribe from this group and stop receiving emails from it, send an email to sqlalchemy+unsubscr...@googlegroups.com. To post to this group, send email to sqlalchemy@googlegroups.com. Visit this group at http://groups.google.com/group/sqlalchemy. For more options, visit https://groups.google.com/groups/opt_out.
[sqlalchemy] ConcreteBase (0.7.3) only supporting 1 level of inheritance ?
Hello, I started playing with Concrete Table Inheritance this morning and tried to implement a portion of my schema: class Mixin(object): __table_args__ = {'schema':'test'} id = Column(Integer, primary_key=True) class Node(ConcreteBase, Base, Mixin): __tablename__ = 'node' __mapper_args__ = {'polymorphic_identity':'node', 'concrete':True} class Sample(Node, Mixin): __tablename__ = 'sample' __mapper_args__ = {'polymorphic_identity':'sample', 'concrete':True} class DNA(Sample, Mixin): __tablename__ = 'dna' __mapper_args__ = {'polymorphic_identity':'dna', 'concrete':True} token = Column(String(128), nullable=False) qty = Column(Integer, nullable=False) comments = Column(String(256)) def __init__(self, token, qty, comments=None): self.token = token self.qty = qty self.comments = comments def __repr__(self): return Sample(%s, %s, Qty: %s) % (self.id, self.token, self.qty) class RNA(Sample, Mixin): __tablename__ = 'rna' __mapper_args__ = {'polymorphic_identity':'rna', 'concrete':True} token = Column(String(128), nullable=False) qty = Column(Integer, nullable=False) comments = Column(String(256)) def __init__(self, token, qty, comments=None): self.token = token self.qty = qty self.comments = comments def __repr__(self): return RNA(%s, %s, Qty: %s) % (self.id, self.token, self.qty) But after inserting some DNA and RNA entities... It seems that: session.query(Node).all() returns an empty list whereas: session.query(Sample).all() returns a polymorphic list of RNAs and DNAs... Am I missing something ? Also: If I declare Node as per: class Node(AbstractConcreteBase, Base): pass Instead of above, I get the following error: assert mapper is mapper.base_mapper AssertionError In a perfect world, I would have both Node and Sample as abstract classes but I can't seem to get that going.. Any pointers ? Thanks ! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/xojj7cGtMqcJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
Re: [sqlalchemy] ConcreteBase (0.7.3) only supporting 1 level of inheritance ?
Hello Michael, Sorry to be the thorn in your side.. I attached a test case as requested.. Ticket 2312. Also, it seems this is incompatible with history_meta based versioning. (Which probably has to do with the use of the __declare_last__() function. Thank you -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/JhizOFgIq_QJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
Re: [sqlalchemy] Versioning and Foreign Keys
Hi Michael, Thanks for your reply... Your input is always very resourcefull, thanks ! I put together a small example which doesn't seem to function as expected: class Sample(Base): __metaclass__ = VersionedMeta __tablename__ = 'sample' __table_args__ = {'schema':'test'} id = Column(Integer, primary_key=True) token = Column(String(64)) box_id = Column(Integer, ForeignKey('test.box.id', onupdate='cascade', ondelete='cascade'), nullable=False) def __init__(self, token, box): self.token = token self.box = box class Container(Base): __metaclass__ = VersionedMeta __tablename__ = 'container' __table_args__ = {'schema':'test'} id = Column(Integer, primary_key=True) discriminator = Column('type', String(64)) token = Column(String(128), nullable=False) description = Column(String) __mapper_args__ = {'polymorphic_on': discriminator, 'polymorphic_identity':'container'} def __init__(self, token, description=''): self.token = token self.description = description class Box(Container): __tablename__ = 'box' __table_args__ = {'schema':'test'} __mapper_args__ = {'polymorphic_identity': 'box'} id = Column(Integer, ForeignKey('test.container.id', onupdate=cascade, ondelete=cascade), primary_key=True) barcode = Column(String(64)) samples = relationship('Sample', backref='box') def __init__(self, token, description='', barcode=''): super(Box, self).__init__(token, description) self.barcode = barcode Base.metadata.drop_all() Base.metadata.create_all() Session = scoped_session(sessionmaker(extension=VersionedListener())) sess = Session() b = Box('Big box', 'sample1') sess.add(b) s = Sample('New sample', b) sess.add(s) sess.commit() sess.delete(b) sess.commit() This fails because of the nullable=False clause on the Sample foreign key as SQLA seems to try to update the sample to set box_id to null... console printout: (from the delete portion) 2011-09-20 11:41:51,021 INFO sqlalchemy.engine.base.Engine BEGIN (implicit) 2011-09-20 11:41:51,022 INFO sqlalchemy.engine.base.Engine SELECT test.container.type AS test_container_type, test.box.id AS test_box_id, test.container.id AS test_container_id, test.container.token AS test_container_token, test.container.description AS test_container_description, test.container.version AS test_container_version, test.box.barcode AS test_box_barcode FROM test.container JOIN test.box ON test.container.id = test.box.id WHERE test.container.id = %(param_1)s 2011-09-20 11:41:51,023 INFO sqlalchemy.engine.base.Engine {'param_1': 1} 2011-09-20 11:41:51,025 INFO sqlalchemy.engine.base.Engine SELECT test.sample.id AS test_sample_id, test.sample.token AS test_sample_token, test.sample.box_id AS test_sample_box_id, test.sample.version AS test_sample_version FROM test.sample WHERE %(param_1)s = test.sample.box_id 2011-09-20 11:41:51,025 INFO sqlalchemy.engine.base.Engine {'param_1': 1} 2011-09-20 11:41:51,028 INFO sqlalchemy.engine.base.Engine INSERT INTO test.container_history (id, type, token, description, version) VALUES (%(id)s, %(type)s, %(token)s, %(description)s, %(version)s) 2011-09-20 11:41:51,028 INFO sqlalchemy.engine.base.Engine {'token': u'Big box', 'version': 1, 'type': u'box', 'id': 1, 'description': u'sample1'} 2011-09-20 11:41:51,029 INFO sqlalchemy.engine.base.Engine INSERT INTO test.box_history (id, barcode, version) VALUES (%(id)s, %(barcode)s, %(version)s) 2011-09-20 11:41:51,029 INFO sqlalchemy.engine.base.Engine {'barcode': u'', 'id': 1, 'version': 1} 2011-09-20 11:41:51,031 INFO sqlalchemy.engine.base.Engine UPDATE test.sample SET box_id=%(box_id)s WHERE test.sample.id = %(test_sample_id)s 2011-09-20 11:41:51,031 INFO sqlalchemy.engine.base.Engine {'box_id': None, 'test_sample_id': 1} 2011-09-20 11:41:51,032 INFO sqlalchemy.engine.base.Engine ROLLBACK So it does indeed seem to visit the sample, but I must be doing something wrong in my declaration because SQLA should be attempting to delete the sample not update it ! Thanks -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/XAPy4uSlJAMJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
Re: [sqlalchemy] Versioning and Foreign Keys
Oh god... I thought the statements used when declaring the ForeignKey (ondelete, onupdate) would imply that the relationship function in the same manner. I didn't think the 2 would be decoupled so much.. Although now that you point it out, it does seem consistent. I guess when I thought the children where deleted but not saved in _history, I did not have the nullable=False statement on the foreign key and when they did not show up in the _history table, didn't think of looking back in the children's table to realise they had not been deleted. Sorry for the trouble... Seems like I owe you a beer or two now. JP -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/JOR1NVrg2bYJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
[sqlalchemy] Versioning and Foreign Keys
Hello, I'm using the versioned objects suggested in the SQLAlchemy examples: http://www.sqlalchemy.org/docs/orm/examples.html#versioned-objects One of the aspects of entity management seems a bit weird though: If entities are linked using foreign keys, (let's say in one-to-many relationship), deleting the parent will indeed delete the children (because of the on delete cascade clause) but the last state of the children will NOT be saved in the _history table of the children So I basically lose the last state of the children. ie: the parent _history is saved but none of the children are. I of course solved this by running a delete on all children prior to deleting the parent but as my model grows in complexity, I would sure love for all of this to be done automagically. in other words for versioned_meta to follow foreign keys and mark and linked entities them as modified as well. I might be doing something wrong or this might be specific to postgresql... But I don't think that's the case... What would I need to modify in versioned_meta to allow for this ? Is it even possible ? Thanks ! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/S-Qf8WjS08IJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
[sqlalchemy] Re: Versioning and Foreign Keys
Oops, above references to versioned_meta should read history_meta. Sorry -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/0ZtFX94qz_wJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
Re: [sqlalchemy] Re: Versioning and multi-level inheritance
Hi Michael, Thank you for your reply. Unfortunately, the mistake was all mine... At some point (and for an obscure reason...), I had stopped using the VersionedListener so changes were no longer registering in the DB :-/ So sorry ! JP -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/WhQyp4AmxWsJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
[sqlalchemy] Re: Querying specific class using String name of class
Hi Mike, Thanks for the reply. I'm just not sure that using `eval` represents a cleaner way than my original code... The Class query options are specified by the end user through a select (html form) so using eval poses a security risk I would like to avoid. I was hoping slqalchemy would give me a clean way to access mapped objects using a String as Identifier. Like a getter of some kind. JP -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/JPo9YefjDXgJ. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
[sqlalchemy] Querying specific class using String name of class
Hello, Is there a proper way to retrieve a class using its name other than going through the _decl_class_registry dictionary of declarative_base ? I'm using the Joined Table Inheritance and would like to enable users to query specific subtypes. ie: if I have the following structure: Base = declarative_base() class Sample(Base): bla class Tissue(Sample): bla class DNA(Sample): bla I would like to build a query using 'DNA' as class type... session.query('DNA').all() But this doesn't work so the solution I found is the following: session.query(Base._decl_class_registry['DNA']) Is this the only way to go or is there a cleaner way to obtain a class based on its String name ? Thanks ! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To view this discussion on the web visit https://groups.google.com/d/msg/sqlalchemy/-/wL8psJb1Jp4J. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
[sqlalchemy] Versioning and multi-level inheritance
Hello, I'm trying to use the versioning recipe describe on the website along with a multi-level inheritance model (Joined-Table inheritance) Here are my declarative statements: [code] class Sample(Base): __metaclass__ = VersionedMeta __tablename__ = 'sample' __table_args__ = {'schema': 'test'} id = Column(Integer, primary_key=True) discriminator = Column('type', String(50)) token = Column(String(128), nullable=False) source_sample_id = Column(Integer, ForeignKey('test.sample.id')) children = relationship(Sample, backref=backref('source_sample', remote_side=id), single_parent=True) __mapper_args__ = {'polymorphic_on': discriminator, 'polymorphic_identity':'sample'} def __init__(self, token, source_sample_id=None): self.token = token self.source_sample_id = source_sample_id class Tissue(Sample): __metaclass__ = VersionedMeta __tablename__ = 'tissue' __mapper_args__ = {'polymorphic_identity': 'tissue'} __table_args__ = {'schema': 'test'} id = Column(Integer, ForeignKey('test.sample.id'), primary_key=True) concentration = Column(String(32)) def __init__(self, token, concentration, source_sample_id=None): super(Sample, self).__init__(token, source_sample_id) self.concentration = concentration class LeukemicTissue(Tissue): __metaclass__ = VersionedMeta __tablename__ = 'leukemic_tissue' __mapper_args__ = {'polymorphic_identity': 'leukemic_tissue'} __table_args__ = {'schema': 'test'} id = Column(Integer, ForeignKey('test.tissue.id'), primary_key=True) leukemia = Column(String) def __init__(self, token, concentration, leukemia, source_sample_id=None): super(Tissue, self).__init__(token, concentration, source_sample_id) self.leukemia = leukemia [/code] Whenever I try to create_all() I get the following error: sqlalchemy.exc.ArgumentError: Can't find any foreign key relationships between 'tissue_history' and 'leucegene_tissue_history'. Single level-inheritance works beautifully (ie if I stop at Tissue and don't declare the LeukemicTissue) but I really need a multi- level inheritance scheme to work.. Can anyone give me any pointers ? Thanks !! -- You received this message because you are subscribed to the Google Groups sqlalchemy group. To post to this group, send email to sqlalchemy@googlegroups.com. To unsubscribe from this group, send email to sqlalchemy+unsubscr...@googlegroups.com. For more options, visit this group at http://groups.google.com/group/sqlalchemy?hl=en.