[prev in list] [next in list] [prev in thread] [next in thread] 

List:       kde-commits
Subject:    KDE/kdebase/runtime/nepomuk/services/queryservice
From:       Sebastian Trueg <sebastian () trueg ! de>
Date:       2010-09-17 16:16:27
Message-ID: 20100917161627.4C435AC888 () svn ! kde ! org
[Download RAW message or body]

SVN commit 1176416 by trueg:

The query service did not scale at all due to it using one thread for each query \
folder. That resulted in tons of threads and thus, connections to the storage \
service. Thus, now we use a max of 10 threads through QThreadPool.

 M  +2 -1      CMakeLists.txt  
 AM            countqueryrunnable.cpp   [License: GPL (v2/3)]
 AM            countqueryrunnable.h   [License: GPL (v2/3)]
 M  +37 -36    folder.cpp  
 M  +12 -7     folder.h  
 M  +13 -0     queryservice.cpp  
 M  +3 -0      queryservice.h  
 AM            searchrunnable.cpp   searchthread.cpp#1174909 [License: LGPL (v2)]
 AM            searchrunnable.h   searchthread.h#1174909 [License: LGPL (v2)]
 D             searchthread.cpp  
 D             searchthread.h  


--- trunk/KDE/kdebase/runtime/nepomuk/services/queryservice/CMakeLists.txt \
#1176415:1176416 @@ -13,9 +13,10 @@
 
 set(queryservice_SRCS
   queryservice.cpp
-  searchthread.cpp
   folder.cpp
   folderconnection.cpp
+  searchrunnable.cpp
+  countqueryrunnable.cpp
 )
 
 qt4_add_dbus_adaptor(queryservice_SRCS
--- trunk/KDE/kdebase/runtime/nepomuk/services/queryservice/folder.cpp \
#1176415:1176416 @@ -19,21 +19,24 @@
 #include "folder.h"
 #include "folderconnection.h"
 #include "queryservice.h"
+#include "countqueryrunnable.h"
+#include "searchrunnable.h"
 
-#include <Soprano/Model>
-#include <Soprano/Node>
-#include <Soprano/Util/AsyncQuery>
-
 #include <Nepomuk/Resource>
 #include <Nepomuk/ResourceManager>
 
+#include <Soprano/Model>
+
 #include <KDebug>
 
+#include <QtCore/QThreadPool>
 
+
 Nepomuk::Query::Folder::Folder( const Query& query, QObject* parent )
     : QObject( parent ),
       m_isSparqlQueryFolder( false ),
-      m_query( query )
+      m_query( query ),
+      m_currentSearchRunnable( 0 )
 {
     init();
 }
@@ -58,13 +61,6 @@
     m_updateTimer.setSingleShot( true );
     m_updateTimer.setInterval( 2000 );
 
-    m_searchThread = new SearchThread( this );
-
-    connect( m_searchThread, SIGNAL( newResult( const Nepomuk::Query::Result& ) ),
-             this, SLOT( slotSearchNewResult( const Nepomuk::Query::Result& ) ),
-             Qt::QueuedConnection );
-    connect( m_searchThread, SIGNAL( finished() ),
-             this, SLOT( slotSearchFinished() ) );
     connect( ResourceManager::instance()->mainModel(), SIGNAL( statementsAdded() ),
              this, SLOT( slotStorageChanged() ) );
     connect( ResourceManager::instance()->mainModel(), SIGNAL( statementsRemoved() \
), @@ -76,7 +72,9 @@
 
 Nepomuk::Query::Folder::~Folder()
 {
-    m_searchThread->cancel();
+    if( m_currentSearchRunnable )
+        m_currentSearchRunnable->cancel();
+
     // cannot use qDeleteAll since deleting a connection changes m_connections
     while ( !m_connections.isEmpty() )
         delete m_connections.first();
@@ -85,25 +83,17 @@
 
 void Nepomuk::Query::Folder::update()
 {
-    if ( !m_searchThread->isRunning() ) {
-        if ( m_query.isValid() ) {
-            // count the results
-            kDebug() << "Count query:" << m_query.toSparqlQuery( \
                Query::CreateCountQuery );
-            delete m_countQuery;
-            m_countQuery = Soprano::Util::AsyncQuery::executeQuery( \
                ResourceManager::instance()->mainModel(),
-                                                                    \
                m_query.toSparqlQuery( Query::CreateCountQuery ),
-                                                                    \
                Soprano::Query::QueryLanguageSparql );
-            connect( m_countQuery, SIGNAL( nextReady( Soprano::Util::AsyncQuery* ) \
                ),
-                     this, SLOT( slotCountQueryFinished( Soprano::Util::AsyncQuery* \
) ) ); +    if ( !m_currentSearchRunnable ) {
+        m_currentSearchRunnable = new SearchRunnable( this );
+        QueryService::searchThreadPool()->start( m_currentSearchRunnable, 1 );
 
-            // and get the results
-            m_searchThread->query( m_query.toSparqlQuery(), \
m_query.requestPropertyMap() ); +        // we only need the count for \
initialListingDone +        if ( !m_initialListingDone &&
+             m_sparqlQuery.isEmpty() ) {
+            QueryService::searchThreadPool()->start( new CountQueryRunnable( this ), \
0 );  }
-        else {
-            m_searchThread->query( m_sparqlQuery, m_requestProperties );
         }
     }
-}
 
 
 QList<Nepomuk::Query::Result> Nepomuk::Query::Folder::entries() const
@@ -120,15 +110,24 @@
 
 QString Nepomuk::Query::Folder::sparqlQuery() const
 {
-    if ( m_query.isValid() )
+    if ( m_sparqlQuery.isEmpty() )
         return m_query.toSparqlQuery();
     else
         return m_sparqlQuery;
 }
 
 
-void Nepomuk::Query::Folder::slotSearchNewResult( const Nepomuk::Query::Result& \
result ) +Nepomuk::Query::RequestPropertyMap \
Nepomuk::Query::Folder::requestPropertyMap() const  {
+    if ( m_sparqlQuery.isEmpty() )
+        return m_query.requestPropertyMap();
+    else
+        return m_requestProperties;
+}
+
+
+void Nepomuk::Query::Folder::addResult( const Nepomuk::Query::Result& result )
+{
     if ( m_initialListingDone ) {
         m_newResults.insert( result.resource().resourceUri(), result );
         if ( !m_results.contains( result.resource().resourceUri() ) ) {
@@ -142,8 +141,10 @@
 }
 
 
-void Nepomuk::Query::Folder::slotSearchFinished()
+void Nepomuk::Query::Folder::listingFinished()
 {
+    m_currentSearchRunnable = 0;
+
     if ( m_initialListingDone ) {
         // inform about removed items
         foreach( const Result& result, m_results ) {
@@ -169,7 +170,7 @@
 
 void Nepomuk::Query::Folder::slotStorageChanged()
 {
-    if ( !m_updateTimer.isActive() && !m_searchThread->isRunning() ) {
+    if ( !m_updateTimer.isActive() && !m_currentSearchRunnable ) {
         update();
     }
     else {
@@ -181,18 +182,18 @@
 // if there was a change in the nepomuk store we update
 void Nepomuk::Query::Folder::slotUpdateTimeout()
 {
-    if ( m_storageChanged && !m_searchThread->isRunning() ) {
+    if ( m_storageChanged && !m_currentSearchRunnable ) {
         m_storageChanged = false;
         update();
     }
 }
 
 
-void Nepomuk::Query::Folder::slotCountQueryFinished( Soprano::Util::AsyncQuery* \
query ) +void Nepomuk::Query::Folder::countQueryFinished( int count )
 {
-    m_countQuery = 0;
-    m_totalCount = query->binding( 0 ).literal().toInt();
+    m_totalCount = count;
     kDebug() << m_totalCount;
+    if( count >= 0 )
     emit totalCount( m_totalCount );
 }
 
--- trunk/KDE/kdebase/runtime/nepomuk/services/queryservice/folder.h #1176415:1176416
@@ -22,6 +22,7 @@
 #include <QtCore/QObject>
 
 #include <Nepomuk/Query/Result>
+#include <Nepomuk/Query/Query>
 
 #include <QtCore/QHash>
 #include <QtCore/QTimer>
@@ -29,8 +30,6 @@
 
 #include <KUrl>
 
-#include "searchthread.h"
-
 namespace Soprano {
     namespace Util {
         class AsyncQuery;
@@ -40,6 +39,7 @@
 namespace Nepomuk {
     namespace Query {
 
+        class SearchRunnable;
         class FolderConnection;
 
         /**
@@ -77,6 +77,8 @@
 
             QString sparqlQuery() const;
 
+            RequestPropertyMap requestPropertyMap() const;
+
             /**
              * Get the total result count. This value will not be available
              * right away since it is calculated async.
@@ -87,6 +89,12 @@
              */
             int getTotalCount() const { return m_totalCount; }
 
+            void addResult( const Result& result );
+
+            void listingFinished();
+
+            void countQueryFinished( int count );
+
         public Q_SLOTS:
             void update();
 
@@ -104,11 +112,8 @@
             void aboutToBeDeleted( Nepomuk::Query::Folder* );
 
         private Q_SLOTS:
-            void slotSearchNewResult( const Nepomuk::Query::Result& );
-            void slotSearchFinished();
             void slotStorageChanged();
             void slotUpdateTimeout();
-            void slotCountQueryFinished( Soprano::Util::AsyncQuery* );
 
         private:
             void init();
@@ -153,8 +158,8 @@
             /// the results gathered during an update, needed to find removed items
             QHash<QUrl, Result> m_newResults;
 
-            /// the thread doing the work
-            SearchThread* m_searchThread;
+            /// the runnable doing work at the moment or 0 if idle
+            SearchRunnable* m_currentSearchRunnable;
 
             /// did the nepomuk store change after the last update - used for \
caching of update signals via m_updateTimer  bool m_storageChanged;
--- trunk/KDE/kdebase/runtime/nepomuk/services/queryservice/queryservice.cpp \
#1176415:1176416 @@ -21,6 +21,7 @@
 #include "folderconnection.h"
 #include "dbusoperators_p.h"
 
+#include <QtCore/QThreadPool>
 #include <QtDBus/QDBusConnection>
 #include <QtDBus/QDBusConnectionInterface>
 #include <QtDBus/QDBusObjectPath>
@@ -38,11 +39,16 @@
 
 NEPOMUK_EXPORT_SERVICE( Nepomuk::Query::QueryService, "nepomukqueryservice" )
 
+static QThreadPool* s_searchThreadPool = 0;
 
 Nepomuk::Query::QueryService::QueryService( QObject* parent, const QVariantList& )
     : Service( parent ),
       m_folderConnectionCnt( 0 )
 {
+    // this looks wrong but there is only one QueryService instance at all time!
+    s_searchThreadPool = new QThreadPool( this );
+    s_searchThreadPool->setMaxThreadCount( 10 );
+
     Nepomuk::Query::registerDBusTypes();
 }
 
@@ -57,6 +63,13 @@
 }
 
 
+// static
+QThreadPool* Nepomuk::Query::QueryService::searchThreadPool()
+{
+    return s_searchThreadPool;
+}
+
+
 QDBusObjectPath Nepomuk::Query::QueryService::query( const QString& query, const \
QDBusMessage& msg )  {
     Query q = Query::fromString( query );
--- trunk/KDE/kdebase/runtime/nepomuk/services/queryservice/queryservice.h \
#1176415:1176416 @@ -32,6 +32,7 @@
 class QDBusObjectPath;
 class QDBusMessage;
 class QDBusServiceWatcher;
+class QThreadPool;
 
 namespace Nepomuk {
     namespace Query {
@@ -48,6 +49,8 @@
             QueryService( QObject* parent, const QVariantList& );
             ~QueryService();
 
+            static QThreadPool* searchThreadPool();
+
         public Q_SLOTS:
             /**
              * Create a query folder from encoded query \p query.


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic