Réutilisation de la connexion Solr, pour ne pas en ouvrir plus que nécessaire.
[Plinn.git] / catalog.py
index 7961a10..05cbd59 100644 (file)
@@ -18,20 +18,24 @@ from BTrees.IIBTree import intersection, IISet
 from BTrees.IIBTree import weightedIntersection
 import warnings
 
 from BTrees.IIBTree import weightedIntersection
 import warnings
 
+_VOLATILE_SOLR_NAME = '_v_solrConnection'
+
 class SolrTransactionHook :
     ''' commit solr couplé sur le commit de la ZODB '''
 class SolrTransactionHook :
     ''' commit solr couplé sur le commit de la ZODB '''
-    def __init__(self, connection) :
-        self.connection = connection
+    def __init__(self, context) :
+        self.context = context
     
     def __call__(self, status) :
     
     def __call__(self, status) :
+        con = getattr(self.context, _VOLATILE_SOLR_NAME)
         if status :
         if status :
-            self.connection.commit()
-            self.connection.close()
+            con.commit()
+            con.close()
         else :
         else :
-            self.connection.close()
+            con.close()
+        delattr(self.context, _VOLATILE_SOLR_NAME)
 
 class CatalogTool(BaseCatalogTool) :
 
 class CatalogTool(BaseCatalogTool) :
-    meta_type = 'Legivoc Catalog'
+    meta_type = 'Plinn Catalog'
     security = ClassSecurityInfo()
     manage_options = (BaseCatalogTool.manage_options[:5] +
                       ({'label' : 'Solr', 'action' : 'manage_solr'},) +
     security = ClassSecurityInfo()
     manage_options = (BaseCatalogTool.manage_options[:5] +
                       ({'label' : 'Solr', 'action' : 'manage_solr'},) +
@@ -45,6 +49,14 @@ class CatalogTool(BaseCatalogTool) :
         self.solr_url = 'http://localhost:8983/solr'
         self.delegatedIndexes = ('Title', 'Description', 'SearchableText')
     
         self.solr_url = 'http://localhost:8983/solr'
         self.delegatedIndexes = ('Title', 'Description', 'SearchableText')
     
+    def _getSolrConnection(self) :
+        if not hasattr(self, _VOLATILE_SOLR_NAME) :
+            con = SolrConnection(self.solr_url)
+            setattr(self, _VOLATILE_SOLR_NAME, con)
+            txn = transaction.get()
+            txn.addAfterCommitHook(SolrTransactionHook(self))
+        return getattr(self, _VOLATILE_SOLR_NAME)
+    
     security.declarePrivate('solrAdd')
     def solrAdd(self, object, idxs=[], uid=None) :
         if IIndexableObject.providedBy(object):
     security.declarePrivate('solrAdd')
     def solrAdd(self, object, idxs=[], uid=None) :
         if IIndexableObject.providedBy(object):
@@ -61,10 +73,8 @@ class CatalogTool(BaseCatalogTool) :
         for name in idxs :
             attr = getattr(w, name, '')
             data[name] = attr() if callable(attr) else attr
         for name in idxs :
             attr = getattr(w, name, '')
             data[name] = attr() if callable(attr) else attr
-        c = SolrConnection(self.solr_url)
+        c = self._getSolrConnection()
         c.add(**data)
         c.add(**data)
-        txn = transaction.get()
-        txn.addAfterCommitHook(SolrTransactionHook(c))
     
     
     # PortalCatalog api overloads
     
     
     # PortalCatalog api overloads
@@ -95,11 +105,9 @@ class CatalogTool(BaseCatalogTool) :
         """Remove from catalog.
         """
         super(CatalogTool, self).unindexObject(object)
         """Remove from catalog.
         """
         super(CatalogTool, self).unindexObject(object)
-        c = SolrConnection(self.solr_url)
+        c = self._getSolrConnection()
         url = self.__url(object)
         c.delete(id=url)
         url = self.__url(object)
         c.delete(id=url)
-        txn = transaction.get()
-        txn.addAfterCommitHook(SolrTransactionHook(c))
         
 InitializeClass(CatalogTool)
 
         
 InitializeClass(CatalogTool)
 
@@ -111,26 +119,24 @@ class DelegatedCatalog(Catalog) :
         Catalog.__init__(self, brains=brains)
         self.zcat = zcat
     
         Catalog.__init__(self, brains=brains)
         self.zcat = zcat
     
-    def getDelegatedIndexes(self) :
-        return ('Title', 'Description', 'SearchableText') # <= TODO virer cette ligne
-        return self.zcat.delegatedIndexes
-    
     def delegateSearch(self, query, plan) :
         '''
         retours faux : 
     def delegateSearch(self, query, plan) :
         '''
         retours faux : 
-        None signifie : pas de délégation, il faut continue à interroger les autres index
+        None signifie : pas de délégation, il faut continuer à interroger les autres index.
         IISet() vide : pas de résultat lors de la délégation, on peut arrêter la recherche.
         '''
         IISet() vide : pas de résultat lors de la délégation, on peut arrêter la recherche.
         '''
-        indexes = set(plan).intersection(set(self.getDelegatedIndexes()))
+        indexes = set(query.keys()).intersection(set(self.zcat.delegatedIndexes))
+        if not indexes :
+            return None
         delegatedQuery = {}
         for i in indexes :
             delegatedQuery[i] = query.pop(i)
         delegatedQuery = {}
         for i in indexes :
             delegatedQuery[i] = query.pop(i)
-            plan.remove(i)
-        if not delegatedQuery :
-            return None
-        c = SolrConnection('http://localhost:8983/solr')
+            try : plan.remove(i)
+            except ValueError : pass
+        c = SolrConnection(self.zcat.solr_url)
         q =' AND '.join(['%s:"%s"' % item for item in delegatedQuery.items()])
         q =' AND '.join(['%s:"%s"' % item for item in delegatedQuery.items()])
-        resp = c.query(q, fields='id')
+        resp = c.query(q, fields='id', rows=len(self))
+        c.close()
         return IISet(filter(None, [self.uids.get(r['id']) for r in resp.results])) 
     
     def search(self, query, sort_index=None, reverse=0, limit=None, merge=1):
         return IISet(filter(None, [self.uids.get(r['id']) for r in resp.results])) 
     
     def search(self, query, sort_index=None, reverse=0, limit=None, merge=1):