def initConnections(site, event): # this is called on first Plone traverse portal_quickinstaller = getToolByName(site, 'portal_quickinstaller') if portal_quickinstaller.isProductInstalled('collective.behavior.sql'): if not getAllUtilitiesRegisteredFor(ISQLConnectionsUtility): ftis = [ a for a in getAllUtilitiesRegisteredFor(IDexterityFTI) if 'collective.behavior.sql.behavior.behaviors.ISQLContent' in a.behaviors and getattr(a, 'sql_table', None) ] if ftis: for fti in ftis: if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) try: initConnectionForFTI(fti) except: LOG.error('Unable to init connection for %s' % (fti.id)) gsm = getGlobalSiteManager() gsm.registerUtility(SQLConnectionsUtility(), ISQLConnectionsUtility) else: gsm = getGlobalSiteManager() gsm.registerUtility(SQLConnectionsUtility(), ISQLConnectionsUtility)
def __call__(self, context): # we take the fti type settings to get the selected connections and table if ISQLTypeSchemaContext.providedBy(context): context = ISQLTypeSettings(context.fti) elif IField.providedBy(context): context = ISQLTypeSettings(aq_parent(context.context).fti) urls = ISQLAlchemyConnectionStrings( component.getUtility(ISiteRoot)).values() if not getattr(context, 'sql_connection', None) or not getattr( context, 'sql_table', None): return SimpleVocabulary([]) columns = [] if not ISQLTypeSettings.providedBy(context): context = ISQLTypeSettings(context) sql_url = context.sql_url sql_table = context.sql_table engine = create_engine(sql_url) insp = reflection.Inspector.from_engine(engine) columns = insp.get_columns(sql_table) columns.sort(lambda x, y: cmp(x.get('name'), y.get('name'))) items = [ SimpleTerm(a.get('name'), a.get('name'), a.get('name') + ' (' + str(a.get('type')) + ')') for a in columns if a.get('name') and 'TIMESTAMP' in str(a.get('type')) ] return SimpleVocabulary(items)
def __call__(self, context): if not getattr(context, 'sql_connection', None): return SimpleVocabulary([]) urls = ISQLAlchemyConnectionStrings( component.getUtility(ISiteRoot)).values() if not urls: return SimpleVocabulary([]) tables = [] if ISQLTypeSchemaContext.providedBy(context): context = ISQLTypeSettings(context.fti) if not ISQLTypeSettings.providedBy(context): context = ISQLTypeSettings(context) sql_url = context.sql_url and context.sql_url or urls[0] engine = create_engine(sql_url) # Base = declarative_base(bind=engine) insp = reflection.Inspector.from_engine(engine) tables = insp.get_table_names() views = insp.get_view_names() # conn = Base.metadata.bind.contextual_connect(close_with_result=True) # table_names = Base.metadata.bind.engine.table_names([], connection=conn) items = [ SimpleTerm(name, name, name + ' (table)') for name in sorted(list(set(tables))) if name ] items += [ SimpleTerm(name, name, name + ' (view)') for name in sorted(list(set(views))) if name and name not in list(tables) ] return SimpleVocabulary(items)
def __call__(self, context): # we take the fti type settings to get the selected connections and table if ISQLTypeSchemaContext.providedBy(context): context = ISQLTypeSettings(context.fti) elif IField.providedBy(context): context = ISQLTypeSettings(aq_parent(context.context).fti) urls = ISQLAlchemyConnectionStrings(component.getUtility(ISiteRoot)).values() if not getattr(context, 'sql_table', None): return SimpleVocabulary([]) items = [] connection = queryUtility(ISQLConnectionsUtility, name=context.id, default=None) if not connection: connection = registerConnectionUtilityForFTI(context.context) columns = [] for a in inspect(connection.tableClass).columns: if a.name: items.append(SimpleTerm(a.name, a.name, a.name+' ('+str(a.type)+')')) columns.append(a.name) for a in getattr(inspect(connection.tableClass), 'relationships', []): if a.key in columns: continue items.append(SimpleTerm(a.key, a.key, a.key+' (Relation)')) for b in inspect(a.table).columns: if b.name: items.append(SimpleTerm(a.key+'.'+b.name, a.key+'.'+b.name, a.key+'.'+b.name+' ('+str(b.type)+')')) columns.append(a.key+'.'+b.name) # for b in getattr(inspect(connection.tableClass), 'relationships', []): # if a.key+'.'+b.key in columns: # continue # items.append(SimpleTerm(a.key+'.'+b.key, a.key+'.'+b.key, a.key+'.'+b.key+' (Relation)')) items.sort( lambda x, y: cmp(x.value, y.value ) ) return SimpleVocabulary(items)
def __call__(self, context): # we take the fti type settings to get the selected connections and table if ISQLTypeSchemaContext.providedBy(context): context = ISQLTypeSettings(context.fti) elif IField.providedBy(context): context = ISQLTypeSettings(aq_parent(context.context).fti) urls = ISQLAlchemyConnectionStrings(component.getUtility(ISiteRoot)).values() if not getattr(context, 'sql_table', None): return SimpleVocabulary([]) columns = [] sql_connection = context.sql_connection sql_table = context.sql_table engine = create_engine(sql_connection) insp = reflection.Inspector.from_engine(engine) base_columns = insp.get_columns(sql_table) columns = set() for constraint in insp.get_unique_constraints(sql_table): if len(constraint.get('column_names')) == 1: columns.update(constraint.get('column_names')[0]) columns = columns.union(set(insp.get_pk_constraint(sql_table).get('constrained_columns'))) columns = list(columns) final = [] for col in base_columns: if col['name'] not in columns: continue final.append(col.copy()) final.sort( lambda x, y: cmp(x.get('name'), y.get('name') ) ) items = [SimpleTerm(a.get('name'), a.get('name'), a.get('name')+' ('+str(a.get('type'))+')') for a in final if a.get('name')] return SimpleVocabulary(items)
def __call__(self): if self.action.name == 'form.buttons.catalogupdate': ISQLTypeSettings(self.form.context.fti).updateCatalogItems() self.request.response.redirect(self.request['ACTUAL_URL']) if self.action.name == 'form.buttons.reindex': ISQLTypeSettings(self.form.context.fti).catalogItems() self.request.response.redirect(self.request['ACTUAL_URL']) if self.action.name == 'form.buttons.unindex': ISQLTypeSettings(self.form.context.fti).unCatalogItems() self.request.response.redirect(self.request['ACTUAL_URL']) else: super(ReindexActionHandler, self).__call__()
def __call__(self, context): # we take the fti type settings to get the selected connections and table # on adding, guess the portal_type request = getattr(context, 'REQUEST', None) request_url = hasattr(request, 'get') and request.get('URL') or '' if '++add++' in request_url: portal_type = context.REQUEST.get('URL').split('++add++')[1] fti = queryUtility(IDexterityFTI, name=portal_type, default=None) if fti: context = ISQLTypeSettings(fti) elif ISQLTypeSchemaContext.providedBy(context): context = ISQLTypeSettings(context.fti) elif ISQLDexterityItem.providedBy(context): fti = queryUtility(IDexterityFTI, name=context.portal_type, default=None) if fti: context = ISQLTypeSettings(fti) elif IField.providedBy(context): context = ISQLTypeSettings(aq_parent(context.context).fti) urls = ISQLAlchemyConnectionStrings( component.getUtility(ISiteRoot)).values() if not urls or not getattr( context, 'sql_connection', None) or not getattr( context, 'sql_table', None) or not getattr( context, 'sql_id_column', None): return SimpleVocabulary([]) ids = [] sql_table = context.sql_table sql_id_column = context.sql_id_column s = text('SELECT ' + sql_id_column + ' FROM ' + sql_table) connection = queryUtility(ISQLConnectionsUtility, name=context.id, default=None) if not connection: connection = registerConnectionUtilityForFTI(context.context) try: res = connection.conn.execute(s).fetchall() except: connection.reinit() res = connection.conn.execute(s).fetchall() items = [] for a in res: title = a[0] try: title = str(a[0]) except: try: title = str(a[0].encode('utf-8')) except: title = str(a[0].decode('utf-8')) items.append(SimpleTerm(title, title, title)) return SimpleVocabulary(items)
def registerConnectionUtilityForFTI(fti): # This registers an utility that will handle connections and sessions for each defined SQL DX types. if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) utility = queryUtility(ISQLConnectionsUtility, name=fti.id, default=None) if utility != None: return utility if not getattr(fti, 'sql_table', None): return processor = SQLConnectionsUtility(fti) gsm = getGlobalSiteManager() gsm.registerUtility(processor, ISQLConnectionsUtility, name=fti.id) LOG.info('SQL Connection utility registered for ' + fti.id) return getUtility(ISQLConnectionsUtility, name=fti.id)
def fields(self): if 'collective.behavior.sql.behavior.behaviors.ISQLContent' not in self.context.fti.behaviors: return super(SQLTypeOverviewForm, self).fields # if this type's class is not a container, # remove the field for filtering contained content types klass = resolveDottedName(self.context.fti.klass) fields = field.Fields(ISQLTypeSettings) fti_adapted = ISQLTypeSettings(self.context.fti) to_omit = [] if not fti_adapted.sql_connection: to_omit = [ 'sql_table', 'sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id' ] fields = fields.omit('sql_table', 'sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id') elif not fti_adapted.sql_table: to_omit = [ 'sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id' ] fields = fields.omit('sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id') else: engine = create_engine(fti_adapted.sql_connection) insp = reflection.Inspector.from_engine(engine) tables = insp.get_table_names() views = insp.get_view_names() if fti_adapted.sql_table in views and fti_adapted.sql_table not in tables: fields['sql_id_column'].field.vocabulary = None fields[ 'sql_id_column'].field.vocabularyName = "collective.behavior.sql.AvailableSQLAlchemyColumns" names = [a for a in ISQLTypeSettings.names() if a not in to_omit] filtered = fields.select('title', 'description', 'allowed_content_types', 'filter_content_types', *names) if not IFolderish.implementedBy(klass): del filtered['filter_content_types'] urls = ISQLAlchemyConnectionStrings( component.getUtility(ISiteRoot)).values() if len(urls) == 1: filtered['sql_connection'].field.default = urls[0] return filtered
def fields(self): if 'collective.behavior.sql.behavior.behaviors.ISQLContent' not in self.context.fti.behaviors: return super(SQLTypeOverviewForm, self).fields # if this type's class is not a container, # remove the field for filtering contained content types klass = resolveDottedName(self.context.fti.klass) fields = field.Fields(ISQLTypeSettings) fti_adapted = ISQLTypeSettings(self.context.fti) to_omit = [] if not fti_adapted.sql_connection: to_omit = ['sql_table', 'sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id'] fields = fields.omit('sql_table', 'sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id') elif not fti_adapted.sql_table: to_omit = ['sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id'] fields = fields.omit('sql_id_column', 'sql_WHERE', 'sql_modification_timestamp_column', 'sql_modification_last_timestamp', 'sql_folder_id') else: engine = create_engine(fti_adapted.sql_connection) insp = reflection.Inspector.from_engine(engine) tables = insp.get_table_names() views = insp.get_view_names() if fti_adapted.sql_table in views and fti_adapted.sql_table not in tables: fields['sql_id_column'].field.vocabulary = None fields['sql_id_column'].field.vocabularyName = "collective.behavior.sql.AvailableSQLAlchemyColumns" names = [a for a in ISQLTypeSettings.names() if a not in to_omit] filtered = fields.select('title', 'description', 'allowed_content_types', 'filter_content_types', *names) if not IFolderish.implementedBy(klass): del filtered['filter_content_types'] urls = ISQLAlchemyConnectionStrings(component.getUtility(ISiteRoot)).values() if len(urls) == 1: filtered['sql_connection'].field.default = urls[0] return filtered
def update(self): fti = self.context.fti self.fti_id = fti.getId() self.sql_id_column = fti.sql_id_column and fti.sql_id_column or 'id' self.factory_utility = queryUtility(IFactory, name=fti.factory) self.sqlfti = ISQLTypeSettings(fti) self.sql_folder_id = getattr(self.sqlfti, 'sql_folder_id', self.fti_id) self.sqlschema = self.context.fti.lookupSchema() connection = queryUtility(ISQLConnectionsUtility, name=self.fti_id, default=None) if connection == None and self.portal_type: fti = queryUtility(IDexterityFTI, name=self.fti_id, default=None) if not fti: return None updateConnectionsForFti(fti) connection = queryUtility(ISQLConnectionsUtility, name=self.fti_id, default=None) self.connection = connection self.fieldnames = self.connection.fieldnames portal_obj = getToolByName(self.context, 'portal_url') self.portal_url = portal_obj() portal = portal_obj.getPortalObject() self.catalog = getToolByName(portal, "portal_catalog") super(SQLItemListingForm, self).update()
def getPhysicalPath(self): """this needs implementation if the object doesnt exists for real in portal""" if not self.sql_virtual: return super(SQLDexterityItem, self).getPhysicalPath() portal_url = getToolByName(getSite(), 'portal_url')() fti = ISQLTypeSettings(getUtility(IDexterityFTI, name=self.portal_type)) folder = None parent_path = None if IRelationValue.providedBy(getattr(fti, 'sql_folder_id', None)): folder = fti.sql_folder_id.to_object if folder: parent_path = folder.getPhysicalPath() elif getattr(fti, 'sql_folder_id', '') and getattr( fti, 'sql_folder_id', '').startswith('/'): portal = getToolByName(getSite(), 'portal_url').getPortalObject() folder = portal.restrictedTraverse(fti.sql_folder_id) if folder: parent_path = folder.getPhysicalPath() if not parent_path: parent_path = ( '', getSite().id, 'data-' + self.portal_type, ) return parent_path + (str(self.id), )
def __init__(self, context, request): super(SQLDexterityPublishTraverse, self).__init__(context, request) annotations = IAnnotations(context) self.fti_id = annotations.get('collective.behavior.sql.sql_type') if self.fti_id: self.fti = getUtility(IDexterityFTI, name=self.fti_id) name = getattr(ISQLTypeSettings(self.fti), 'sql_folder_id', self.fti_id) if name and IRelationValue.providedBy(name): obj = name.to_object if obj: name = obj.getId() else: name = self.fti_id elif name and name.startswith('/'): portal = getToolByName(getSite(), 'portal_url').getPortalObject() obj = portal.restrictedTraverse(name) if obj: name = obj.getId() else: name = self.fti_id elif not name: name = self.fti_id self.name = name self.Title = self.fti.Title()
def updateConnectionsForFti(fti): # find the FTI and model connection = queryUtility(ISQLConnectionsUtility, name=fti.id, default=None) if not connection: connection = registerConnectionUtilityForFTI(fti) adapted = ISQLTypeSettings(fti) sql_id_column = getattr(adapted, 'sql_id_column', 'id') # fieldnames = {'id':sql_id_column} fieldnames = {} for field_name, field in schema.getFieldsInOrder( fti.lookupSchema() ): if getattr(field, 'sql_column', None): sql_column = getattr(field, 'sql_column', None) fieldnames[field_name] = sql_column for line in getattr(adapted, 'sql_fields_columns', []): fieldnames[line.split(':')[0]] = line.split(':')[1] connection.fieldnames = fieldnames sqlfti = adapted.updateCatalogItems()
def updateConnectionsForFti(fti): # find the FTI and model connection = queryUtility(ISQLConnectionsUtility, name=fti.id, default=None) if not connection: connection = registerConnectionUtilityForFTI(fti) adapted = ISQLTypeSettings(fti) sql_id_column = getattr(adapted, 'sql_id_column', 'id') # fieldnames = {'id':sql_id_column} fieldnames = {} for field_name, field in schema.getFieldsInOrder(fti.lookupSchema()): if getattr(field, 'sql_column', None): sql_column = getattr(field, 'sql_column', None) fieldnames[field_name] = sql_column for line in getattr(adapted, 'sql_fields_columns', []): fieldnames[line.split(':')[0]] = line.split(':')[1] connection.fieldnames = fieldnames sqlfti = adapted.updateCatalogItems()
def updateConnectionsForFti(fti): # find the FTI and model if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) connection = queryUtility(ISQLConnectionsUtility, name=fti.id, default=None) if not connection: connection = registerConnectionUtilityForFTI(fti) if not getattr(connection, 'name', None): return registerPublisherForFTI(fti) sql_id_column = getattr(fti, 'sql_id_column', 'id') # fieldnames = {'id':sql_id_column} fieldnames = {} for field_name, field in schema.getFieldsInOrder( fti.context.lookupSchema() ): if getattr(field, 'sql_column', None): sql_column = getattr(field, 'sql_column', None) fieldnames[field_name] = sql_column for line in getattr(fti, 'sql_fields_columns', []): fieldnames[line.split(':')[0]] = line.split(':')[1] connection.fieldnames = fieldnames sqlfti = fti.updateCatalogItems()
def __call__(self): ftis = [ a for a in getAllUtilitiesRegisteredFor(IDexterityFTI) if 'collective.behavior.sql.behavior.behaviors.ISQLContent' in a.behaviors and getattr(a, 'sql_table', None) ] for fti in ftis: items = ISQLTypeSettings(fti).updateCatalogItems() LOG.info( str(len(items)) + ' items have been updated in catalog for ' + str(fti.id) + '.') return ''
def __init__(self, context, request): super(SQLFieldEditForm, self).__init__(context, request) self.field.context = context self.sqlfti = ISQLTypeSettings(self.context.fti) datas = {} for a,b in [(line.split(':')[0],line.split(':')[1]) for line in getattr(self.sqlfti, 'sql_fields_columns', [])]: datas[a] = b fieldname = self.field.__name__ if fieldname == 'subjects': fieldname = 'subject' if datas.get(fieldname): self.field.sql_column = datas[fieldname]
def registerConnectionUtilityForFTI(fti): # This registers an utility that will handle connections and sessions for each defined SQL DX types. if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) utility = queryUtility(ISQLConnectionsUtility, name=fti.id, default=None) if utility != None: return utility if not getattr(fti, 'sql_table', None): return processor = SQLConnectionsUtility(fti) gsm = getGlobalSiteManager() gsm.registerUtility(processor, ISQLConnectionsUtility, name=fti.id) LOG.info('SQL Connection utility registered for '+fti.id) return getUtility(ISQLConnectionsUtility, name=fti.id)
def updateConnectionsForFti(fti): # find the FTI and model if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) connection = queryUtility(ISQLConnectionsUtility, name=fti.id, default=None) if not connection: connection = registerConnectionUtilityForFTI(fti) if not getattr(connection, 'name', None): return registerPublisherForFTI(fti) sql_id_column = getattr(fti, 'sql_id_column', 'id') # fieldnames = {'id':sql_id_column} fieldnames = {} for field_name, field in schema.getFieldsInOrder( fti.context.lookupSchema()): if getattr(field, 'sql_column', None): sql_column = getattr(field, 'sql_column', None) fieldnames[field_name] = sql_column for line in getattr(fti, 'sql_fields_columns', []): fieldnames[line.split(':')[0]] = line.split(':')[1] connection.fieldnames = fieldnames sqlfti = fti.updateCatalogItems()
def initConnections(site, event): # this is called on first Plone traverse portal_quickinstaller = getToolByName(site, 'portal_quickinstaller') if portal_quickinstaller.isProductInstalled('collective.behavior.sql'): if not getAllUtilitiesRegisteredFor(ISQLConnectionsUtility): ftis = [a for a in getAllUtilitiesRegisteredFor(IDexterityFTI) if 'collective.behavior.sql.behavior.behaviors.ISQLContent' in a.behaviors and getattr(a, 'sql_table', None)] if ftis: for fti in ftis: if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) try: initConnectionForFTI(fti) except: LOG.error('Unable to init connection for %s' % (fti.id)) gsm = getGlobalSiteManager() gsm.registerUtility(SQLConnectionsUtility(), ISQLConnectionsUtility) else: gsm = getGlobalSiteManager() gsm.registerUtility(SQLConnectionsUtility(), ISQLConnectionsUtility)
def initConnectionForFTI(fti): if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) registerPublisherForFTI(fti) registerConnectionUtilityForFTI(fti)
def applyChanges(self, data): returned = super(SQLTypeOverviewForm, self).applyChanges(data) self.updateWidgets() ISQLTypeSettings(self.context.fti).catalogItems() return returned
def __getattribute__(self, name): if name.startswith('_') or name.startswith( 'portal_') or name.startswith('@@'): return super(SQLDexterityItem, self).__getattribute__(name) if name == 'id' and not self.sql_virtual: return super(SQLDexterityItem, self).__getattribute__(name) connection = queryUtility(ISQLConnectionsUtility, name=self.portal_type, default=None) if connection == None and self.portal_type: fti = queryUtility(IDexterityFTI, name=self.portal_type, default=None) if not fti: return None updateConnectionsForFti(fti) connection = queryUtility(ISQLConnectionsUtility, name=self.portal_type, default=None) if not connection: return super(SQLDexterityItem, self).__getattribute__(name) if name == 'UID': return self.portal_type + '-' + connection.sql_table + '-' + str( self.sql_id) if name == 'id' and 'id' not in connection.fieldnames.keys(): fti = ISQLTypeSettings( getUtility(IDexterityFTI, name=self.portal_type)) nameFromTitle = INameFromTitle(self, None) if nameFromTitle is not None and nameFromTitle.title: sql_folder_id = getattr(fti, 'sql_folder_id', 'data-' + self.portal_type) title = nameFromTitle.title if IRelationValue.providedBy(name): folder = sql_folder_id.to_object if folder: return INameChooser(folder).chooseName(title, self) return INameChooser(getSite()).chooseName(title, self) if name in connection.fieldnames.keys(): sql_column = connection.fieldnames[name] sql_item = self.getSQLItem() fieldname = 'name' if sql_item and sql_column: while '.' in sql_column: sql_item = getattr(sql_item, sql_column.split('.')[0], None) if sql_item and ( (isinstance(sql_item, list) and len(sql_item) > 1) or hasattr(sql_item, '_sa_instance_state')): value = sql_item fieldname = sql_column.split('.')[-1] break sql_column = '.'.join(sql_column.split('.')[1:]) else: value = getattr(sql_item, sql_column, None) #this is a relation if value and (isinstance(value, list) or hasattr(value, '_sa_instance_state')): sqlftis = [ a for a in getAllUtilitiesRegisteredFor(IDexterityFTI) if 'collective.behavior.sql.behavior.behaviors.ISQLContent' in a.behaviors and getattr(a, 'sql_table', None) ] if name == 'subject': return tuple( [getattr(a, fieldname, '') for a in value]) tableftis = [] for iface in iterSchemataForType(self.portal_type): if name in iface.names(): field = iface[name] if IList.providedBy(field): return [ getattr(a, fieldname, '') for a in value ] # hope it has name! elif ITuple.providedBy(field): return tuple( [getattr(a, fieldname, '') for a in value]) if IRelationChoice.providedBy( field) or IRelationList.providedBy(field): if IRelationChoice.providedBy(field): allowed_types = field.source.query.get( 'portal_type', []) else: allowed_types = field.value_type.source.query.get( 'portal_type', []) tableftis = [] for sqlfti in sqlftis: adapted = ISQLTypeSettings(sqlfti, None) if isinstance(value, list): classname = value[0].__class__.__name__ else: classname = value.__class__.__name__ if adapted and getattr( adapted, 'sql_table', None) == classname: if not allowed_types or sqlfti.id in allowed_types: tableftis.append(adapted) catalog = getToolByName( getSite(), 'portal_catalog') relations = [] for tablefti in tableftis: sql_id_column = getattr( tablefti, 'sql_id_column', 'id') valueids = [] if isinstance(value, list): valueids = [ getattr(a, sql_id_column, None) for a in value if getattr(a, sql_id_column, None) ] else: valueids = getattr( value, sql_id_column, None) brains = catalog.searchResults( portal_type=tablefti.id, sql_id=valueids) for brain in brains: relations.append( SQLRelationValue( brain.portal_type, brain.sql_id)) if IRelationChoice.providedBy( field) and relations: return relations[0] elif IRelationList.providedBy( field) and relations: return relations for iface in iterSchemataForType(self.portal_type): if name == 'subject': try: return tuple([ a.decode('utf-8') for a in literal_eval(value) ]) except: return tuple([a.strip() for a in value.split(',')]) if name in iface.names(): field = iface[name] if IRichText.providedBy(field): return RichTextValue(value) if INamedBlobImage.providedBy(field): return NamedBlobImage( base64.b64decode(value), filename=unicode(self.portal_type + self.id + ".jpg")) if IList.providedBy(field): try: return [ a.decode('utf-8') for a in literal_eval(value) ] except: return [a.strip() for a in value.split(',')] if ITuple.providedBy(field): try: return tuple([ a.decode('utf-8') for a in literal_eval(value) ]) except: return tuple( [a.strip() for a in value.split(',')]) if isinstance(value, unicode) or name == 'id': try: return str(value) except: pass return value return super(SQLDexterityItem, self).__getattribute__(name)
def initConnectionForFTI(fti): if not ISQLTypeSettings.providedBy(fti): fti = ISQLTypeSettings(fti) registerPublisherForFTI(fti) registerConnectionUtilityForFTI(fti)
def item_count(self): sqlfti = ISQLTypeSettings(self.context) s = text('SELECT '+sqlfti.sql_id_column+' FROM '+sqlfti.sql_table) return len(sqlfti.conn.execute(s).fetchall())
def __getattribute__(self, name): if name.startswith('_') or name.startswith( 'portal_') or name.startswith('@@') or name == 'sql_id': return super(SQLDexterityItem, self).__getattribute__(name) connection = queryUtility(ISQLConnectionsUtility, name=self.portal_type, default=None) if connection == None and self.portal_type: fti = queryUtility(IDexterityFTI, name=self.portal_type, default=None) if not fti: return None updateConnectionsForFti(fti) connection = queryUtility(ISQLConnectionsUtility, name=self.portal_type, default=None) if name == 'view': #be sure session and sqlitem are up to date self._v_sql_item = None connection.session.close() if not connection: return super(SQLDexterityItem, self).__getattribute__(name) if name == 'UID' and self.sql_virtual: return self.portal_type + '-' + connection.sql_table + '-' + str( self.sql_id) if name == 'id' and 'id' not in connection.fieldnames.keys(): if not self.sql_virtual: return super(SQLDexterityItem, self).__getattribute__(name) fti = ISQLTypeSettings( getUtility(IDexterityFTI, name=self.portal_type)) nameFromTitle = INameFromTitle(self, None) if nameFromTitle is not None and nameFromTitle.title: sql_folder_id = getattr(fti, 'sql_folder_id', 'data-' + self.portal_type) title = nameFromTitle.title folder = None if IRelationValue.providedBy(sql_folder_id): folder = sql_folder_id.to_object elif sql_folder_id and sql_folder_id.startswith('/'): portal = getToolByName(getSite(), 'portal_url').getPortalObject() folder = portal.restrictedTraverse(sql_folder_id) if folder: name = INameChooser(folder).chooseName(title, self) return name # return INameChooser(getSite()).chooseName(title, self) # return getUtility(IURLNormalizer).normalize(title) return self.sql_id if name in connection.fieldnames.keys(): sql_column = connection.fieldnames[name] sql_item = self.getSQLItem() try: sql_id = getattr(sql_item, connection.sql_id_column, None) except orm_exc.DetachedInstanceError: self._v_sql_item = None sql_item = self.getSQLItem() sql_id = getattr(sql_item, connection.sql_id_column, None) fieldname = 'name' if sql_item and sql_column: while '.' in sql_column: sql_key = sql_column.split('.')[0] sql_item = getattr(sql_item, sql_key, None) if isinstance(sql_item, list): value = sql_item fieldname = sql_column.split('.')[-1] break sql_column = '.'.join(sql_column.split('.')[1:]) else: if not isinstance(sql_item, list): value = getattr(sql_item, sql_column, None) if not value and (isinstance(value, list) or hasattr(value, '_sa_instance_state')): value = '' elif (isinstance(value, list) or hasattr(value, '_sa_instance_state')): sqlftis = [ a for a in getAllUtilitiesRegisteredFor(IDexterityFTI) if 'collective.behavior.sql.behavior.behaviors.ISQLContent' in a.behaviors and getattr(a, 'sql_table', None) ] if name == 'subject': return tuple( [getattr(a, fieldname, '') for a in value]) tableftis = [] for iface in iterSchemataForType(self.portal_type): if name in iface.names(): field = iface[name] if IRelationChoice.providedBy( field) or IRelationList.providedBy(field): if IRelationChoice.providedBy(field): allowed_types = field.source.query.get( 'portal_type', []) else: allowed_types = field.value_type.source.query.get( 'portal_type', []) tableftis = [] for sqlfti in sqlftis: adapted = ISQLTypeSettings(sqlfti, None) if isinstance(value, list): classname = value[0].__class__.__name__ else: classname = value.__class__.__name__ if adapted and getattr( adapted, 'sql_table', None) == classname: if not allowed_types or sqlfti.id in allowed_types: tableftis.append(adapted) catalog = getToolByName( getSite(), 'portal_catalog') relations = [] for tablefti in tableftis: sql_id_column = getattr( tablefti, 'sql_id_column', 'id') valueids = [] if isinstance(value, list): valueids = [ getattr(a, sql_id_column, None) for a in value if getattr(a, sql_id_column, None) ] else: valueids = getattr( value, sql_id_column, None) valueids = [str(a) for a in valueids] brains = catalog.unrestrictedSearchResults( portal_type=tablefti.id, sql_id=valueids) for brain in brains: relations.append( SQLRelationValue( brain.portal_type, brain.UID, self)) if IRelationChoice.providedBy( field) and relations: return relations[0] elif IRelationList.providedBy( field) and relations: return relations elif ITuple.providedBy(field): return tuple( [getattr(a, fieldname, '') for a in value]) elif IList.providedBy(field): return [ getattr(a, fieldname, '') for a in value ] elif value and isinstance(value, list): value = getattr(value[0], fieldname, '') for iface in iterSchemataForType(self.portal_type): if name == 'subject': try: return tuple([ a.decode('utf-8') for a in literal_eval(value) ]) except: return tuple([a.strip() for a in value.split(',')]) if name in iface.names(): field = iface[name] if IRichText.providedBy(field): if not value: return '' if not '<p' in value or not '<br' in value: value = '<p>' + '</p><p>'.join([ a for a in value.split('\n') if a.strip() ]) + '</p>' # try: # value = str(value) # except: # try: # value = value.decode('utf-8') # except: # try: # value = value.encode('utf-8') # except: # pass return RichTextValue(unidecode(value)) elif INamedBlobImage.providedBy(field): return NamedBlobImage( base64.b64decode(value), filename=unicode(self.portal_type + self.id + ".jpg")) elif ITuple.providedBy(field): if not value: return tuple([]) try: return tuple([ a.decode('utf-8') for a in literal_eval(value) ]) except: return tuple( [a.strip() for a in value.split(',')]) elif IList.providedBy(field): if not value: return [] try: return [ a.decode('utf-8') for a in literal_eval(value) ] except: return [a.strip() for a in value.split(',')] elif IDatetime.providedBy(field) and hasattr( value, 'day') and not hasattr(value, 'hour'): value = datetime.datetime.combine( value, datetime.datetime.min.time()) if name in [ 'expiration_date', 'effective_date', 'effective', 'expires' ] and hasattr(value, 'day') and not hasattr(value, 'hour'): value = datetime.datetime.combine( value, datetime.datetime.min.time()) if isinstance(value, unicode) or name == 'id': try: value = str(value) except: pass return value return super(SQLDexterityItem, self).__getattribute__(name)
def getSQLTable(obj): utility = queryUtility(IDexterityFTI, name=obj.portal_type) if utility: sql_type = ISQLTypeSettings(utility) return getattr(sql_type, 'sql_table', '') return ''