def configurable_mappings(kls): """Add mappings, as per configured features for a domain type. """ name = kls.__name__ # auditable if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) change_tbl = getattr(schema, "%s_changes" % (schema.un_camel(name))) def changes_properties(change_tbl): return {"user": relation(domain.User, primaryjoin=(change_tbl.c.user_id == schema.users.c.user_id), uselist=False, lazy=True ), } mapper(change_kls, change_tbl, properties=changes_properties(change_tbl) ) # versionable if interfaces.IVersionable.implementedBy(kls): assert change_kls, "May not be IVersionable and not IAuditable" version_kls = getattr(domain, "%sVersion" % (name)) version_tbl = getattr(schema, "%s_versions" % (schema.un_camel(name))) def versions_properties(item_class, change_class, versions_table): props = { "change": relation(change_class, uselist=False), "head": relation(item_class, uselist=False) } # Notes: # - domain.AttachedFile is the only versionable type that is # not a ParliamentaryItem. # - !+IVersionable(mr, jul-2011) an AttachedFile does not have # attached_files; but, this violates the meaning of IVersionable? # Or, the ability to have attached_files should be independent of # being versionable? IMayAttachFiles if item_class is not domain.AttachedFile: props["attached_files"] = relation(domain.AttachedFileVersion, primaryjoin=rdb.and_( versions_table.c.content_id == schema.attached_file_versions.c.item_id, versions_table.c.version_id == schema.attached_file_versions.c.file_version_id ), foreign_keys=[ schema.attached_file_versions.c.item_id, schema.attached_file_versions.c.file_version_id ] ) return props mapper(version_kls, version_tbl, properties=versions_properties(kls, change_kls, version_tbl) )
def configurable_mappings(kls): """Add mappings, as per configured features for a domain type. Executed on adapters.load_workflow() """ name = kls.__name__ # auditable, determine properties and set mapper for change class/table if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) change_tbl = getattr(schema, "%s_changes" % (schema.un_camel(name))) def changes_properties(item_class, change_tbl): return { "user": relation(domain.User, primaryjoin=( change_tbl.c.user_id == schema.users.c.user_id), uselist=False, lazy=True), "head": relation(item_class, uselist=False) } mapper(change_kls, change_tbl, properties=changes_properties(kls, change_tbl)) # versionable, determine properties and set mapper for version class/table if interfaces.IVersionable.implementedBy(kls): assert change_kls, "May not be IVersionable and not IAuditable" version_kls = getattr(domain, "%sVersion" % (name)) version_tbl = getattr(schema, "%s_versions" % (schema.un_camel(name))) def versions_properties(item_class, change_class, versions_table): props = { "change": relation(change_class, uselist=False), "head": relation(item_class, uselist=False) } return props mapper(version_kls, version_tbl, properties=versions_properties(kls, change_kls, version_tbl)) # attachmentable, add related properties to version class/table if interfaces.IAttachmentable.implementedBy(kls): # !+ current constrain assert version_kls, "May not be IAttachmentable and not IVersionable" class_mapper(version_kls).add_property( "attached_files", relation(domain.AttachedFileVersion, primaryjoin=rdb.and_( version_tbl.c.content_id == schema.attached_file_versions.c.item_id, version_tbl.c.version_id == schema.attached_file_versions.c.file_version_id), foreign_keys=[ schema.attached_file_versions.c.item_id, schema.attached_file_versions.c.file_version_id ])) # finally, add any properties to the master kls itself def mapper_add_configurable_properties(kls): kls_mapper = class_mapper(kls) def configurable_properties(kls, mapper_properties): """Add properties, as per configured features for a domain type. """ # auditable if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) mapper_properties["changes"] = relation( change_kls, backref="origin", # !+HEAD_DOCUMENT_ITEM(mr, nov-2011) head? lazy=True, cascade="all, delete-orphan", passive_deletes=False) # versionable if interfaces.IVersionable.implementedBy(kls): kls.versions = one2many( "versions", "bungeni.models.domain.%sVersionContainer" % (name), "content_id") # attachmentable if interfaces.IAttachmentable.implementedBy(kls): pass # nothing to do return mapper_properties for key, prop in configurable_properties(kls, {}).items(): kls_mapper.add_property(key, prop) # mapper_add_configurable_properties(kls)
def configurable_mappings(kls, kls_mapper=None): """Add mappings, as per configured features for a domain type. !+kls_mapper(mr, jul-2011) when called at time of loading this module i.e. mappers are in the process of being defined, cannot seem to retrieve the mapper with class_mapper(kls), so as workaround am passing the newly created mapper instance; calling this downstream does not require to specify the mapper instance as it is retrievable with class_mapper(kls). """ name = kls.__name__ # auditable, determine properties and set mapper for change class/table if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) change_tbl = getattr(schema, "%s_changes" % (schema.un_camel(name))) def changes_properties(change_tbl): return {"user": relation(domain.User, primaryjoin=(change_tbl.c.user_id == schema.users.c.user_id), uselist=False, lazy=True ), } mapper(change_kls, change_tbl, properties=changes_properties(change_tbl) ) # versionable,determine properties and set mapper for change class/table if interfaces.IVersionable.implementedBy(kls): assert change_kls, "May not be IVersionable and not IAuditable" version_kls = getattr(domain, "%sVersion" % (name)) version_tbl = getattr(schema, "%s_versions" % (schema.un_camel(name))) def versions_properties(item_class, change_class, versions_table): props = { "change": relation(change_class, uselist=False), "head": relation(item_class, uselist=False) } # Notes: # - domain.AttachedFile is the only versionable type that is # not a ParliamentaryItem. # - !+IVersionable(mr, jul-2011) an AttachedFile does not have # attached_files; but, this violates the meaning of IVersionable? # Or, the ability to have attached_files should be independent of # being versionable? IMayAttachFiles if item_class is not domain.AttachedFile: props["attached_files"] = relation(domain.AttachedFileVersion, primaryjoin=rdb.and_( versions_table.c.content_id == schema.attached_file_versions.c.item_id, versions_table.c.version_id == schema.attached_file_versions.c.file_version_id ), foreign_keys=[ schema.attached_file_versions.c.item_id, schema.attached_file_versions.c.file_version_id ] ) return props mapper(version_kls, version_tbl, properties=versions_properties(kls, change_kls, version_tbl) ) # finally, add any properties to the master kls itself def mapper_add_configurable_properties(kls, kls_mapper): def configurable_properties(kls, mapper_properties): """Add properties, as per configured features for a domain type. """ # auditable if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) mapper_properties["changes"] = relation(change_kls, backref="origin", lazy=True, cascade="all, delete-orphan", passive_deletes=False ) # versionable if interfaces.IVersionable.implementedBy(kls): kls.versions = one2many("versions", "bungeni.models.domain.%sVersionContainer" % (name), "content_id") return mapper_properties for key, prop in configurable_properties(kls, {}).items(): kls_mapper.add_property(key, prop) # !+kls_mapper if kls_mapper is None: from sqlalchemy.orm import class_mapper kls_mapper = class_mapper(kls) mapper_add_configurable_properties(kls, kls_mapper)
def configurable_mappings(kls, kls_mapper=None): """Add mappings, as per configured features for a domain type. !+kls_mapper(mr, jul-2011) when called at time of loading this module i.e. mappers are in the process of being defined, cannot seem to retrieve the mapper with class_mapper(kls), so as workaround am passing the newly created mapper instance; calling this downstream does not require to specify the mapper instance as it is retrievable with class_mapper(kls). """ name = kls.__name__ # auditable, determine properties and set mapper for change class/table if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) change_tbl = getattr(schema, "%s_changes" % (schema.un_camel(name))) def changes_properties(change_tbl): return { "user": relation( domain.User, primaryjoin=(change_tbl.c.user_id == schema.users.c.user_id), uselist=False, lazy=True ) } mapper(change_kls, change_tbl, properties=changes_properties(change_tbl)) # versionable,determine properties and set mapper for change class/table if interfaces.IVersionable.implementedBy(kls): assert change_kls, "May not be IVersionable and not IAuditable" version_kls = getattr(domain, "%sVersion" % (name)) version_tbl = getattr(schema, "%s_versions" % (schema.un_camel(name))) def versions_properties(item_class, change_class, versions_table): props = {"change": relation(change_class, uselist=False), "head": relation(item_class, uselist=False)} # Notes: # - domain.AttachedFile is the only versionable type that is # not a ParliamentaryItem. # - !+IVersionable(mr, jul-2011) an AttachedFile does not have # attached_files; but, this violates the meaning of IVersionable? # Or, the ability to have attached_files should be independent of # being versionable? IMayAttachFiles if item_class is not domain.AttachedFile: props["attached_files"] = relation( domain.AttachedFileVersion, primaryjoin=rdb.and_( versions_table.c.content_id == schema.attached_file_versions.c.item_id, versions_table.c.version_id == schema.attached_file_versions.c.file_version_id, ), foreign_keys=[ schema.attached_file_versions.c.item_id, schema.attached_file_versions.c.file_version_id, ], ) return props mapper(version_kls, version_tbl, properties=versions_properties(kls, change_kls, version_tbl)) # finally, add any properties to the master kls itself def mapper_add_configurable_properties(kls, kls_mapper): def configurable_properties(kls, mapper_properties): """Add properties, as per configured features for a domain type. """ # auditable if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) mapper_properties["changes"] = relation( change_kls, backref="origin", lazy=False, cascade="all, delete-orphan", passive_deletes=False ) # versionable if interfaces.IVersionable.implementedBy(kls): kls.versions = one2many("versions", "bungeni.models.domain.%sVersionContainer" % (name), "content_id") return mapper_properties for key, prop in configurable_properties(kls, {}).items(): kls_mapper.add_property(key, prop) # !+kls_mapper if kls_mapper is None: from sqlalchemy.orm import class_mapper kls_mapper = class_mapper(kls) mapper_add_configurable_properties(kls, kls_mapper)
def configurable_mappings(kls): """Add mappings, as per configured features for a domain type. Executed on adapters.load_workflow() """ name = kls.__name__ # auditable, determine properties and set mapper for change class/table if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) change_tbl = getattr(schema, "%s_changes" % (schema.un_camel(name))) def changes_properties(change_tbl): return { "user": relation(domain.User, primaryjoin=(change_tbl.c.user_id == schema.users.c.user_id), uselist=False, lazy=True ), } mapper(change_kls, change_tbl, properties=changes_properties(change_tbl) ) # versionable, determine properties and set mapper for version class/table if interfaces.IVersionable.implementedBy(kls): assert change_kls, "May not be IVersionable and not IAuditable" version_kls = getattr(domain, "%sVersion" % (name)) version_tbl = getattr(schema, "%s_versions" % (schema.un_camel(name))) def versions_properties(item_class, change_class, versions_table): props = { "change": relation(change_class, uselist=False), "head": relation(item_class, uselist=False) } return props mapper(version_kls, version_tbl, properties=versions_properties(kls, change_kls, version_tbl) ) # attachmentable, add related properties to version class/table if interfaces.IAttachmentable.implementedBy(kls): # !+ current constrain assert version_kls, "May not be IAttachmentable and not IVersionable" class_mapper(version_kls).add_property("attached_files", relation(domain.AttachedFileVersion, primaryjoin=rdb.and_( version_tbl.c.content_id == schema.attached_file_versions.c.item_id, version_tbl.c.version_id == schema.attached_file_versions.c.file_version_id ), foreign_keys=[ schema.attached_file_versions.c.item_id, schema.attached_file_versions.c.file_version_id ] ) ) # finally, add any properties to the master kls itself def mapper_add_configurable_properties(kls): kls_mapper = class_mapper(kls) def configurable_properties(kls, mapper_properties): """Add properties, as per configured features for a domain type. """ # auditable if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) mapper_properties["changes"] = relation(change_kls, backref="origin", lazy=True, cascade="all, delete-orphan", passive_deletes=False ) # versionable if interfaces.IVersionable.implementedBy(kls): kls.versions = one2many("versions", "bungeni.models.domain.%sVersionContainer" % (name), "content_id") # attachmentable if interfaces.IAttachmentable.implementedBy(kls): pass # nothing to do return mapper_properties for key, prop in configurable_properties(kls, {}).items(): kls_mapper.add_property(key, prop) # mapper_add_configurable_properties(kls)
def configurable_mappings(kls): """Add mappings, as per configured features for a domain type. Executed on adapters.load_workflow() """ name = kls.__name__ # auditable, determine properties and set mapper for change class/table if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) change_tbl = getattr(schema, "%s_changes" % (schema.un_camel(name))) def changes_properties(change_tbl): return { "user": relation(domain.User, primaryjoin=(change_tbl.c.user_id == schema.users.c.user_id), uselist=False, lazy=True ), } mapper(change_kls, change_tbl, properties=changes_properties(change_tbl) ) # versionable,determine properties and set mapper for change class/table if interfaces.IVersionable.implementedBy(kls): assert change_kls, "May not be IVersionable and not IAuditable" version_kls = getattr(domain, "%sVersion" % (name)) version_tbl = getattr(schema, "%s_versions" % (schema.un_camel(name))) def versions_properties(item_class, change_class, versions_table): props = { "change": relation(change_class, uselist=False), "head": relation(item_class, uselist=False) } # Notes: # - domain.AttachedFile is the only versionable type that is # not a ParliamentaryItem. # - !+IVersionable(mr, jul-2011) an AttachedFile does not have # attached_files; but, this violates the meaning of IVersionable? # Or, the ability to have attached_files should be independent of # being versionable? IMayAttachFiles if item_class is not domain.AttachedFile: props["attached_files"] = relation(domain.AttachedFileVersion, primaryjoin=rdb.and_( versions_table.c.content_id == schema.attached_file_versions.c.item_id, versions_table.c.version_id == schema.attached_file_versions.c.file_version_id ), foreign_keys=[ schema.attached_file_versions.c.item_id, schema.attached_file_versions.c.file_version_id ] ) return props mapper(version_kls, version_tbl, properties=versions_properties(kls, change_kls, version_tbl) ) # finally, add any properties to the master kls itself def mapper_add_configurable_properties(kls, kls_mapper): def configurable_properties(kls, mapper_properties): """Add properties, as per configured features for a domain type. """ # auditable if interfaces.IAuditable.implementedBy(kls): change_kls = getattr(domain, "%sChange" % (name)) mapper_properties["changes"] = relation(change_kls, backref="origin", lazy=True, cascade="all, delete-orphan", passive_deletes=False ) # versionable if interfaces.IVersionable.implementedBy(kls): kls.versions = one2many("versions", "bungeni.models.domain.%sVersionContainer" % (name), "content_id") return mapper_properties for key, prop in configurable_properties(kls, {}).items(): kls_mapper.add_property(key, prop) mapper_add_configurable_properties(kls, class_mapper(kls))