On Tuesday, September 18, 2012 8:41:15 PM UTC-7, Michael Bayer wrote: > > > On Sep 18, 2012, at 8:04 PM, Gerald Thibault wrote: > > > before_insert() is not generally necessary, people frequently want to take > advantage of the fact that it provides a built-in iteration of objects to > be inserted, but this iteration can be done for the purposes of affecting > the flush plan ahead of time within the before_flush() event, by iterating > session.new. An object detected at this stage can be omitted from the > insert by calling session.expunge(obj). >
This did the trick. This is the current working event listener: @event.listens_for(orm.sessionmaker(), 'before_flush') def normalize_phonenumbers(session, flush_context, instances): for obj in session.new: if isinstance(obj, Phone): if obj.location: # we already have the location in the session country = obj.location.country else: country = session.query(Location) \ .get(obj.location_id) \ .country try: number = phonenumbers.parse(obj.number, country) obj.number = phonenumbers.format_number(number, phonenumbers.PhoneNumberFormat.E164) except: session.expunge(obj) I have one more question. When I do the following: test = BusinessPhone(type='fax', number='2068857529', location_id=1) session.add(test) session.commit() At what point is the 'location' relationship populated? I tried this and it failed on this line, due to the relation not being populated: country = obj.location.country which necessitated adding the conditional manual load of Location. Am I handling this in an appropriate way? On Tuesday, September 18, 2012 4:29:43 PM UTC-7, Michael Bayer wrote: > >> On Sep 18, 2012, at 6:28 PM, Gerald Thibault wrote: >> >> > I am working with 2 models, a "Location" model, and a "Phone" model. >> There is a one-to-many relationship between them. >> > >> > When a phone number is submitted, I need to format it using the >> phonenumbers modules, which requires a country code, which exists on the >> Location object. So the formatting can only happen after the flush(), as I >> need to have the location_id populated, so I can grab the country code from >> the parent Location. If the formatting of the phone number fails, I want >> the entire object eliminated and not written to the db. >> >> At some point, the Phone is being associated with a Location object in >> memory, and this would be independent of whether or not location_id is >> present. The location_id can only be set, assuming this is >> relationship() mechanics, if this is the case. So you shouldn't need a >> flush() for this to happen, and you can perform this validation before a >> flush plan is established. >> >> Otherwise if location_id is populated by some other means, that would >> point to an area where you'd want to get Location objects present in memory >> ahead of time, rather than relying upon primary keys alone. >> >> This might not be enough to solve your issue so feel free to add some >> detail how location_id is coming into being here, such that the Location >> isn't nearby. >> >> >> > -- > 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/-/mElFMIjDpsEJ. > To post to this group, send email to sqlal...@googlegroups.com<javascript:> > . > To unsubscribe from this group, send email to > sqlalchemy+...@googlegroups.com <javascript:>. > For more options, visit this group at > http://groups.google.com/group/sqlalchemy?hl=en. > > > -- 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/-/HJPIjS4Y_vkJ. 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.