00001
00002 #ifdef HAVE_CONFIG_H
00003 #include <config.h>
00004 #endif
00005
00006 #include "config.h"
00007 #include "kmkernel.h"
00008
00009 #include <weaver.h>
00010 #include <weaverlogger.h>
00011
00012 #include "globalsettings.h"
00013 #include "broadcaststatus.h"
00014 using KPIM::BroadcastStatus;
00015 #include "kmstartup.h"
00016 #include "index.h"
00017 #include "kmmainwin.h"
00018 #include "composer.h"
00019 #include "kmmsgpart.h"
00020 #include "kmreadermainwin.h"
00021 #include "kmfoldermgr.h"
00022 #include "kmfoldercachedimap.h"
00023 #include "kmacctcachedimap.h"
00024 #include "kmfiltermgr.h"
00025 #include "kmfilteraction.h"
00026 #define REALLY_WANT_KMSENDER
00027 #include "kmsender.h"
00028 #undef REALLY_WANT_KMSENDER
00029 #include "undostack.h"
00030 #include "accountmanager.h"
00031 using KMail::AccountManager;
00032 #include <libkdepim/kfileio.h>
00033 #include "kmversion.h"
00034 #include "kmreaderwin.h"
00035 #include "kmmainwidget.h"
00036 #include "kmfoldertree.h"
00037 #include "recentaddresses.h"
00038 using KRecentAddress::RecentAddresses;
00039 #include "kmmsgdict.h"
00040 #include <libkpimidentities/identity.h>
00041 #include <libkpimidentities/identitymanager.h>
00042 #include "configuredialog.h"
00043 #include "kmcommands.h"
00044 #include "kmsystemtray.h"
00045 #include "transportmanager.h"
00046
00047 #include <kwin.h>
00048 #include "kmailicalifaceimpl.h"
00049 #include "mailserviceimpl.h"
00050 using KMail::MailServiceImpl;
00051 #include "mailcomposerIface.h"
00052 #include "folderIface.h"
00053 using KMail::FolderIface;
00054 #include "jobscheduler.h"
00055 #include "templateparser.h"
00056
00057 #include <kapplication.h>
00058 #include <kmessagebox.h>
00059 #include <knotifyclient.h>
00060 #include <kstaticdeleter.h>
00061 #include <kstandarddirs.h>
00062 #include <kconfig.h>
00063 #include <kprogress.h>
00064 #include <kpassivepopup.h>
00065 #include <dcopclient.h>
00066 #include <ksystemtray.h>
00067 #include <kpgp.h>
00068 #include <kdebug.h>
00069 #include <kio/netaccess.h>
00070 #include <kwallet.h>
00071 using KWallet::Wallet;
00072 #include "actionscheduler.h"
00073
00074 #include <qutf7codec.h>
00075 #include <qvbox.h>
00076 #include <qdir.h>
00077 #include <qwidgetlist.h>
00078 #include <qobjectlist.h>
00079
00080 #include <sys/types.h>
00081 #include <dirent.h>
00082 #include <sys/stat.h>
00083 #include <unistd.h>
00084 #include <stdio.h>
00085 #include <stdlib.h>
00086 #include <assert.h>
00087
00088 #include <X11/Xlib.h>
00089 #include <fixx11h.h>
00090 #include <kcmdlineargs.h>
00091 #include <kstartupinfo.h>
00092
00093 KMKernel *KMKernel::mySelf = 0;
00094
00095
00096
00097
00098 KMKernel::KMKernel (QObject *parent, const char *name) :
00099 DCOPObject("KMailIface"), QObject(parent, name),
00100 mIdentityManager(0), mConfigureDialog(0),
00101 mContextMenuShown( false ), mWallet( 0 )
00102 {
00103 kdDebug(5006) << "KMKernel::KMKernel" << endl;
00104 mySelf = this;
00105 the_startingUp = true;
00106 closed_by_user = true;
00107 the_firstInstance = true;
00108 the_msgIndex = 0;
00109
00110 the_inboxFolder = 0;
00111 the_outboxFolder = 0;
00112 the_sentFolder = 0;
00113 the_trashFolder = 0;
00114 the_draftsFolder = 0;
00115 the_templatesFolder = 0;
00116
00117 the_folderMgr = 0;
00118 the_imapFolderMgr = 0;
00119 the_dimapFolderMgr = 0;
00120 the_searchFolderMgr = 0;
00121 the_undoStack = 0;
00122 the_acctMgr = 0;
00123 the_filterMgr = 0;
00124 the_popFilterMgr = 0;
00125 the_filterActionDict = 0;
00126 the_msgSender = 0;
00127 mWin = 0;
00128 mMailCheckAborted = false;
00129
00130
00131 KMKernel::config();
00132
00133
00134
00135 GlobalSettings::self();
00136
00137
00138 mICalIface = new KMailICalIfaceImpl();
00139
00140 mJobScheduler = new JobScheduler( this );
00141
00142 mXmlGuiInstance = 0;
00143
00144 new Kpgp::Module();
00145
00146
00147
00148 if ( !QTextCodec::codecForName("utf-7") ) {
00149 kdDebug(5006) << "No Qt-native utf-7 codec found; registering QUtf7Codec from libkdenetwork" << endl;
00150 (void) new QUtf7Codec();
00151 }
00152
00153
00154
00155
00156 if ( QCString(QTextCodec::codecForLocale()->name()).lower() == "eucjp" )
00157 {
00158 netCodec = QTextCodec::codecForName("jis7");
00159
00160
00161
00162 } else {
00163 netCodec = QTextCodec::codecForLocale();
00164 }
00165 mMailService = new MailServiceImpl();
00166
00167 connectDCOPSignal( 0, 0, "kmailSelectFolder(QString)",
00168 "selectFolder(QString)", false );
00169 }
00170
00171 KMKernel::~KMKernel ()
00172 {
00173 QMap<KIO::Job*, putData>::Iterator it = mPutJobs.begin();
00174 while ( it != mPutJobs.end() )
00175 {
00176 KIO::Job *job = it.key();
00177 mPutJobs.remove( it );
00178 job->kill();
00179 it = mPutJobs.begin();
00180 }
00181
00182 delete mICalIface;
00183 mICalIface = 0;
00184 delete mMailService;
00185 mMailService = 0;
00186
00187 GlobalSettings::self()->writeConfig();
00188 delete mWallet;
00189 mWallet = 0;
00190 mySelf = 0;
00191 kdDebug(5006) << "KMKernel::~KMKernel" << endl;
00192 }
00193
00194 bool KMKernel::handleCommandLine( bool noArgsOpensReader )
00195 {
00196 QString to, cc, bcc, subj, body;
00197 QCStringList customHeaders;
00198 KURL messageFile;
00199 KURL::List attachURLs;
00200 bool mailto = false;
00201 bool checkMail = false;
00202 bool viewOnly = false;
00203 bool calledWithSession = false;
00204
00205
00206 KCmdLineArgs *args = KCmdLineArgs::parsedArgs();
00207 if (args->getOption("subject"))
00208 {
00209 subj = QString::fromLocal8Bit(args->getOption("subject"));
00210
00211
00212
00213
00214
00215
00216
00217 if ( subj == "ession" ) {
00218 subj = QString::null;
00219 calledWithSession = true;
00220 }
00221 else
00222 mailto = true;
00223 }
00224
00225 if (args->getOption("cc"))
00226 {
00227 mailto = true;
00228 cc = QString::fromLocal8Bit(args->getOption("cc"));
00229 }
00230
00231 if (args->getOption("bcc"))
00232 {
00233 mailto = true;
00234 bcc = QString::fromLocal8Bit(args->getOption("bcc"));
00235 }
00236
00237 if (args->getOption("msg"))
00238 {
00239 mailto = true;
00240 messageFile.setPath( QString::fromLocal8Bit(args->getOption("msg")) );
00241 }
00242
00243 if (args->getOption("body"))
00244 {
00245 mailto = true;
00246 body = QString::fromLocal8Bit(args->getOption("body"));
00247 }
00248
00249 QCStringList attachList = args->getOptionList("attach");
00250 if (!attachList.isEmpty())
00251 {
00252 mailto = true;
00253 for ( QCStringList::Iterator it = attachList.begin() ; it != attachList.end() ; ++it )
00254 if ( !(*it).isEmpty() )
00255 attachURLs += KURL( QString::fromLocal8Bit( *it ) );
00256 }
00257
00258 customHeaders = args->getOptionList("header");
00259
00260 if (args->isSet("composer"))
00261 mailto = true;
00262
00263 if (args->isSet("check"))
00264 checkMail = true;
00265
00266 if ( args->getOption( "view" ) ) {
00267 viewOnly = true;
00268 const QString filename =
00269 QString::fromLocal8Bit( args->getOption( "view" ) );
00270 messageFile = KURL::fromPathOrURL( filename );
00271 if ( !messageFile.isValid() ) {
00272 messageFile = KURL();
00273 messageFile.setPath( filename );
00274 }
00275 }
00276
00277 if ( !calledWithSession ) {
00278
00279
00280 for(int i= 0; i < args->count(); i++)
00281 {
00282 if (strncasecmp(args->arg(i),"mailto:",7)==0)
00283 to += args->url(i).path() + ", ";
00284 else {
00285 QString tmpArg = QString::fromLocal8Bit( args->arg(i) );
00286 KURL url( tmpArg );
00287 if ( url.isValid() )
00288 attachURLs += url;
00289 else
00290 to += tmpArg + ", ";
00291 }
00292 mailto = true;
00293 }
00294 if ( !to.isEmpty() ) {
00295
00296 to.truncate( to.length() - 2 );
00297 }
00298 }
00299
00300 if ( !calledWithSession )
00301 args->clear();
00302
00303 if ( !noArgsOpensReader && !mailto && !checkMail && !viewOnly )
00304 return false;
00305
00306 if ( viewOnly )
00307 viewMessage( messageFile );
00308 else
00309 action( mailto, checkMail, to, cc, bcc, subj, body, messageFile,
00310 attachURLs, customHeaders );
00311 return true;
00312 }
00313
00314
00315
00316
00317 void KMKernel::checkMail ()
00318 {
00319 if ( !kmkernel->askToGoOnline() )
00320 return;
00321 kmkernel->acctMgr()->checkMail(false);
00322 }
00323
00324 QStringList KMKernel::accounts()
00325 {
00326 if( kmkernel->acctMgr() )
00327 return kmkernel->acctMgr()->getAccounts();
00328 return QStringList();
00329 }
00330
00331 void KMKernel::checkAccount (const QString &account)
00332 {
00333 kdDebug(5006) << "KMKernel::checkMail called" << endl;
00334
00335 KMAccount* acct = kmkernel->acctMgr()->findByName(account);
00336 if (acct)
00337 kmkernel->acctMgr()->singleCheckMail(acct, false);
00338 }
00339
00340 void KMKernel::loadProfile( const QString& )
00341 {
00342 }
00343
00344 void KMKernel::saveToProfile( const QString& ) const
00345 {
00346 }
00347
00348 void KMKernel::openReader( bool onlyCheck )
00349 {
00350 mWin = 0;
00351 KMainWindow *ktmw = 0;
00352 kdDebug(5006) << "KMKernel::openReader called" << endl;
00353
00354 if (KMainWindow::memberList)
00355 for (ktmw = KMainWindow::memberList->first(); ktmw;
00356 ktmw = KMainWindow::memberList->next())
00357 if (ktmw->isA("KMMainWin"))
00358 break;
00359
00360 bool activate;
00361 if (ktmw) {
00362 mWin = (KMMainWin *) ktmw;
00363 activate = !onlyCheck;
00364 if ( activate )
00365 mWin->show();
00366 } else {
00367 mWin = new KMMainWin;
00368 mWin->show();
00369 activate = false;
00370 }
00371
00372 if ( activate ) {
00373
00374
00375 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00376 KStartupInfo::setNewStartupId( mWin, kapp->startupId() );
00377 #endif
00378 }
00379 }
00380
00381 int KMKernel::openComposer (const QString &to, const QString &cc,
00382 const QString &bcc, const QString &subject,
00383 const QString &body, int hidden,
00384 const KURL &messageFile,
00385 const KURL::List &attachURLs,
00386 const QCStringList &customHeaders)
00387 {
00388 kdDebug(5006) << "KMKernel::openComposer called" << endl;
00389 KMMessage *msg = new KMMessage;
00390 msg->initHeader();
00391 msg->setCharset("utf-8");
00392
00393
00394 if (!to.isEmpty())
00395 msg->setTo( KMMsgBase::decodeRFC2047String( to.latin1() ) );
00396 if (!cc.isEmpty())
00397 msg->setCc( KMMsgBase::decodeRFC2047String( cc.latin1() ) );
00398 if (!bcc.isEmpty())
00399 msg->setBcc( KMMsgBase::decodeRFC2047String( bcc.latin1() ) );
00400 if (!subject.isEmpty()) msg->setSubject(subject);
00401 if (!messageFile.isEmpty() && messageFile.isLocalFile()) {
00402 QCString str = KPIM::kFileToString( messageFile.path(), true, false );
00403 if( !str.isEmpty() ) {
00404 msg->setBody( QString::fromLocal8Bit( str ).utf8() );
00405 } else {
00406 TemplateParser parser( msg, TemplateParser::NewMessage,
00407 "", false, false, false, false );
00408 parser.process( NULL, NULL );
00409 }
00410 }
00411 else if (!body.isEmpty())
00412 {
00413 msg->setBody(body.utf8());
00414 }
00415 else
00416 {
00417 TemplateParser parser( msg, TemplateParser::NewMessage,
00418 "", false, false, false, false );
00419 parser.process( NULL, NULL );
00420 }
00421
00422 if (!customHeaders.isEmpty())
00423 {
00424 for ( QCStringList::ConstIterator it = customHeaders.begin() ; it != customHeaders.end() ; ++it )
00425 if ( !(*it).isEmpty() )
00426 {
00427 const int pos = (*it).find( ':' );
00428 if ( pos > 0 )
00429 {
00430 QCString header, value;
00431 header = (*it).left( pos ).stripWhiteSpace();
00432 value = (*it).mid( pos+1 ).stripWhiteSpace();
00433 if ( !header.isEmpty() && !value.isEmpty() )
00434 msg->setHeaderField( header, value );
00435 }
00436 }
00437 }
00438
00439 KMail::Composer * cWin = KMail::makeComposer( msg );
00440 cWin->setCharset("", true);
00441 for ( KURL::List::ConstIterator it = attachURLs.begin() ; it != attachURLs.end() ; ++it )
00442 cWin->addAttach((*it));
00443 if (hidden == 0) {
00444 cWin->show();
00445
00446
00447 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00448 KStartupInfo::setNewStartupId( cWin, kapp->startupId() );
00449 #endif
00450 }
00451 return 1;
00452 }
00453
00454
00455 int KMKernel::openComposer (const QString &to, const QString &cc,
00456 const QString &bcc, const QString &subject,
00457 const QString &body, int hidden,
00458 const QString &attachName,
00459 const QCString &attachCte,
00460 const QCString &attachData,
00461 const QCString &attachType,
00462 const QCString &attachSubType,
00463 const QCString &attachParamAttr,
00464 const QString &attachParamValue,
00465 const QCString &attachContDisp )
00466 {
00467 kdDebug(5006) << "KMKernel::openComposer called (deprecated version)" << endl;
00468
00469 return openComposer ( to, cc, bcc, subject, body, hidden,
00470 attachName, attachCte, attachData,
00471 attachType, attachSubType, attachParamAttr,
00472 attachParamValue, attachContDisp, QCString() );
00473 }
00474
00475 int KMKernel::openComposer (const QString &to, const QString &cc,
00476 const QString &bcc, const QString &subject,
00477 const QString &body, int hidden,
00478 const QString &attachName,
00479 const QCString &attachCte,
00480 const QCString &attachData,
00481 const QCString &attachType,
00482 const QCString &attachSubType,
00483 const QCString &attachParamAttr,
00484 const QString &attachParamValue,
00485 const QCString &attachContDisp,
00486 const QCString &attachCharset )
00487 {
00488 kdDebug(5006) << "KMKernel::openComposer()" << endl;
00489
00490 KMMessage *msg = new KMMessage;
00491 KMMessagePart *msgPart = 0;
00492 msg->initHeader();
00493 msg->setCharset( "utf-8" );
00494 if ( !cc.isEmpty() ) msg->setCc(cc);
00495 if ( !bcc.isEmpty() ) msg->setBcc(bcc);
00496 if ( !subject.isEmpty() ) msg->setSubject(subject);
00497 if ( !to.isEmpty() ) msg->setTo(to);
00498 if ( !body.isEmpty() ) {
00499 msg->setBody(body.utf8());
00500 } else {
00501 TemplateParser parser( msg, TemplateParser::NewMessage,
00502 "", false, false, false, false );
00503 parser.process( NULL, NULL );
00504 }
00505
00506 bool iCalAutoSend = false;
00507 bool noWordWrap = false;
00508 bool isICalInvitation = false;
00509 KConfigGroup options( config(), "Groupware" );
00510 if ( !attachData.isEmpty() ) {
00511 isICalInvitation = attachName == "cal.ics" &&
00512 attachType == "text" &&
00513 attachSubType == "calendar" &&
00514 attachParamAttr == "method";
00515
00516 if ( isICalInvitation && bcc.isEmpty() )
00517 msg->setBcc( "" );
00518 if ( isICalInvitation &&
00519 GlobalSettings::self()->legacyBodyInvites() ) {
00520
00521 msg->setBody( attachData );
00522 msg->setHeaderField( "Content-Type",
00523 QString( "text/calendar; method=%1; "
00524 "charset=\"utf-8\"" ).
00525 arg( attachParamValue ) );
00526
00527 iCalAutoSend = true;
00528 noWordWrap = true;
00529 } else {
00530
00531 msgPart = new KMMessagePart;
00532 msgPart->setName( attachName );
00533 msgPart->setCteStr( attachCte );
00534 msgPart->setBodyEncoded( attachData );
00535 msgPart->setTypeStr( attachType );
00536 msgPart->setSubtypeStr( attachSubType );
00537 msgPart->setParameter( attachParamAttr, attachParamValue );
00538 if( ! GlobalSettings::self()->exchangeCompatibleInvitations() ) {
00539 msgPart->setContentDisposition( attachContDisp );
00540 }
00541 if( !attachCharset.isEmpty() ) {
00542
00543
00544 msgPart->setCharset( attachCharset );
00545 }
00546
00547 KConfigGroup options( config(), "Groupware" );
00548 iCalAutoSend = options.readBoolEntry( "AutomaticSending", true );
00549 }
00550 }
00551
00552 KMail::Composer * cWin = KMail::makeComposer();
00553 cWin->setMsg( msg, !isICalInvitation );
00554 cWin->setSigningAndEncryptionDisabled( isICalInvitation
00555 && GlobalSettings::self()->legacyBodyInvites() );
00556 cWin->setAutoDelete( true );
00557 if( noWordWrap )
00558 cWin->disableWordWrap();
00559 else
00560 cWin->setCharset( "", true );
00561 if ( msgPart )
00562 cWin->addAttach(msgPart);
00563
00564 if ( hidden == 0 && !iCalAutoSend ) {
00565 cWin->show();
00566
00567
00568 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00569 KStartupInfo::setNewStartupId( cWin, kapp->startupId() );
00570 #endif
00571 } else {
00572 cWin->setAutoDeleteWindow( true );
00573 cWin->slotSendNow();
00574 }
00575
00576 return 1;
00577 }
00578
00579 void KMKernel::setDefaultTransport( const QString & transport )
00580 {
00581 QStringList availTransports = KMail::TransportManager::transportNames();
00582 QStringList::const_iterator it = availTransports.find( transport );
00583 if ( it == availTransports.end() ) {
00584 kdWarning() << "The transport you entered is not available" << endl;
00585 return;
00586 }
00587 GlobalSettings::self()->setDefaultTransport( transport );
00588 }
00589
00590 DCOPRef KMKernel::openComposer(const QString &to, const QString &cc,
00591 const QString &bcc, const QString &subject,
00592 const QString &body,bool hidden)
00593 {
00594 KMMessage *msg = new KMMessage;
00595 msg->initHeader();
00596 msg->setCharset("utf-8");
00597 if (!cc.isEmpty()) msg->setCc(cc);
00598 if (!bcc.isEmpty()) msg->setBcc(bcc);
00599 if (!subject.isEmpty()) msg->setSubject(subject);
00600 if (!to.isEmpty()) msg->setTo(to);
00601 if (!body.isEmpty()) {
00602 msg->setBody(body.utf8());
00603 } else {
00604 TemplateParser parser( msg, TemplateParser::NewMessage,
00605 "", false, false, false, false );
00606 parser.process( NULL, NULL );
00607 }
00608
00609 KMail::Composer * cWin = KMail::makeComposer( msg );
00610 cWin->setCharset("", true);
00611 if (!hidden) {
00612 cWin->show();
00613
00614
00615 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00616 KStartupInfo::setNewStartupId( cWin, kapp->startupId() );
00617 #endif
00618 }
00619
00620 return DCOPRef( cWin->asMailComposerIFace() );
00621 }
00622
00623 DCOPRef KMKernel::newMessage(const QString &to,
00624 const QString &cc,
00625 const QString &bcc,
00626 bool hidden,
00627 bool useFolderId,
00628 const KURL & ,
00629 const KURL &attachURL)
00630 {
00631 KMail::Composer * win = 0;
00632 KMMessage *msg = new KMMessage;
00633 KMFolder *folder = NULL;
00634 uint id;
00635
00636 if ( useFolderId ) {
00637
00638 folder = currentFolder();
00639 id = folder ? folder->identity() : 0;
00640 msg->initHeader( id );
00641 } else {
00642 msg->initHeader();
00643 }
00644 msg->setCharset("utf-8");
00645
00646 if (!to.isEmpty()) msg->setTo(to);
00647 if (!cc.isEmpty()) msg->setCc(cc);
00648 if (!bcc.isEmpty()) msg->setBcc(bcc);
00649
00650 if ( useFolderId ) {
00651 TemplateParser parser( msg, TemplateParser::NewMessage,
00652 "", false, false, false, false );
00653 parser.process( NULL, folder );
00654 win = makeComposer( msg, id );
00655 } else {
00656 TemplateParser parser( msg, TemplateParser::NewMessage,
00657 "", false, false, false, false );
00658 parser.process( NULL, folder );
00659 win = makeComposer( msg );
00660 }
00661
00662
00663 if(!attachURL.isEmpty() && attachURL.isValid()) {
00664 win->addAttach(attachURL);
00665 }
00666
00667
00668 if(!hidden) {
00669 win->show();
00670 }
00671 return DCOPRef( win->asMailComposerIFace() );
00672 }
00673
00674 int KMKernel::viewMessage( const KURL & messageFile )
00675 {
00676 KMOpenMsgCommand *openCommand = new KMOpenMsgCommand( 0, messageFile );
00677
00678 openCommand->start();
00679
00680 return 1;
00681 }
00682
00683 int KMKernel::sendCertificate( const QString& to, const QByteArray& certData )
00684 {
00685 KMMessage *msg = new KMMessage;
00686 msg->initHeader();
00687 msg->setCharset("utf-8");
00688 msg->setSubject( i18n( "Certificate Signature Request" ) );
00689 if (!to.isEmpty()) msg->setTo(to);
00690
00691 msg->setBody( i18n( "Please create a certificate from attachment and return to sender." ).utf8() );
00692
00693 KMail::Composer * cWin = KMail::makeComposer( msg );
00694 cWin->setCharset("", true);
00695 cWin->slotSetAlwaysSend( true );
00696 if (!certData.isEmpty()) {
00697 KMMessagePart *msgPart = new KMMessagePart;
00698 msgPart->setName("smime.p10");
00699 msgPart->setCteStr("base64");
00700 msgPart->setBodyEncodedBinary(certData);
00701 msgPart->setTypeStr("application");
00702 msgPart->setSubtypeStr("pkcs10");
00703 msgPart->setContentDisposition("attachment; filename=smime.p10");
00704 cWin->addAttach(msgPart);
00705 }
00706
00707 cWin->show();
00708 return 1;
00709 }
00710
00711 KMMsgStatus KMKernel::strToStatus(const QString &flags)
00712 {
00713 KMMsgStatus status = 0;
00714 if (!flags.isEmpty()) {
00715 for (uint n = 0; n < flags.length() ; n++) {
00716 switch (flags[n]) {
00717 case 'N':
00718 status |= KMMsgStatusNew;
00719 break;
00720 case 'U':
00721 status |= KMMsgStatusUnread;
00722 break;
00723 case 'O':
00724 status |= KMMsgStatusOld;
00725 break;
00726 case 'R':
00727 status |= KMMsgStatusRead;
00728 break;
00729 case 'D':
00730 status |= KMMsgStatusDeleted;
00731 break;
00732 case 'A':
00733 status |= KMMsgStatusReplied;
00734 break;
00735 case 'F':
00736 status |= KMMsgStatusForwarded;
00737 break;
00738 case 'Q':
00739 status |= KMMsgStatusQueued;
00740 break;
00741 case 'K':
00742 status |= KMMsgStatusTodo;
00743 break;
00744 case 'S':
00745 status |= KMMsgStatusSent;
00746 break;
00747 case 'G':
00748 status |= KMMsgStatusFlag;
00749 break;
00750 case 'W':
00751 status |= KMMsgStatusWatched;
00752 break;
00753 case 'I':
00754 status |= KMMsgStatusIgnored;
00755 break;
00756 case 'P':
00757 status |= KMMsgStatusSpam;
00758 break;
00759 case 'H':
00760 status |= KMMsgStatusHam;
00761 break;
00762 case 'T':
00763 status |= KMMsgStatusHasAttach;
00764 break;
00765 case 'C':
00766 status |= KMMsgStatusHasNoAttach;
00767 break;
00768 default:
00769 break;
00770 }
00771 }
00772 }
00773 return status;
00774 }
00775
00776 int KMKernel::dcopAddMessage( const QString & foldername, const QString & msgUrlString,
00777 const QString & MsgStatusFlags)
00778 {
00779 return dcopAddMessage(foldername, KURL(msgUrlString), MsgStatusFlags);
00780 }
00781
00782 int KMKernel::dcopAddMessage( const QString & foldername,const KURL & msgUrl,
00783 const QString & MsgStatusFlags)
00784 {
00785 kdDebug(5006) << "KMKernel::dcopAddMessage called" << endl;
00786
00787 if ( foldername.isEmpty() || foldername.startsWith("."))
00788 return -1;
00789
00790 int retval;
00791 bool readFolderMsgIds = false;
00792 QString _foldername = foldername.stripWhiteSpace();
00793 _foldername = _foldername.replace('\\',"");
00794
00795 if ( foldername != mAddMessageLastFolder ) {
00796 mAddMessageMsgIds.clear();
00797 readFolderMsgIds = true;
00798 mAddMessageLastFolder = foldername;
00799 }
00800
00801 if (!msgUrl.isEmpty() && msgUrl.isLocalFile()) {
00802
00803
00804
00805
00806
00807
00808
00809
00810 const QCString messageText =
00811 KPIM::kFileToString( msgUrl.path(), true, false );
00812 if ( messageText.isEmpty() )
00813 return -2;
00814
00815 KMMessage *msg = new KMMessage();
00816 msg->fromString( messageText );
00817
00818 if (readFolderMsgIds) {
00819 if ( foldername.contains("/")) {
00820 QString tmp_fname = "";
00821 KMFolder *folder = NULL;
00822 KMFolderDir *subfolder;
00823 bool root = true;
00824
00825 QStringList subFList = QStringList::split("/",_foldername,false);
00826
00827 for ( QStringList::Iterator it = subFList.begin(); it != subFList.end(); ++it ) {
00828 QString _newFolder = *it;
00829 if(_newFolder.startsWith(".")) return -1;
00830
00831 if(root) {
00832 folder = the_folderMgr->findOrCreate(*it, false);
00833 if (folder) {
00834 root = false;
00835 tmp_fname = "/" + *it;
00836 }
00837 else return -1;
00838 } else {
00839 subfolder = folder->createChildFolder();
00840 tmp_fname += "/" + *it;
00841 if(!the_folderMgr->getFolderByURL( tmp_fname )) {
00842 folder = the_folderMgr->createFolder(*it, false, folder->folderType(), subfolder);
00843 }
00844
00845 if(!(folder = the_folderMgr->getFolderByURL( tmp_fname ))) return -1;
00846 }
00847 }
00848
00849 mAddMsgCurrentFolder = the_folderMgr->getFolderByURL( tmp_fname );
00850 if(!folder) return -1;
00851
00852 } else {
00853 mAddMsgCurrentFolder = the_folderMgr->findOrCreate(_foldername, false);
00854 }
00855 }
00856
00857 if ( mAddMsgCurrentFolder ) {
00858 if (readFolderMsgIds) {
00859
00860
00861
00862
00863
00864
00865
00866
00867
00868
00869
00870
00871
00872
00873
00874
00875
00876
00877
00878
00879
00880
00881 int i;
00882
00883 mAddMsgCurrentFolder->open("dcopadd");
00884 for( i=0; i<mAddMsgCurrentFolder->count(); i++) {
00885 KMMsgBase *mb = mAddMsgCurrentFolder->getMsgBase(i);
00886 QString id = mb->msgIdMD5();
00887 if ( id.isEmpty() ) {
00888 id = mb->subject();
00889 if ( id.isEmpty() )
00890 id = mb->fromStrip();
00891 if ( id.isEmpty() )
00892 id = mb->toStrip();
00893
00894 id += mb->dateStr();
00895 }
00896
00897
00898 if ( !id.isEmpty() ) {
00899 mAddMessageMsgIds.append(id);
00900 }
00901 }
00902 mAddMsgCurrentFolder->close("dcopadd");
00903 }
00904
00905 QString msgId = msg->msgIdMD5();
00906 if ( msgId.isEmpty()) {
00907 msgId = msg->subject();
00908 if ( msgId.isEmpty() )
00909 msgId = msg->fromStrip();
00910 if ( msgId.isEmpty() )
00911 msgId = msg->toStrip();
00912
00913 msgId += msg->dateStr();
00914 }
00915
00916 int k = mAddMessageMsgIds.findIndex( msgId );
00917
00918
00919 if ( k == -1 ) {
00920 if ( !msgId.isEmpty() ) {
00921 mAddMessageMsgIds.append( msgId );
00922 }
00923
00924 if ( !MsgStatusFlags.isEmpty() ) {
00925 KMMsgStatus status = strToStatus(MsgStatusFlags);
00926 if (status) msg->setStatus(status);
00927 }
00928
00929 int index;
00930 if ( mAddMsgCurrentFolder->addMsg( msg, &index ) == 0 ) {
00931 mAddMsgCurrentFolder->unGetMsg( index );
00932 retval = 1;
00933 } else {
00934 retval =- 2;
00935 delete msg;
00936 msg = 0;
00937 }
00938 } else {
00939
00940 retval = -4;
00941 }
00942 } else {
00943 retval = -1;
00944 }
00945 } else {
00946 retval = -2;
00947 }
00948 return retval;
00949 }
00950
00951 void KMKernel::dcopResetAddMessage()
00952 {
00953 mAddMessageMsgIds.clear();
00954 mAddMessageLastFolder = QString();
00955 }
00956
00957 int KMKernel::dcopAddMessage_fastImport( const QString & foldername,
00958 const QString & msgUrlString,
00959 const QString & MsgStatusFlags)
00960 {
00961 return dcopAddMessage_fastImport(foldername, KURL(msgUrlString), MsgStatusFlags);
00962 }
00963
00964 int KMKernel::dcopAddMessage_fastImport( const QString & foldername,
00965 const KURL & msgUrl,
00966 const QString & MsgStatusFlags)
00967 {
00968
00969
00970 kdDebug(5006) << "KMKernel::dcopAddMessage_fastImport called" << endl;
00971
00972 if ( foldername.isEmpty() || foldername.startsWith("."))
00973 return -1;
00974
00975 int retval;
00976 bool createNewFolder = false;
00977
00978 QString _foldername = foldername.stripWhiteSpace();
00979 _foldername = _foldername.replace('\\',"");
00980
00981 if ( foldername != mAddMessageLastFolder ) {
00982 createNewFolder = true;
00983 mAddMessageLastFolder = foldername;
00984 }
00985
00986
00987 if ( !msgUrl.isEmpty() && msgUrl.isLocalFile() ) {
00988 const QCString messageText =
00989 KPIM::kFileToString( msgUrl.path(), true, false );
00990 if ( messageText.isEmpty() )
00991 return -2;
00992
00993 KMMessage *msg = new KMMessage();
00994 msg->fromString( messageText );
00995
00996 if (createNewFolder) {
00997 if ( foldername.contains("/")) {
00998 QString tmp_fname = "";
00999 KMFolder *folder = NULL;
01000 KMFolderDir *subfolder;
01001 bool root = true;
01002
01003 QStringList subFList = QStringList::split("/",_foldername,false);
01004
01005 for ( QStringList::Iterator it = subFList.begin(); it != subFList.end(); ++it ) {
01006 QString _newFolder = *it;
01007 if(_newFolder.startsWith(".")) return -1;
01008
01009 if(root) {
01010 folder = the_folderMgr->findOrCreate(*it, false);
01011 if (folder) {
01012 root = false;
01013 tmp_fname = "/" + *it;
01014 }
01015 else return -1;
01016 } else {
01017 subfolder = folder->createChildFolder();
01018 tmp_fname += "/" + *it;
01019 if(!the_folderMgr->getFolderByURL( tmp_fname )) {
01020 folder = the_folderMgr->createFolder(*it, false, folder->folderType(), subfolder);
01021 }
01022 if(!(folder = the_folderMgr->getFolderByURL( tmp_fname ))) return -1;
01023 }
01024 }
01025
01026 mAddMsgCurrentFolder = the_folderMgr->getFolderByURL( tmp_fname );
01027 if(!folder) return -1;
01028
01029 } else {
01030 mAddMsgCurrentFolder = the_folderMgr->findOrCreate(_foldername, false);
01031 }
01032 }
01033
01034 if ( mAddMsgCurrentFolder ) {
01035 int index;
01036
01037 if( !MsgStatusFlags.isEmpty() ) {
01038 KMMsgStatus status = strToStatus(MsgStatusFlags);
01039 if (status) msg->setStatus(status);
01040 }
01041
01042 if ( mAddMsgCurrentFolder->addMsg( msg, &index ) == 0 ) {
01043 mAddMsgCurrentFolder->unGetMsg( index );
01044 retval = 1;
01045 } else {
01046 retval =- 2;
01047 delete msg;
01048 msg = 0;
01049 }
01050 } else {
01051 retval = -1;
01052 }
01053 } else {
01054 retval = -2;
01055 }
01056
01057 return retval;
01058 }
01059
01060 QStringList KMKernel::folderList() const
01061 {
01062 QStringList folders;
01063 const QString localPrefix = "/Local";
01064 folders << localPrefix;
01065 the_folderMgr->getFolderURLS( folders, localPrefix );
01066 the_imapFolderMgr->getFolderURLS( folders );
01067 the_dimapFolderMgr->getFolderURLS( folders );
01068 return folders;
01069 }
01070
01071 DCOPRef KMKernel::getFolder( const QString& vpath )
01072 {
01073 const QString localPrefix = "/Local";
01074 if ( the_folderMgr->getFolderByURL( vpath ) )
01075 return DCOPRef( new FolderIface( vpath ) );
01076 else if ( vpath.startsWith( localPrefix ) &&
01077 the_folderMgr->getFolderByURL( vpath.mid( localPrefix.length() ) ) )
01078 return DCOPRef( new FolderIface( vpath.mid( localPrefix.length() ) ) );
01079 else if ( the_imapFolderMgr->getFolderByURL( vpath ) )
01080 return DCOPRef( new FolderIface( vpath ) );
01081 else if ( the_dimapFolderMgr->getFolderByURL( vpath ) )
01082 return DCOPRef( new FolderIface( vpath ) );
01083 return DCOPRef();
01084 }
01085
01086 void KMKernel::raise()
01087 {
01088 DCOPRef kmail( "kmail", "kmail" );
01089 kmail.call( "newInstance" );
01090 }
01091
01092 bool KMKernel::showMail( Q_UINT32 serialNumber, QString )
01093 {
01094 KMMainWidget *mainWidget = 0;
01095 if (KMainWindow::memberList) {
01096 KMainWindow *win = 0;
01097 QObjectList *l;
01098
01099
01100 for (win = KMainWindow::memberList->first(); win;
01101 win = KMainWindow::memberList->next()) {
01102
01103 l = win->queryList("KMMainWidget");
01104 if (l && l->first()) {
01105 mainWidget = dynamic_cast<KMMainWidget *>(l->first());
01106 if (win->isActiveWindow())
01107 break;
01108 }
01109 }
01110 }
01111
01112 if (mainWidget) {
01113 int idx = -1;
01114 KMFolder *folder = 0;
01115 KMMsgDict::instance()->getLocation(serialNumber, &folder, &idx);
01116 if (!folder || (idx == -1))
01117 return false;
01118 KMFolderOpener openFolder(folder, "showmail");
01119 KMMsgBase *msgBase = folder->getMsgBase(idx);
01120 if (!msgBase)
01121 return false;
01122 bool unGet = !msgBase->isMessage();
01123 KMMessage *msg = folder->getMsg(idx);
01124
01125 KMReaderMainWin *win = new KMReaderMainWin( false, false );
01126 KMMessage *newMessage = new KMMessage( *msg );
01127 newMessage->setParent( msg->parent() );
01128 newMessage->setMsgSerNum( msg->getMsgSerNum() );
01129 newMessage->setReadyToShow( true );
01130 win->showMsg( GlobalSettings::self()->overrideCharacterEncoding(), newMessage );
01131 win->show();
01132
01133 if (unGet)
01134 folder->unGetMsg(idx);
01135 return true;
01136 }
01137
01138 return false;
01139 }
01140
01141 QString KMKernel::getFrom( Q_UINT32 serialNumber )
01142 {
01143 int idx = -1;
01144 KMFolder *folder = 0;
01145 KMMsgDict::instance()->getLocation(serialNumber, &folder, &idx);
01146 if (!folder || (idx == -1))
01147 return QString::null;
01148 KMFolderOpener openFolder(folder, "getFrom");
01149 KMMsgBase *msgBase = folder->getMsgBase(idx);
01150 if (!msgBase)
01151 return QString::null;
01152 bool unGet = !msgBase->isMessage();
01153 KMMessage *msg = folder->getMsg(idx);
01154 QString result = msg->from();
01155 if (unGet)
01156 folder->unGetMsg(idx);
01157 return result;
01158 }
01159
01160 QString KMKernel::debugScheduler()
01161 {
01162 QString res = KMail::ActionScheduler::debug();
01163 return res;
01164 }
01165
01166 QString KMKernel::debugSernum( Q_UINT32 serialNumber )
01167 {
01168 QString res;
01169 if (serialNumber != 0) {
01170 int idx = -1;
01171 KMFolder *folder = 0;
01172 KMMsgBase *msg = 0;
01173 KMMsgDict::instance()->getLocation( serialNumber, &folder, &idx );
01174
01175
01176 if (folder && (idx != -1)) {
01177
01178 KMFolderOpener openFolder(folder, "debugser");
01179 msg = folder->getMsgBase( idx );
01180 if (msg) {
01181 res.append( QString( " subject %s,\n sender %s,\n date %s.\n" )
01182 .arg( msg->subject() )
01183 .arg( msg->fromStrip() )
01184 .arg( msg->dateStr() ) );
01185 } else {
01186 res.append( QString( "Invalid serial number." ) );
01187 }
01188 } else {
01189 res.append( QString( "Invalid serial number." ) );
01190 }
01191 }
01192 return res;
01193 }
01194
01195
01196 void KMKernel::pauseBackgroundJobs()
01197 {
01198 mBackgroundTasksTimer->stop();
01199 mJobScheduler->pause();
01200 }
01201
01202 void KMKernel::resumeBackgroundJobs()
01203 {
01204 mJobScheduler->resume();
01205 mBackgroundTasksTimer->start( 4 * 60 * 60 * 1000, true );
01206 }
01207
01208 void KMKernel::stopNetworkJobs()
01209 {
01210 if ( GlobalSettings::self()->networkState() == GlobalSettings::EnumNetworkState::Offline )
01211 return;
01212
01213 GlobalSettings::setNetworkState( GlobalSettings::EnumNetworkState::Offline );
01214 BroadcastStatus::instance()->setStatusMsg( i18n("KMail is set to be offline; all network jobs are suspended"));
01215 emit onlineStatusChanged( (GlobalSettings::EnumNetworkState::type)GlobalSettings::networkState() );
01216 }
01217
01218 void KMKernel::resumeNetworkJobs()
01219 {
01220 if ( GlobalSettings::self()->networkState() == GlobalSettings::EnumNetworkState::Online )
01221 return;
01222
01223 GlobalSettings::setNetworkState( GlobalSettings::EnumNetworkState::Online );
01224 BroadcastStatus::instance()->setStatusMsg( i18n("KMail is set to be online; all network jobs resumed"));
01225 emit onlineStatusChanged( (GlobalSettings::EnumNetworkState::type)GlobalSettings::networkState() );
01226
01227 if ( kmkernel->msgSender()->sendImmediate() ) {
01228 kmkernel->msgSender()->sendQueued();
01229 }
01230 }
01231
01232 bool KMKernel::isOffline()
01233 {
01234 if ( GlobalSettings::self()->networkState() == GlobalSettings::EnumNetworkState::Offline )
01235 return true;
01236 else
01237 return false;
01238 }
01239
01240 bool KMKernel::askToGoOnline()
01241 {
01242 if ( kmkernel->isOffline() ) {
01243 int rc =
01244 KMessageBox::questionYesNo( KMKernel::self()->mainWin(),
01245 i18n("KMail is currently in offline mode. "
01246 "How do you want to proceed?"),
01247 i18n("Online/Offline"),
01248 i18n("Work Online"),
01249 i18n("Work Offline"));
01250
01251 if( rc == KMessageBox::No ) {
01252 return false;
01253 } else {
01254 kmkernel->resumeNetworkJobs();
01255 }
01256 }
01257 return true;
01258 }
01259
01260
01261
01262
01263
01264 void KMKernel::quit()
01265 {
01266
01267
01268 }
01269
01270
01271
01272
01273
01274
01275
01276
01277
01278
01279
01280
01281
01282
01283
01284
01285
01286
01287
01288
01289
01290
01291
01292
01293
01294
01295
01296
01297
01298
01299
01300
01301
01302
01303
01304
01305
01306
01307
01308
01309
01310
01311
01312
01313
01314
01315 void KMKernel::testDir(const char *_name)
01316 {
01317 QString foldersPath = QDir::homeDirPath() + QString( _name );
01318 QFileInfo info( foldersPath );
01319 if ( !info.exists() ) {
01320 if ( ::mkdir( QFile::encodeName( foldersPath ) , S_IRWXU ) == -1 ) {
01321 KMessageBox::sorry(0, i18n("KMail could not create folder '%1';\n"
01322 "please make sure that you can view and "
01323 "modify the content of the folder '%2'.")
01324 .arg( foldersPath ).arg( QDir::homeDirPath() ) );
01325 ::exit(-1);
01326 }
01327 }
01328 if ( !info.isDir() || !info.isReadable() || !info.isWritable() ) {
01329 KMessageBox::sorry(0, i18n("The permissions of the folder '%1' are "
01330 "incorrect;\n"
01331 "please make sure that you can view and modify "
01332 "the content of this folder.")
01333 .arg( foldersPath ) );
01334 ::exit(-1);
01335 }
01336 }
01337
01338
01339
01340
01341 void KMKernel::recoverDeadLetters()
01342 {
01343 const QString pathName = localDataPath();
01344 QDir dir( pathName );
01345 if ( !dir.exists( "autosave" ) )
01346 return;
01347
01348 KMFolder folder( 0, pathName + "autosave", KMFolderTypeMaildir, false );
01349 KMFolderOpener openFolder( &folder, "recover" );
01350 if ( !folder.isOpened() ) {
01351 perror( "cannot open autosave folder" );
01352 return;
01353 }
01354
01355 const int num = folder.count();
01356 for ( int i = 0; i < num; i++ ) {
01357 KMMessage *msg = folder.take( 0 );
01358 if ( msg ) {
01359 KMail::Composer * win = KMail::makeComposer();
01360 win->setMsg( msg, false, false, true );
01361 win->setAutoSaveFilename( msg->fileName() );
01362 win->show();
01363 }
01364 }
01365 }
01366
01367
01368 void KMKernel::initFolders(KConfig* cfg)
01369 {
01370 QString name;
01371
01372 name = cfg->readEntry("inboxFolder");
01373
01374
01375
01376
01377
01378 if (name.isEmpty()) name = I18N_NOOP("inbox");
01379
01380 the_inboxFolder = (KMFolder*)the_folderMgr->findOrCreate(name);
01381
01382 if (the_inboxFolder->canAccess() != 0) {
01383 emergencyExit( i18n("You do not have read/write permission to your inbox folder.") );
01384 }
01385
01386 the_inboxFolder->setSystemFolder(true);
01387 if ( the_inboxFolder->userWhoField().isEmpty() )
01388 the_inboxFolder->setUserWhoField( QString::null );
01389
01390
01391 the_outboxFolder = the_folderMgr->findOrCreate(cfg->readEntry("outboxFolder", I18N_NOOP("outbox")));
01392 if (the_outboxFolder->canAccess() != 0) {
01393 emergencyExit( i18n("You do not have read/write permission to your outbox folder.") );
01394 }
01395 the_outboxFolder->setNoChildren(true);
01396
01397 the_outboxFolder->setSystemFolder(true);
01398 if ( the_outboxFolder->userWhoField().isEmpty() )
01399 the_outboxFolder->setUserWhoField( QString::null );
01400
01401
01402
01403
01404
01405
01406
01407
01408 the_outboxFolder->open("kmkernel");
01409
01410 the_sentFolder = the_folderMgr->findOrCreate(cfg->readEntry("sentFolder", I18N_NOOP("sent-mail")));
01411 if (the_sentFolder->canAccess() != 0) {
01412 emergencyExit( i18n("You do not have read/write permission to your sent-mail folder.") );
01413 }
01414 the_sentFolder->setSystemFolder(true);
01415 if ( the_sentFolder->userWhoField().isEmpty() )
01416 the_sentFolder->setUserWhoField( QString::null );
01417
01418
01419 the_trashFolder = the_folderMgr->findOrCreate(cfg->readEntry("trashFolder", I18N_NOOP("trash")));
01420 if (the_trashFolder->canAccess() != 0) {
01421 emergencyExit( i18n("You do not have read/write permission to your trash folder.") );
01422 }
01423 the_trashFolder->setSystemFolder( true );
01424 if ( the_trashFolder->userWhoField().isEmpty() )
01425 the_trashFolder->setUserWhoField( QString::null );
01426
01427
01428 the_draftsFolder = the_folderMgr->findOrCreate(cfg->readEntry("draftsFolder", I18N_NOOP("drafts")));
01429 if (the_draftsFolder->canAccess() != 0) {
01430 emergencyExit( i18n("You do not have read/write permission to your drafts folder.") );
01431 }
01432 the_draftsFolder->setSystemFolder( true );
01433 if ( the_draftsFolder->userWhoField().isEmpty() )
01434 the_draftsFolder->setUserWhoField( QString::null );
01435 the_draftsFolder->open("kmkernel");
01436
01437 the_templatesFolder =
01438 the_folderMgr->findOrCreate( cfg->readEntry( "templatesFolder",
01439 I18N_NOOP("templates") ) );
01440 if ( the_templatesFolder->canAccess() != 0 ) {
01441 emergencyExit( i18n("You do not have read/write permission to your templates folder.") );
01442 }
01443 the_templatesFolder->setSystemFolder( true );
01444 if ( the_templatesFolder->userWhoField().isEmpty() )
01445 the_templatesFolder->setUserWhoField( QString::null );
01446 the_templatesFolder->open("kmkernel");
01447 }
01448
01449
01450 void KMKernel::init()
01451 {
01452 the_shuttingDown = false;
01453 the_server_is_ready = false;
01454
01455 KConfig* cfg = KMKernel::config();
01456
01457 QDir dir;
01458
01459 KConfigGroupSaver saver(cfg, "General");
01460 the_firstStart = cfg->readBoolEntry("first-start", true);
01461 cfg->writeEntry("first-start", false);
01462 the_previousVersion = cfg->readEntry("previous-version");
01463 cfg->writeEntry("previous-version", KMAIL_VERSION);
01464 QString foldersPath = cfg->readPathEntry( "folders" );
01465 kdDebug(5006) << k_funcinfo << "foldersPath (from config): '" << foldersPath << "'" << endl;
01466
01467 if ( foldersPath.isEmpty() ) {
01468 foldersPath = localDataPath() + "mail";
01469 if ( transferMail( foldersPath ) ) {
01470 cfg->writePathEntry( "folders", foldersPath );
01471 }
01472 kdDebug(5006) << k_funcinfo << "foldersPath (after transferMail): '" << foldersPath << "'" << endl;
01473 }
01474
01475
01476 KMMessage::readConfig();
01477
01478 the_undoStack = new UndoStack(20);
01479 the_folderMgr = new KMFolderMgr(foldersPath);
01480 the_imapFolderMgr = new KMFolderMgr( KMFolderImap::cacheLocation(), KMImapDir);
01481 the_dimapFolderMgr = new KMFolderMgr( KMFolderCachedImap::cacheLocation(), KMDImapDir);
01482
01483 the_searchFolderMgr = new KMFolderMgr(locateLocal("data","kmail/search"), KMSearchDir);
01484 KMFolder *lsf = the_searchFolderMgr->find( i18n("Last Search") );
01485 if (lsf)
01486 the_searchFolderMgr->remove( lsf );
01487
01488 the_acctMgr = new AccountManager();
01489 the_filterMgr = new KMFilterMgr();
01490 the_popFilterMgr = new KMFilterMgr(true);
01491 the_filterActionDict = new KMFilterActionDict;
01492
01493 initFolders(cfg);
01494 the_acctMgr->readConfig();
01495 the_filterMgr->readConfig();
01496 the_popFilterMgr->readConfig();
01497 cleanupImapFolders();
01498
01499 the_msgSender = new KMSender;
01500 the_server_is_ready = true;
01501 imProxy()->initialize();
01502 {
01503 KConfigGroupSaver saver(cfg, "Composer");
01504 if (cfg->readListEntry("pref-charsets").isEmpty())
01505 {
01506 cfg->writeEntry("pref-charsets", "us-ascii,iso-8859-1,locale,utf-8");
01507 }
01508 }
01509 readConfig();
01510 mICalIface->readConfig();
01511
01512 #ifdef HAVE_INDEXLIB
01513 the_msgIndex = new KMMsgIndex(this);
01514 #else
01515 the_msgIndex = 0;
01516 #endif
01517
01518
01519 the_weaver = new KPIM::ThreadWeaver::Weaver( this );
01520 the_weaverLogger = new KPIM::ThreadWeaver::WeaverThreadLogger(this);
01521 the_weaverLogger->attach (the_weaver);
01522
01523
01524 connect( the_folderMgr, SIGNAL( folderRemoved(KMFolder*) ),
01525 this, SIGNAL( folderRemoved(KMFolder*) ) );
01526 connect( the_dimapFolderMgr, SIGNAL( folderRemoved(KMFolder*) ),
01527 this, SIGNAL( folderRemoved(KMFolder*) ) );
01528 connect( the_imapFolderMgr, SIGNAL( folderRemoved(KMFolder*) ),
01529 this, SIGNAL( folderRemoved(KMFolder*) ) );
01530 connect( the_searchFolderMgr, SIGNAL( folderRemoved(KMFolder*) ),
01531 this, SIGNAL( folderRemoved(KMFolder*) ) );
01532
01533 mBackgroundTasksTimer = new QTimer( this, "mBackgroundTasksTimer" );
01534 connect( mBackgroundTasksTimer, SIGNAL( timeout() ), this, SLOT( slotRunBackgroundTasks() ) );
01535 #ifdef DEBUG_SCHEDULER // for debugging, see jobscheduler.h
01536 mBackgroundTasksTimer->start( 10000, true );
01537 #else
01538 mBackgroundTasksTimer->start( 5 * 60000, true );
01539 #endif
01540 }
01541
01542 void KMKernel::readConfig()
01543 {
01544
01545
01546 KMMessage::readConfig();
01547 }
01548
01549 void KMKernel::cleanupImapFolders()
01550 {
01551 KMAccount *acct = 0;
01552 KMFolderNode *node = the_imapFolderMgr->dir().first();
01553 while (node)
01554 {
01555 if (node->isDir() || ((acct = the_acctMgr->find(node->id()))
01556 && ( acct->type() == "imap" )) )
01557 {
01558 node = the_imapFolderMgr->dir().next();
01559 } else {
01560 KMFolder* folder = static_cast<KMFolder*>(node);
01561
01562 static_cast<KMFolderImap*>( folder->storage() )->setAlreadyRemoved( true );
01563 the_imapFolderMgr->remove(folder);
01564 node = the_imapFolderMgr->dir().first();
01565 }
01566 }
01567
01568 node = the_dimapFolderMgr->dir().first();
01569 while (node)
01570 {
01571 if (node->isDir() || ((acct = the_acctMgr->find(node->id()))
01572 && ( acct->type() == "cachedimap" )) )
01573 {
01574 node = the_dimapFolderMgr->dir().next();
01575 } else {
01576 the_dimapFolderMgr->remove(static_cast<KMFolder*>(node));
01577 node = the_dimapFolderMgr->dir().first();
01578 }
01579 }
01580
01581 the_imapFolderMgr->quiet(true);
01582 for (acct = the_acctMgr->first(); acct; acct = the_acctMgr->next())
01583 {
01584 KMFolderImap *fld;
01585 KMAcctImap *imapAcct;
01586
01587 if (acct->type() != "imap") continue;
01588 fld = static_cast<KMFolderImap*>(the_imapFolderMgr
01589 ->findOrCreate(QString::number(acct->id()), false, acct->id())->storage());
01590 fld->setNoContent(true);
01591 fld->folder()->setLabel(acct->name());
01592 imapAcct = static_cast<KMAcctImap*>(acct);
01593 fld->setAccount(imapAcct);
01594 imapAcct->setImapFolder(fld);
01595 fld->close( "kernel", true );
01596 }
01597 the_imapFolderMgr->quiet(false);
01598
01599 the_dimapFolderMgr->quiet( true );
01600 for (acct = the_acctMgr->first(); acct; acct = the_acctMgr->next())
01601 {
01602 KMFolderCachedImap *cfld = 0;
01603 KMAcctCachedImap *cachedImapAcct;
01604
01605 if (acct->type() != "cachedimap" ) continue;
01606
01607 KMFolder* fld = the_dimapFolderMgr->find(QString::number(acct->id()));
01608 if( fld )
01609 cfld = static_cast<KMFolderCachedImap*>( fld->storage() );
01610 if (cfld == 0) {
01611
01612 cfld = static_cast<KMFolderCachedImap*>(the_dimapFolderMgr->createFolder(QString::number(acct->id()),
01613 false, KMFolderTypeCachedImap)->storage());
01614 if (!cfld) {
01615 KMessageBox::error(0,(i18n("Cannot create file `%1' in %2.\nKMail cannot start without it.").arg(acct->name()).arg(the_dimapFolderMgr->basePath())));
01616 exit(-1);
01617 }
01618 cfld->folder()->setId( acct->id() );
01619 }
01620
01621 cfld->setNoContent(true);
01622 cfld->folder()->setLabel(acct->name());
01623 cachedImapAcct = static_cast<KMAcctCachedImap*>(acct);
01624 cfld->setAccount(cachedImapAcct);
01625 cachedImapAcct->setImapFolder(cfld);
01626 cfld->close("kmkernel");
01627 }
01628 the_dimapFolderMgr->quiet( false );
01629 }
01630
01631 bool KMKernel::doSessionManagement()
01632 {
01633
01634
01635 if (kapp->isRestored()){
01636 int n = 1;
01637 while (KMMainWin::canBeRestored(n)){
01638
01639 if (KMMainWin::classNameOfToplevel(n) == "KMMainWin")
01640 (new KMMainWin)->restore(n);
01641 n++;
01642 }
01643 return true;
01644 }
01645 return false;
01646 }
01647
01648 void KMKernel::closeAllKMailWindows()
01649 {
01650 if (!KMainWindow::memberList) return;
01651 QPtrListIterator<KMainWindow> it(*KMainWindow::memberList);
01652 KMainWindow *window = 0;
01653 while ((window = it.current()) != 0) {
01654 ++it;
01655 if (window->isA("KMMainWindow") ||
01656 window->inherits("KMail::SecondaryWindow"))
01657 window->close( true );
01658 }
01659 }
01660
01661 void KMKernel::cleanup(void)
01662 {
01663 dumpDeadLetters();
01664 the_shuttingDown = true;
01665 closeAllKMailWindows();
01666
01667 delete the_acctMgr;
01668 the_acctMgr = 0;
01669 delete the_filterMgr;
01670 the_filterMgr = 0;
01671 delete the_msgSender;
01672 the_msgSender = 0;
01673 delete the_filterActionDict;
01674 the_filterActionDict = 0;
01675 delete the_undoStack;
01676 the_undoStack = 0;
01677 delete the_popFilterMgr;
01678 the_popFilterMgr = 0;
01679
01680 #if 0
01681 delete the_weaver;
01682 the_weaver = 0;
01683 #endif
01684
01685 KConfig* config = KMKernel::config();
01686 KConfigGroupSaver saver(config, "General");
01687
01688 if (the_trashFolder) {
01689
01690 the_trashFolder->close("kmkernel", true);
01691
01692 if (config->readBoolEntry("empty-trash-on-exit", true))
01693 {
01694 if ( the_trashFolder->count( true ) > 0 )
01695 the_trashFolder->expunge();
01696 }
01697 }
01698
01699 mICalIface->cleanup();
01700
01701 QValueList<QGuardedPtr<KMFolder> > folders;
01702 QStringList strList;
01703 KMFolder *folder;
01704 the_folderMgr->createFolderList(&strList, &folders);
01705 for (int i = 0; folders.at(i) != folders.end(); i++)
01706 {
01707 folder = *folders.at(i);
01708 if (!folder || folder->isDir()) continue;
01709 folder->close("kmkernel", true);
01710 }
01711 strList.clear();
01712 folders.clear();
01713 the_searchFolderMgr->createFolderList(&strList, &folders);
01714 for (int i = 0; folders.at(i) != folders.end(); i++)
01715 {
01716 folder = *folders.at(i);
01717 if (!folder || folder->isDir()) continue;
01718 folder->close("kmkernel", true);
01719 }
01720
01721 delete the_msgIndex;
01722 the_msgIndex = 0;
01723 delete the_folderMgr;
01724 the_folderMgr = 0;
01725 delete the_imapFolderMgr;
01726 the_imapFolderMgr = 0;
01727 delete the_dimapFolderMgr;
01728 the_dimapFolderMgr = 0;
01729 delete the_searchFolderMgr;
01730 the_searchFolderMgr = 0;
01731 delete mConfigureDialog;
01732 mConfigureDialog = 0;
01733
01734
01735 mWin = 0;
01736
01737 if ( RecentAddresses::exists() )
01738 RecentAddresses::self( config )->save( config );
01739 config->sync();
01740 }
01741
01742 bool KMKernel::transferMail( QString & destinationDir )
01743 {
01744 QString dir;
01745
01746
01747 QFileInfo fi( QDir::home(), "KMail" );
01748 if ( fi.exists() && fi.isDir() ) {
01749 dir = QDir::homeDirPath() + "/KMail";
01750
01751 destinationDir = dir;
01752 return true;
01753 }
01754
01755 if ( dir.isEmpty() ) {
01756
01757 fi.setFile( QDir::home(), "Mail" );
01758 if ( fi.exists() && fi.isDir() &&
01759 QFile::exists( QDir::homeDirPath() + "/Mail/.inbox.index" ) ) {
01760
01761
01762 dir = QDir::homeDirPath() + "/Mail";
01763
01764 destinationDir = dir;
01765 return true;
01766 }
01767 }
01768
01769 if ( dir.isEmpty() ) {
01770 return true;
01771 }
01772
01773 #if 0
01774
01775 const QString kmailName = kapp->aboutData()->programName();
01776 QString msg;
01777 if ( KIO::NetAccess::exists( destinationDir, true, 0 ) ) {
01778
01779
01780 msg = i18n( "%1-%3 is the application name, %4-%7 are folder path",
01781 "<qt>The <i>%4</i> folder exists. "
01782 "%1 now uses the <i>%5</i> folder for "
01783 "its messages.<p>"
01784 "%2 can move the contents of <i>%6<i> into this folder for "
01785 "you, though this may replace any existing files with "
01786 "the same name in <i>%7</i>.<p>"
01787 "<strong>Would you like %3 to move the mail "
01788 "files now?</strong></qt>" )
01789 .arg( kmailName, kmailName, kmailName )
01790 .arg( dir, destinationDir, dir, destinationDir );
01791 } else {
01792 msg = i18n( "%1-%3 is the application name, %4-%6 are folder path",
01793 "<qt>The <i>%4</i> folder exists. "
01794 "%1 now uses the <i>%5</i> folder for "
01795 "its messages. %2 can move the contents of <i>%6</i> into "
01796 "this folder for you.<p>"
01797 "<strong>Would you like %3 to move the mail "
01798 "files now?</strong></qt>" )
01799 .arg( kmailName, kmailName, kmailName )
01800 .arg( dir, destinationDir, dir );
01801 }
01802 QString title = i18n( "Migrate Mail Files?" );
01803 QString buttonText = i18n( "Move" );
01804
01805 if ( KMessageBox::questionYesNo( 0, msg, title, buttonText, i18n("Do Not Move") ) ==
01806 KMessageBox::No ) {
01807 destinationDir = dir;
01808 return true;
01809 }
01810
01811 if ( !KIO::NetAccess::move( dir, destinationDir ) ) {
01812 kdDebug(5006) << k_funcinfo << "Moving " << dir << " to " << destinationDir << " failed: " << KIO::NetAccess::lastErrorString() << endl;
01813 kdDebug(5006) << k_funcinfo << "Deleting " << destinationDir << endl;
01814 KIO::NetAccess::del( destinationDir, 0 );
01815 destinationDir = dir;
01816 return false;
01817 }
01818 #endif
01819
01820 return true;
01821 }
01822
01823
01824 void KMKernel::ungrabPtrKb(void)
01825 {
01826 if(!KMainWindow::memberList) return;
01827 QWidget* widg = KMainWindow::memberList->first();
01828 Display* dpy;
01829
01830 if (!widg) return;
01831 dpy = widg->x11Display();
01832 XUngrabKeyboard(dpy, CurrentTime);
01833 XUngrabPointer(dpy, CurrentTime);
01834 }
01835
01836
01837
01838 void KMKernel::kmailMsgHandler(QtMsgType aType, const char* aMsg)
01839 {
01840 static int recurse=-1;
01841
01842 recurse++;
01843
01844 switch (aType)
01845 {
01846 case QtDebugMsg:
01847 case QtWarningMsg:
01848 kdDebug(5006) << aMsg << endl;
01849 break;
01850
01851 case QtFatalMsg:
01852 ungrabPtrKb();
01853 kdDebug(5006) << kapp->caption() << " fatal error "
01854 << aMsg << endl;
01855 KMessageBox::error(0, aMsg);
01856 abort();
01857 }
01858
01859 recurse--;
01860 }
01861
01862
01863 void KMKernel::dumpDeadLetters()
01864 {
01865 if ( shuttingDown() )
01866 return;
01867
01868
01869 if ( !KMainWindow::memberList )
01870 return;
01871
01872 for ( QPtrListIterator<KMainWindow> it(*KMainWindow::memberList) ; it.current() != 0; ++it ) {
01873 if ( KMail::Composer * win = ::qt_cast<KMail::Composer*>( it.current() ) ) {
01874 win->autoSaveMessage();
01875
01876
01877
01878
01879 while ( win->isComposing() )
01880 qApp->processEvents();
01881 }
01882 }
01883 }
01884
01885
01886
01887 void KMKernel::action(bool mailto, bool check, const QString &to,
01888 const QString &cc, const QString &bcc,
01889 const QString &subj, const QString &body,
01890 const KURL &messageFile,
01891 const KURL::List &attachURLs,
01892 const QCStringList &customHeaders)
01893 {
01894 if ( mailto )
01895 openComposer( to, cc, bcc, subj, body, 0, messageFile, attachURLs, customHeaders );
01896 else
01897 openReader( check );
01898
01899 if ( check )
01900 checkMail();
01901
01902 }
01903
01904 void KMKernel::byteArrayToRemoteFile(const QByteArray &aData, const KURL &aURL,
01905 bool overwrite)
01906 {
01907
01908 KIO::Job *job = KIO::put(aURL, -1, overwrite, false);
01909 putData pd; pd.url = aURL; pd.data = aData; pd.offset = 0;
01910 mPutJobs.insert(job, pd);
01911 connect(job, SIGNAL(dataReq(KIO::Job*,QByteArray&)),
01912 SLOT(slotDataReq(KIO::Job*,QByteArray&)));
01913 connect(job, SIGNAL(result(KIO::Job*)),
01914 SLOT(slotResult(KIO::Job*)));
01915 }
01916
01917 void KMKernel::slotDataReq(KIO::Job *job, QByteArray &data)
01918 {
01919
01920 const int MAX_CHUNK_SIZE = 64*1024;
01921 QMap<KIO::Job*, putData>::Iterator it = mPutJobs.find(job);
01922 assert(it != mPutJobs.end());
01923 int remainingBytes = (*it).data.size() - (*it).offset;
01924 if( remainingBytes > MAX_CHUNK_SIZE )
01925 {
01926
01927 data.duplicate( (*it).data.data() + (*it).offset, MAX_CHUNK_SIZE );
01928 (*it).offset += MAX_CHUNK_SIZE;
01929
01930
01931 }
01932 else
01933 {
01934
01935 data.duplicate( (*it).data.data() + (*it).offset, remainingBytes );
01936 (*it).data = QByteArray();
01937 (*it).offset = 0;
01938
01939 }
01940 }
01941
01942 void KMKernel::slotResult(KIO::Job *job)
01943 {
01944 QMap<KIO::Job*, putData>::Iterator it = mPutJobs.find(job);
01945 assert(it != mPutJobs.end());
01946 if (job->error())
01947 {
01948 if (job->error() == KIO::ERR_FILE_ALREADY_EXIST)
01949 {
01950 if (KMessageBox::warningContinueCancel(0,
01951 i18n("File %1 exists.\nDo you want to replace it?")
01952 .arg((*it).url.prettyURL()), i18n("Save to File"), i18n("&Replace"))
01953 == KMessageBox::Continue)
01954 byteArrayToRemoteFile((*it).data, (*it).url, true);
01955 }
01956 else job->showErrorDialog();
01957 }
01958 mPutJobs.remove(it);
01959 }
01960
01961 void KMKernel::slotRequestConfigSync() {
01962
01963 KMKernel::config()->sync();
01964 }
01965
01966 void KMKernel::slotShowConfigurationDialog()
01967 {
01968 if( !mConfigureDialog ) {
01969 mConfigureDialog = new ConfigureDialog( 0, "configure", false );
01970 connect( mConfigureDialog, SIGNAL( configCommitted() ),
01971 this, SLOT( slotConfigChanged() ) );
01972 }
01973
01974 if( KMKernel::getKMMainWidget() == 0 )
01975 {
01976
01977
01978
01979 KMMainWin * win = new KMMainWin;
01980 win->show();
01981 }
01982
01983 if( mConfigureDialog->isHidden() )
01984 mConfigureDialog->show();
01985 else
01986 mConfigureDialog->raise();
01987 }
01988
01989 void KMKernel::slotConfigChanged()
01990 {
01991 readConfig();
01992 emit configChanged();
01993 }
01994
01995
01996
01997 QString KMKernel::localDataPath()
01998 {
01999 return locateLocal( "data", "kmail/" );
02000 }
02001
02002
02003
02004 bool KMKernel::haveSystemTrayApplet()
02005 {
02006 return !systemTrayApplets.isEmpty();
02007 }
02008
02009 bool KMKernel::registerSystemTrayApplet( const KSystemTray* applet )
02010 {
02011 if ( systemTrayApplets.findIndex( applet ) == -1 ) {
02012 systemTrayApplets.append( applet );
02013 return true;
02014 }
02015 else
02016 return false;
02017 }
02018
02019 bool KMKernel::unregisterSystemTrayApplet( const KSystemTray* applet )
02020 {
02021 QValueList<const KSystemTray*>::iterator it =
02022 systemTrayApplets.find( applet );
02023 if ( it != systemTrayApplets.end() ) {
02024 systemTrayApplets.remove( it );
02025 return true;
02026 }
02027 else
02028 return false;
02029 }
02030
02031 void KMKernel::emergencyExit( const QString& reason )
02032 {
02033 QString mesg;
02034 if ( reason.length() == 0 ) {
02035 mesg = i18n("KMail encountered a fatal error and will terminate now");
02036 } else {
02037 mesg = i18n("KMail encountered a fatal error and will "
02038 "terminate now.\nThe error was:\n%1").arg( reason );
02039 }
02040
02041 kdWarning() << mesg << endl;
02042 KNotifyClient::userEvent( 0, "<qt>"+mesg+"</qt>", KNotifyClient::Messagebox, KNotifyClient::Error );
02043
02044 ::exit(1);
02045 }
02046
02050 bool KMKernel::folderIsDraftOrOutbox(const KMFolder * folder)
02051 {
02052 assert( folder );
02053 if ( folder == the_outboxFolder )
02054 return true;
02055 return folderIsDrafts( folder );
02056 }
02057
02058 bool KMKernel::folderIsDrafts(const KMFolder * folder)
02059 {
02060 assert( folder );
02061 if ( folder == the_draftsFolder )
02062 return true;
02063
02064 QString idString = folder->idString();
02065 if ( idString.isEmpty() )
02066 return false;
02067
02068
02069 const KPIM::IdentityManager *im = identityManager();
02070 for ( KPIM::IdentityManager::ConstIterator it=im->begin(); it != im->end(); ++it )
02071 if ( (*it).drafts() == idString )
02072 return true;
02073 return false;
02074 }
02075
02076 bool KMKernel::folderIsTemplates( const KMFolder *folder )
02077 {
02078 assert( folder );
02079 if ( folder == the_templatesFolder )
02080 return true;
02081
02082 QString idString = folder->idString();
02083 if ( idString.isEmpty() )
02084 return false;
02085
02086
02087 const KPIM::IdentityManager *im = identityManager();
02088 for ( KPIM::IdentityManager::ConstIterator it=im->begin(); it != im->end(); ++it )
02089 if ( (*it).templates() == idString )
02090 return true;
02091 return false;
02092 }
02093
02094 bool KMKernel::folderIsTrash(KMFolder * folder)
02095 {
02096 assert(folder);
02097 if (folder == the_trashFolder) return true;
02098 QStringList actList = acctMgr()->getAccounts();
02099 QStringList::Iterator it( actList.begin() );
02100 for( ; it != actList.end() ; ++it ) {
02101 KMAccount* act = acctMgr()->findByName( *it );
02102 if ( act && ( act->trash() == folder->idString() ) )
02103 return true;
02104 }
02105 return false;
02106 }
02107
02108 bool KMKernel::folderIsSentMailFolder( const KMFolder * folder )
02109 {
02110 assert( folder );
02111 if ( folder == the_sentFolder )
02112 return true;
02113
02114 QString idString = folder->idString();
02115 if ( idString.isEmpty() ) return false;
02116
02117
02118 const KPIM::IdentityManager * im = identityManager();
02119 for( KPIM::IdentityManager::ConstIterator it = im->begin(); it != im->end(); ++it )
02120 if ( (*it).fcc() == idString ) return true;
02121 return false;
02122 }
02123
02124 KPIM::IdentityManager * KMKernel::identityManager() {
02125 if ( !mIdentityManager ) {
02126 kdDebug(5006) << "instantating KPIM::IdentityManager" << endl;
02127 mIdentityManager = new KPIM::IdentityManager( false, this, "mIdentityManager" );
02128 }
02129 return mIdentityManager;
02130 }
02131
02132 KMMsgIndex *KMKernel::msgIndex()
02133 {
02134 return the_msgIndex;
02135 }
02136
02137 KMainWindow* KMKernel::mainWin()
02138 {
02139 if (KMainWindow::memberList) {
02140 KMainWindow *kmWin = 0;
02141
02142
02143 for (kmWin = KMainWindow::memberList->first(); kmWin;
02144 kmWin = KMainWindow::memberList->next())
02145 if (kmWin->isA("KMMainWin"))
02146 return kmWin;
02147
02148
02149
02150
02151 kmWin = KMainWindow::memberList->first();
02152 if ( kmWin )
02153 return kmWin;
02154 }
02155
02156
02157
02158
02159
02160 mWin = new KMMainWin;
02161 return mWin;
02162 }
02163
02164
02168 void KMKernel::slotEmptyTrash()
02169 {
02170 QString title = i18n("Empty Trash");
02171 QString text = i18n("Are you sure you want to empty the trash folders of all accounts?");
02172 if (KMessageBox::warningContinueCancel(0, text, title,
02173 KStdGuiItem::cont(), "confirm_empty_trash")
02174 != KMessageBox::Continue)
02175 {
02176 return;
02177 }
02178
02179 for (KMAccount* acct = acctMgr()->first(); acct; acct = acctMgr()->next())
02180 {
02181 KMFolder* trash = findFolderById(acct->trash());
02182 if (trash)
02183 {
02184 trash->expunge();
02185 }
02186 }
02187 }
02188
02189 KConfig* KMKernel::config()
02190 {
02191 assert(mySelf);
02192 if (!mySelf->mConfig)
02193 {
02194 mySelf->mConfig = KSharedConfig::openConfig( "kmailrc" );
02195
02196 KMail::checkConfigUpdates();
02197 }
02198 return mySelf->mConfig;
02199 }
02200
02201 KMailICalIfaceImpl& KMKernel::iCalIface()
02202 {
02203 assert( mICalIface );
02204 return *mICalIface;
02205 }
02206
02207 void KMKernel::selectFolder( QString folderPath )
02208 {
02209 kdDebug(5006)<<"Selecting a folder "<<folderPath<<endl;
02210 const QString localPrefix = "/Local";
02211 KMFolder *folder = kmkernel->folderMgr()->getFolderByURL( folderPath );
02212 if ( !folder && folderPath.startsWith( localPrefix ) )
02213 folder = the_folderMgr->getFolderByURL( folderPath.mid( localPrefix.length() ) );
02214 if ( !folder )
02215 folder = kmkernel->imapFolderMgr()->getFolderByURL( folderPath );
02216 if ( !folder )
02217 folder = kmkernel->dimapFolderMgr()->getFolderByURL( folderPath );
02218 Q_ASSERT( folder );
02219
02220 KMMainWidget *widget = getKMMainWidget();
02221 Q_ASSERT( widget );
02222 if ( !widget )
02223 return;
02224
02225 KMFolderTree *tree = widget->folderTree();
02226 tree->doFolderSelected( tree->indexOfFolder( folder ) );
02227 tree->ensureItemVisible( tree->indexOfFolder( folder ) );
02228 }
02229
02230 KMMainWidget *KMKernel::getKMMainWidget()
02231 {
02232
02233 QWidgetList *l = kapp->topLevelWidgets();
02234 QWidgetListIt it( *l );
02235 QWidget *wid;
02236
02237 while ( ( wid = it.current() ) != 0 ) {
02238 ++it;
02239 QObjectList *l2 = wid->topLevelWidget()->queryList( "KMMainWidget" );
02240 if (l2 && l2->first()) {
02241 KMMainWidget* kmmw = dynamic_cast<KMMainWidget *>( l2->first() );
02242 Q_ASSERT( kmmw );
02243 delete l2;
02244 delete l;
02245 return kmmw;
02246 }
02247 delete l2;
02248 }
02249 delete l;
02250 return 0;
02251 }
02252
02253 void KMKernel::slotRunBackgroundTasks()
02254 {
02255
02256
02257 KConfigGroup generalGroup( config(), "General" );
02258
02259 if ( generalGroup.readBoolEntry( "auto-expiring", true ) ) {
02260 the_folderMgr->expireAllFolders( false );
02261 the_imapFolderMgr->expireAllFolders( false );
02262 the_dimapFolderMgr->expireAllFolders( false );
02263
02264 }
02265
02266 if ( generalGroup.readBoolEntry( "auto-compaction", true ) ) {
02267 the_folderMgr->compactAllFolders( false );
02268
02269 the_dimapFolderMgr->compactAllFolders( false );
02270
02271 }
02272
02273 #ifdef DEBUG_SCHEDULER // for debugging, see jobscheduler.h
02274 mBackgroundTasksTimer->start( 60 * 1000, true );
02275 #else
02276 mBackgroundTasksTimer->start( 4 * 60 * 60 * 1000, true );
02277 #endif
02278
02279 }
02280
02281 void KMKernel::expireAllFoldersNow()
02282 {
02283 the_folderMgr->expireAllFolders( true );
02284 the_imapFolderMgr->expireAllFolders( true );
02285 the_dimapFolderMgr->expireAllFolders( true );
02286 }
02287
02288 void KMKernel::compactAllFolders()
02289 {
02290 the_folderMgr->compactAllFolders( true );
02291
02292 the_dimapFolderMgr->compactAllFolders( true );
02293 }
02294
02295 KMFolder* KMKernel::findFolderById( const QString& idString )
02296 {
02297 KMFolder * folder = the_folderMgr->findIdString( idString );
02298 if ( !folder )
02299 folder = the_imapFolderMgr->findIdString( idString );
02300 if ( !folder )
02301 folder = the_dimapFolderMgr->findIdString( idString );
02302 if ( !folder )
02303 folder = the_searchFolderMgr->findIdString( idString );
02304 return folder;
02305 }
02306
02307 ::KIMProxy* KMKernel::imProxy()
02308 {
02309 return KIMProxy::instance( kapp->dcopClient() );
02310 }
02311
02312 void KMKernel::enableMailCheck()
02313 {
02314 mMailCheckAborted = false;
02315 }
02316
02317 bool KMKernel::mailCheckAborted() const
02318 {
02319 return mMailCheckAborted;
02320 }
02321
02322 void KMKernel::abortMailCheck()
02323 {
02324 mMailCheckAborted = true;
02325 }
02326
02327 bool KMKernel::canQueryClose()
02328 {
02329 if ( KMMainWidget::mainWidgetList() &&
02330 KMMainWidget::mainWidgetList()->count() > 1 )
02331 return true;
02332 KMMainWidget *widget = getKMMainWidget();
02333 if ( !widget )
02334 return true;
02335 KMSystemTray* systray = widget->systray();
02336 if ( !systray || GlobalSettings::closeDespiteSystemTray() )
02337 return true;
02338 if ( systray->mode() == GlobalSettings::EnumSystemTrayPolicy::ShowAlways ) {
02339 systray->hideKMail();
02340 return false;
02341 } else if ( systray->mode() == GlobalSettings::EnumSystemTrayPolicy::ShowOnUnread ) {
02342 systray->show();
02343 systray->hideKMail();
02344 return false;
02345 }
02346 return true;
02347 }
02348
02349 void KMKernel::messageCountChanged()
02350 {
02351 mTimeOfLastMessageCountChange = ::time( 0 );
02352 }
02353
02354 int KMKernel::timeOfLastMessageCountChange() const
02355 {
02356 return mTimeOfLastMessageCountChange;
02357 }
02358
02359 Wallet *KMKernel::wallet() {
02360 static bool walletOpenFailed = false;
02361 if ( mWallet && mWallet->isOpen() )
02362 return mWallet;
02363
02364 if ( !Wallet::isEnabled() || walletOpenFailed )
02365 return 0;
02366
02367
02368 WId window = 0;
02369 if ( qApp->activeWindow() )
02370 window = qApp->activeWindow()->winId();
02371 else if ( getKMMainWidget() )
02372 window = getKMMainWidget()->topLevelWidget()->winId();
02373
02374 delete mWallet;
02375 mWallet = Wallet::openWallet( Wallet::NetworkWallet(), window );
02376
02377 if ( !mWallet ) {
02378 walletOpenFailed = true;
02379 return 0;
02380 }
02381
02382 if ( !mWallet->hasFolder( "kmail" ) )
02383 mWallet->createFolder( "kmail" );
02384 mWallet->setFolder( "kmail" );
02385 return mWallet;
02386 }
02387
02388 QValueList< QGuardedPtr<KMFolder> > KMKernel::allFolders()
02389 {
02390 QStringList names;
02391 QValueList<QGuardedPtr<KMFolder> > folders;
02392 folderMgr()->createFolderList(&names, &folders);
02393 imapFolderMgr()->createFolderList(&names, &folders);
02394 dimapFolderMgr()->createFolderList(&names, &folders);
02395 searchFolderMgr()->createFolderList(&names, &folders);
02396
02397 return folders;
02398 }
02399
02400 KMFolder *KMKernel::currentFolder() {
02401 KMMainWidget *widget = getKMMainWidget();
02402 KMFolder *folder = 0;
02403 if ( widget && widget->folderTree() ) {
02404 folder = widget->folderTree()->currentFolder();
02405 }
02406 return folder;
02407 }
02408
02409
02410
02411 KMail::MessageSender * KMKernel::msgSender() { return the_msgSender; }
02412
02413 #include "kmkernel.moc"