From kde-commits Mon Nov 18 16:18:34 2013 From: Andras Mantia Date: Mon, 18 Nov 2013 16:18:34 +0000 To: kde-commits Subject: [kdepim-runtime] resources/maildir: Use QDirIterator for listing the maildir folders. This: Message-Id: X-MARC-Message: https://marc.info/?l=kde-commits&m=138479152300598 Git commit 6100bbf86a5ddf5ae009fb6724d4d2ac53593c7f by Andras Mantia. Committed on 18/11/2013 at 16:18. Pushed by amantia into branch 'master'. Use QDirIterator for listing the maildir folders. This: - avoids some extra stats - avoids calling into Maildir::findRealKey that caches the keys and uses a = lot of memory for no real reason (in this case) REVIEW: 113918 BUG: 321944 M +16 -0 resources/maildir/libmaildir/maildir.cpp M +6 -0 resources/maildir/libmaildir/maildir.h M +32 -23 resources/maildir/retrieveitemsjob.cpp M +3 -3 resources/maildir/retrieveitemsjob.h http://commits.kde.org/kdepim-runtime/6100bbf86a5ddf5ae009fb6724d4d2ac53593= c7f diff --git a/resources/maildir/libmaildir/maildir.cpp b/resources/maildir/l= ibmaildir/maildir.cpp index 7834b04..9bd3802 100644 --- a/resources/maildir/libmaildir/maildir.cpp +++ b/resources/maildir/libmaildir/maildir.cpp @@ -422,6 +422,22 @@ QStringList Maildir::listNew() const return result; } = +QString Maildir::pathToNew() const +{ + if ( isValid() ) { + return d->path + QString::fromLatin1( "/new" ); + } + return QString(); +} + +QString Maildir::pathToCurrent() const +{ + if ( isValid() ) { + return d->path + QString::fromLatin1( "/cur" ); + } + return QString(); +} + QString Maildir::subDirPath() const { QDir dir( d->path ); diff --git a/resources/maildir/libmaildir/maildir.h b/resources/maildir/lib= maildir/maildir.h index b23fb7a..5c4c870 100644 --- a/resources/maildir/libmaildir/maildir.h +++ b/resources/maildir/libmaildir/maildir.h @@ -100,6 +100,12 @@ public: */ QStringList listCurrent() const; = + /** Return the path to the "new" directory */ + QString pathToNew() const; + + /** Return the path to the "cur" directory */ + QString pathToCurrent() const; + /** * Returns the full path to the subdir (the NAME.directory folder ). **/ diff --git a/resources/maildir/retrieveitemsjob.cpp b/resources/maildir/ret= rieveitemsjob.cpp index 5de627f..8b6cca6 100644 --- a/resources/maildir/retrieveitemsjob.cpp +++ b/resources/maildir/retrieveitemsjob.cpp @@ -26,6 +26,7 @@ #include = #include +#include #include = RetrieveItemsJob::RetrieveItemsJob ( const Akonadi::Collection& collection= , const KPIM::Maildir& md, QObject* parent ) : @@ -34,9 +35,9 @@ RetrieveItemsJob::RetrieveItemsJob ( const Akonadi::Colle= ction& collection, cons m_maildir( md ), m_mimeType( KMime::Message::mimeType() ), m_transaction( 0 ), + m_entryIterator(0), m_previousMtime( 0 ), - m_highestMtime( 0 ), - m_nextIndex( 0 ) + m_highestMtime( 0 ) { Q_ASSERT( m_collection.isValid() ); Q_ASSERT( m_maildir.isValid() ); @@ -66,63 +67,69 @@ void RetrieveItemsJob::localListDone ( KJob* job ) } = m_listingPath =3D m_maildir.path() + QLatin1String( "/new/" ); - m_entryList =3D m_maildir.listNew(); + delete m_entryIterator; + m_entryIterator =3D new QDirIterator( m_maildir.pathToNew(), QDir::Files= ); m_previousMtime =3D m_collection.remoteRevision().toLongLong(); m_highestMtime =3D 0; - processEntry(0); + processEntry(); } = -void RetrieveItemsJob::processEntry(qint64 index) +void RetrieveItemsJob::processEntry() { - QString entry; + QFileInfo entryInfo; + + QString filePath =3D m_entryIterator->next(); + + QString fileName =3D m_entryIterator->fileName(); = bool newItemFound =3D false; while ( !newItemFound ) { - if ( index >=3D m_entryList.size() ) { + if ( filePath.isEmpty() ) { if ( m_listingPath.endsWith( QLatin1String( "/new/" ) ) ) { m_listingPath =3D m_maildir.path() + QLatin1String( "/cur/" ); - m_entryList =3D m_maildir.listCurrent(); - processEntry( 0 ); + delete m_entryIterator; + m_entryIterator =3D new QDirIterator( m_maildir.pathToCurrent(), Q= Dir::Files ); + processEntry(); } else { entriesProcessed(); } return; } = - entry =3D m_entryList[index]; - const qint64 currentMtime =3D m_maildir.lastModified( entry ).toMSecsS= inceEpoch(); + entryInfo =3D m_entryIterator->fileInfo(); + const qint64 currentMtime =3D entryInfo.lastModified().toMSecsSinceEpo= ch(); m_highestMtime =3D qMax( m_highestMtime, currentMtime ); - if ( currentMtime <=3D m_previousMtime && m_localItems.contains( entry= ) ) { // old, we got this one already - m_localItems.remove( entry ); - index++; + if ( currentMtime <=3D m_previousMtime && m_localItems.contains( fileN= ame ) ) { // old, we got this one already + m_localItems.remove( fileName ); + filePath =3D m_entryIterator->next(); + fileName =3D m_entryIterator->fileName(); } else { newItemFound =3D true; } } Akonadi::Item item; - item.setRemoteId( entry ); + item.setRemoteId( fileName ); item.setMimeType( m_mimeType ); - const qint64 entrySize =3D m_maildir.size( entry ); + const qint64 entrySize =3D entryInfo.size(); if ( entrySize >=3D 0 ) item.setSize( entrySize ); = KMime::Message *msg =3D new KMime::Message; - msg->setHead( KMime::CRLFtoLF( m_maildir.readEntryHeadersFromFile( m_lis= tingPath + entry ) ) ); + msg->setHead( KMime::CRLFtoLF( m_maildir.readEntryHeadersFromFile( m_lis= tingPath + fileName ) ) ); msg->parse(); = - Akonadi::Item::Flags flags =3D m_maildir.readEntryFlags( entry ); + Akonadi::Item::Flags flags =3D m_maildir.readEntryFlags( fileName ); Q_FOREACH ( const Akonadi::Item::Flag &flag, flags ) { item.setFlag( flag ); } = item.setPayload( KMime::Message::Ptr( msg ) ); = - m_nextIndex =3D index + 1; KJob *job =3D 0; - if ( m_localItems.contains( entry ) ) { // modification - item.setId( m_localItems.value( entry ).id() ); + if ( m_localItems.contains( fileName ) ) { // modification + item.setId( m_localItems.value( fileName ).id() ); job =3D new Akonadi::ItemModifyJob( item, transaction() ); - m_localItems.remove( entry ); + m_localItems.remove( fileName ); } else { // new item job =3D new Akonadi::ItemCreateJob( item, m_collection, transaction() = ); } @@ -131,11 +138,13 @@ void RetrieveItemsJob::processEntry(qint64 index) = void RetrieveItemsJob::processEntryDone( KJob* ) { - processEntry( m_nextIndex ); + processEntry(); } = void RetrieveItemsJob::entriesProcessed() { + delete m_entryIterator; + m_entryIterator =3D 0; if ( !m_localItems.isEmpty() ) { Akonadi::ItemDeleteJob *job =3D new Akonadi::ItemDeleteJob( m_localIte= ms.values(), transaction() ); m_maildir.removeCachedKeys( m_localItems.keys() ); diff --git a/resources/maildir/retrieveitemsjob.h b/resources/maildir/retri= eveitemsjob.h index 60f3602..538d5ad 100644 --- a/resources/maildir/retrieveitemsjob.h +++ b/resources/maildir/retrieveitemsjob.h @@ -26,6 +26,7 @@ = #include "maildir.h" = +class QDirIterator; namespace Akonadi { class TransactionSequence; @@ -52,7 +53,7 @@ class RetrieveItemsJob : public Akonadi::Job private slots: void localListDone( KJob *job ); void transactionDone( KJob *job ); - void processEntry( qint64 index ); + void processEntry(); void processEntryDone( KJob * ); = private: @@ -61,10 +62,9 @@ class RetrieveItemsJob : public Akonadi::Job QHash m_localItems; QString m_mimeType; Akonadi::TransactionSequence *m_transaction; - QStringList m_entryList; + QDirIterator *m_entryIterator; qint64 m_previousMtime; qint64 m_highestMtime; - qint64 m_nextIndex; QString m_listingPath; }; =20