00001
00002
00003
00004
00005
#ifdef HAVE_CONFIG_H
00006
#include <config.h>
00007
#endif
00008
00009
#include "kmfiltermgr.h"
00010
00011
00012
#include "filterlog.h"
00013
using KMail::FilterLog;
00014
#include "kmfilterdlg.h"
00015
#include "kmfolderindex.h"
00016
#include "messageproperty.h"
00017
using KMail::MessageProperty;
00018
00019
00020
#include <kdebug.h>
00021
#include <klocale.h>
00022
#include <kconfig.h>
00023
00024
00025
#include <qregexp.h>
00026
00027
00028
#include <assert.h>
00029
00030
00031
00032 KMFilterMgr::KMFilterMgr(
bool popFilter )
00033 :
QPtrList<KMFilter>(),
00034 mEditDialog( 0 ),
00035 bPopFilter( popFilter ),
00036 mShowLater( false ),
00037 mRefCount( 0 )
00038 {
00039
if (bPopFilter)
00040 kdDebug(5006) <<
"pPopFilter set" << endl;
00041 setAutoDelete(TRUE);
00042 connect( kmkernel, SIGNAL( folderRemoved(
KMFolder* ) ),
00043
this, SLOT( slotFolderRemoved(
KMFolder* ) ) );
00044 }
00045
00046
00047
00048 KMFilterMgr::~KMFilterMgr()
00049 {
00050 deref(
true);
00051 writeConfig(FALSE);
00052 }
00053
00054
00055
00056
void KMFilterMgr::readConfig(
void)
00057 {
00058 KConfig* config = KMKernel::config();
00059
int numFilters;
00060
QString grpName;
00061
00062 clear();
00063
00064 KConfigGroupSaver saver(config,
"General");
00065
00066
if (bPopFilter) {
00067 numFilters = config->readNumEntry(
"popfilters",0);
00068 mShowLater = config->readNumEntry(
"popshowDLmsgs",0);
00069 }
else {
00070 numFilters = config->readNumEntry(
"filters",0);
00071 }
00072
00073
for (
int i=0 ; i < numFilters ; ++i ) {
00074 grpName.sprintf(
"%s #%d", (bPopFilter ?
"PopFilter" :
"Filter") , i);
00075 KConfigGroupSaver saver(config, grpName);
00076 KMFilter * filter =
new KMFilter(config, bPopFilter);
00077 filter->purify();
00078
if ( filter->isEmpty() ) {
00079
#ifndef NDEBUG
00080
kdDebug(5006) <<
"KMFilter::readConfig: filter\n" << filter->asString()
00081 <<
"is empty!" << endl;
00082
#endif
00083
delete filter;
00084 }
else
00085 append(filter);
00086 }
00087 }
00088
00089
00090
00091
void KMFilterMgr::writeConfig(
bool withSync)
00092 {
00093 KConfig* config = KMKernel::config();
00094
00095
00096
QStringList filterGroups =
00097 config->groupList().grep(
QRegExp( bPopFilter ?
"PopFilter #\\d+" :
"Filter #\\d+" ) );
00098
for ( QStringList::Iterator it = filterGroups.begin() ;
00099 it != filterGroups.end() ; ++it )
00100 config->deleteGroup( *it );
00101
00102
00103
int i = 0;
00104
QString grpName;
00105
for (
QPtrListIterator<KMFilter> it(*
this) ; it.current() ; ++it )
00106
if ( !(*it)->isEmpty() ) {
00107
if ( bPopFilter )
00108 grpName.sprintf(
"PopFilter #%d", i);
00109
else
00110 grpName.sprintf(
"Filter #%d", i);
00111 KConfigGroupSaver saver(config, grpName);
00112 (*it)->writeConfig(config);
00113 ++i;
00114 }
00115
00116 KConfigGroupSaver saver(config,
"General");
00117
if (bPopFilter) {
00118 config->writeEntry(
"popfilters", i);
00119 config->writeEntry(
"popshowDLmsgs", mShowLater);
00120 }
else
00121 config->writeEntry(
"filters", i);
00122
00123
if (withSync) config->sync();
00124 }
00125
00126
00127
int KMFilterMgr::processPop( KMMessage * msg )
const {
00128
for (
QPtrListIterator<KMFilter> it( *
this ) ; it.current() ; ++it )
00129
if ( (*it)->pattern()->matches( msg ) )
00130
return (*it)->action();
00131
return NoAction;
00132 }
00133
00134
bool KMFilterMgr::beginFiltering(KMMsgBase *msgBase)
const
00135
{
00136
if (MessageProperty::filtering( msgBase ))
00137
return false;
00138 MessageProperty::setFiltering( msgBase,
true );
00139 MessageProperty::setFilterFolder( msgBase, 0 );
00140
if (
FilterLog::instance()->
isLogging() ) {
00141
FilterLog::instance()->
addSeparator();
00142 }
00143
return true;
00144 }
00145
00146
int KMFilterMgr::moveMessage(KMMessage *msg)
const
00147
{
00148
if (MessageProperty::filterFolder(msg)->moveMsg( msg ) == 0) {
00149
if ( kmkernel->folderIsTrash( MessageProperty::filterFolder( msg )))
00150
KMFilterAction::sendMDN( msg, KMime::MDN::Deleted );
00151 }
else {
00152 kdDebug(5006) <<
"KMfilterAction - couldn't move msg" << endl;
00153
return 2;
00154 }
00155
return 0;
00156 }
00157
00158
void KMFilterMgr::endFiltering(KMMsgBase *msgBase)
const
00159
{
00160
KMFolder *parent = msgBase->parent();
00161
if ( parent ) {
00162
if ( parent == MessageProperty::filterFolder( msgBase ) ) {
00163 parent->
take( parent->
find( msgBase ) );
00164 }
00165
else if ( ! MessageProperty::filterFolder( msgBase ) ) {
00166
int index = parent->
find( msgBase );
00167 KMMessage *msg = parent->
getMsg( index );
00168 parent->
take( index );
00169 parent->
addMsgKeepUID( msg );
00170 }
00171 }
00172 MessageProperty::setFiltering( msgBase,
false );
00173 }
00174
00175
int KMFilterMgr::process( KMMessage * msg,
const KMFilter * filter ) {
00176
if ( !msg || !filter || !beginFiltering( msg ))
00177
return 1;
00178
bool stopIt =
false;
00179
int result = 1;
00180
00181
if (
FilterLog::instance()->
isLogging() ) {
00182
QString logText( i18n(
"<b>Evaluating filter rules:</b> " ) );
00183 logText.append( filter->pattern()->asString() );
00184
FilterLog::instance()->
add( logText, FilterLog::patternDesc );
00185 }
00186
00187
if (filter->pattern()->matches( msg )) {
00188
if (
FilterLog::instance()->
isLogging() ) {
00189
FilterLog::instance()->
add( i18n(
"<b>Filter rules have matched.</b>" ),
00190 FilterLog::patternResult );
00191 }
00192
if (filter->execActions( msg, stopIt ) == KMFilter::CriticalError)
00193
return 2;
00194
00195
KMFolder *folder = MessageProperty::filterFolder( msg );
00196
00197 endFiltering( msg );
00198
if (folder) {
00199 tempOpenFolder( folder );
00200 result = folder->
moveMsg( msg );
00201 }
00202 }
else {
00203 endFiltering( msg );
00204 result = 1;
00205 }
00206
return result;
00207 }
00208
00209
int KMFilterMgr::process( KMMessage * msg, FilterSet set ) {
00210
if ( bPopFilter )
00211
return processPop( msg );
00212
00213
if ( set == NoSet ) {
00214 kdDebug(5006) <<
"KMFilterMgr: process() called with not filter set selected"
00215 << endl;
00216
return 1;
00217 }
00218
00219
bool stopIt =
false;
00220
00221
if (!beginFiltering( msg ))
00222
return 1;
00223
for (
QPtrListIterator<KMFilter> it(*
this) ; !stopIt && it.current() ; ++it ) {
00224
00225
if ( ( (set&Outbound) && (*it)->applyOnOutbound() ) ||
00226 ( (set&Inbound) && (*it)->applyOnInbound() ) ||
00227 ( (set&Explicit) && (*it)->applyOnExplicit() ) ) {
00228
00229
00230
if (
FilterLog::instance()->
isLogging() ) {
00231
QString logText( i18n(
"<b>Evaluating filter rules:</b> " ) );
00232 logText.append( (*it)->pattern()->asString() );
00233
FilterLog::instance()->
add( logText, FilterLog::patternDesc );
00234 }
00235
if ( (*it)->pattern()->matches( msg ) ) {
00236
00237
if (
FilterLog::instance()->
isLogging() ) {
00238
FilterLog::instance()->
add( i18n(
"<b>Filter rules have matched.</b>" ),
00239 FilterLog::patternResult );
00240 }
00241
00242
if ( (*it)->execActions(msg, stopIt) == KMFilter::CriticalError )
00243
return 2;
00244 }
00245 }
00246 }
00247
00248
KMFolder *folder = MessageProperty::filterFolder( msg );
00249 endFiltering( msg );
00250
if (folder) {
00251 tempOpenFolder( folder );
00252 folder->
moveMsg(msg);
00253
return 0;
00254 }
00255
return 1;
00256 }
00257
00258
00259
00260
void KMFilterMgr::ref(
void)
00261 {
00262 mRefCount++;
00263 }
00264
00265
00266
void KMFilterMgr::deref(
bool force)
00267 {
00268
if (!force)
00269 mRefCount--;
00270
if (mRefCount < 0)
00271 mRefCount = 0;
00272
if (mRefCount && !force)
00273
return;
00274
QPtrListIterator<KMFolder> it(mOpenFolders);
00275
for ( it.toFirst() ; it.current() ; ++it )
00276 (*it)->close();
00277 mOpenFolders.clear();
00278 }
00279
00280
00281
00282
int KMFilterMgr::tempOpenFolder(
KMFolder* aFolder)
00283 {
00284 assert( aFolder );
00285
00286
int rc = aFolder->
open();
00287
if (rc)
return rc;
00288
00289 mOpenFolders.append( aFolder );
00290
return 0;
00291 }
00292
00293
00294
00295
void KMFilterMgr::openDialog(
QWidget * )
00296 {
00297
if( !mEditDialog )
00298 {
00299
00300
00301
00302
00303 mEditDialog =
new KMFilterDlg( 0,
"filterdialog", bPopFilter );
00304 }
00305 mEditDialog->show();
00306 }
00307
00308
00309
00310
void KMFilterMgr::createFilter(
const QCString & field,
const QString & value )
00311 {
00312 openDialog( 0 );
00313 mEditDialog->createFilter( field, value );
00314 }
00315
00316
00317
00318
void KMFilterMgr::appendFilters(
const QPtrList<KMFilter> filters )
00319 {
00320 beginUpdate();
00321
QPtrListIterator<KMFilter> it(filters);
00322
for ( it.toFirst(); it.current() ; ++it )
00323 append( *it );
00324 writeConfig( TRUE );
00325 endUpdate();
00326 }
00327
00328
00329
void KMFilterMgr::slotFolderRemoved(
KMFolder * aFolder )
00330 {
00331 folderRemoved( aFolder, 0 );
00332 }
00333
00334
00335
bool KMFilterMgr::folderRemoved(
KMFolder* aFolder,
KMFolder* aNewFolder)
00336 {
00337
bool rem = FALSE;
00338
00339
QPtrListIterator<KMFilter> it(*
this);
00340
for ( it.toFirst() ; it.current() ; ++it )
00341
if ( (*it)->folderRemoved(aFolder, aNewFolder) ) rem=TRUE;
00342
00343
return rem;
00344 }
00345
00346
00347
00348
#ifndef NDEBUG
00349
void KMFilterMgr::dump(
void)
00350 {
00351
QPtrListIterator<KMFilter> it(*
this);
00352
for ( it.toFirst() ; it.current() ; ++it )
00353 {
00354 kdDebug(5006) << (*it)->asString() << endl;
00355 }
00356 }
00357
#endif
00358
00359
00360
void KMFilterMgr::endUpdate(
void)
00361 {
00362 emit filterListUpdated();
00363 }
00364
00365
#include "kmfiltermgr.moc"