libkpimexchange Library API Documentation

exchangeaccount.cpp

00001 /*
00002     This file is part of libkpimexchange
00003 
00004     Copyright (c) 2002 Jan-Pascal van Best <janpascal@vanbest.org>
00005     Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org>
00006 
00007     This library is free software; you can redistribute it and/or
00008     modify it under the terms of the GNU Library General Public
00009     License as published by the Free Software Foundation; either
00010     version 2 of the License, or (at your option) any later version.
00011 
00012     This library is distributed in the hope that it will be useful,
00013     but WITHOUT ANY WARRANTY; without even the implied warranty of
00014     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015     Library General Public License for more details.
00016 
00017     You should have received a copy of the GNU Library General Public License
00018     along with this library; see the file COPYING.LIB.  If not, write to
00019     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00020     Boston, MA 02111-1307, USA.
00021 */
00022 
00023 #include <qstring.h>
00024 #include <qtextstream.h>
00025 #include <qapplication.h>
00026 #include <qdom.h>
00027 #include <qwidgetlist.h>
00028 #include <qwidget.h>
00029 #include <qfile.h>
00030 
00031 #include <kurl.h>
00032 #include <kapplication.h>
00033 #include <kdebug.h>
00034 #include <kconfig.h>
00035 #include <dcopclient.h>
00036 #include <kcursor.h>
00037 #include <kmessagebox.h>
00038 #include <klocale.h>
00039 
00040 #include <kio/authinfo.h>
00041 #include <kio/davjob.h>
00042 #include <kio/job.h>
00043 #include <kio/netaccess.h>
00044 
00045 #include "exchangeaccount.h"
00046 #include "utils.h"
00047 
00048 using namespace KPIM;
00049 
00050 ExchangeAccount::ExchangeAccount( const QString &host, const QString &port,
00051                                   const QString &account,
00052                                   const QString &password,
00053                                   const QString &mailbox )
00054   : mError( false )
00055 {
00056   KURL url( "webdav://" + host + "/exchange/" + account );
00057 
00058   if ( !port.isEmpty() )
00059   {
00060     url.setPort( port.toInt() );
00061   }
00062 
00063   mHost = host;
00064   mPort = port;
00065   mAccount = account;
00066   mPassword = password;
00067 
00068   if ( mailbox.isEmpty() ) {
00069     mMailbox = url.url();
00070     kdDebug() << "#!#!#!#!#!#!# mailbox url: " << mMailbox << endl;
00071   } else
00072     mMailbox = mailbox;
00073 
00074   kdDebug() << "ExchangeAccount: mMailbox: " << mMailbox << endl;
00075 
00076   mCalendarURL = 0;
00077 }
00078 
00079 ExchangeAccount::ExchangeAccount( const QString& group )
00080 {
00081   load( group );
00082 }
00083 
00084 ExchangeAccount::~ExchangeAccount()
00085 {
00086 }
00087 
00088 QString endecryptStr( const QString &aStr ) 
00089 {
00090   QString result;
00091   for (uint i = 0; i < aStr.length(); i++)
00092     result += (aStr[i].unicode() < 0x20) ? aStr[i] :
00093               QChar(0x1001F - aStr[i].unicode());
00094   return result;
00095 }
00096 
00097 void ExchangeAccount::save( QString const &group )
00098 {
00099   kapp->config()->setGroup( group );
00100   kapp->config()->writeEntry( "host", mHost );
00101   kapp->config()->writeEntry( "user", mAccount );
00102   kapp->config()->writeEntry( "mailbox", mMailbox );
00103   kapp->config()->writeEntry( "MS-ID", endecryptStr( mPassword ) );
00104   kapp->config()->sync();
00105 }
00106 
00107 void ExchangeAccount::load( QString const &group )
00108 {
00109   kapp->config()->setGroup( group );
00110 
00111   QString host = kapp->config()->readEntry( "host" );
00112   if ( ! host.isNull() ) {
00113     mHost = host;
00114   } else {
00115     mHost = "mail.company.com";
00116   }
00117 
00118   QString user = kapp->config()->readEntry( "user" );
00119   if ( ! user.isNull() ) {
00120     mAccount = user;
00121   } else {
00122     mAccount = "username";
00123   }
00124 
00125   QString mailbox = kapp->config()->readEntry( "mailbox" );
00126   if ( ! mailbox.isNull() ) {
00127     mMailbox = mailbox;
00128   } else {
00129     mMailbox = "webdav://" + host + "/exchange/" + mAccount;
00130   }
00131 
00132   QString password = endecryptStr( kapp->config()->readEntry( "MS-ID" ) );
00133   if ( ! password.isNull() ) {
00134     mPassword = password;
00135   }
00136 }
00137 
00138 KURL ExchangeAccount::baseURL()
00139 {
00140   KURL url = KURL( mMailbox );
00141   return url;
00142 }
00143 
00144 KURL ExchangeAccount::calendarURL()
00145 {
00146   if ( mCalendarURL ) {
00147     return *mCalendarURL;
00148   } else {
00149     KURL url = baseURL();
00150     url.addPath( "Calendar" );
00151     return url;
00152   }
00153 }
00154 
00155 bool ExchangeAccount::authenticate( QWidget *window )
00156 {
00157   if ( window )
00158     return authenticate( window->winId() );
00159   else
00160     return authenticate();
00161 }
00162 
00163 bool ExchangeAccount::authenticate()
00164 {
00165   long windowId;
00166   QWidgetList *widgets = QApplication::topLevelWidgets();
00167   if ( widgets->isEmpty() )
00168     windowId = 0;
00169   else
00170     windowId = widgets->first()->winId();
00171   delete widgets;
00172 
00173   return authenticate( windowId );
00174 }
00175 
00176 bool ExchangeAccount::authenticate( int windowId )
00177 {
00178   kdDebug() << "Entering ExchangeAccount::authenticate( windowId=" << windowId << " )" << endl;
00179 
00180   kdDebug() << "Authenticating to base URL: " << baseURL().prettyURL() << endl;
00181 
00182   KIO::AuthInfo info;
00183   info.url = baseURL();
00184   info.username = mAccount;
00185   info.password = mPassword;
00186   info.realmValue = mHost;
00187   info.digestInfo = "Basic";
00188 
00189   DCOPClient *dcopClient = new DCOPClient();
00190   dcopClient->attach();
00191 
00192   QByteArray params;
00193   QDataStream stream(params, IO_WriteOnly);
00194   stream << info << windowId;
00195 
00196   dcopClient->send( "kded", "kpasswdserver",
00197                     "addAuthInfo(KIO::AuthInfo, long int)", params );
00198 
00199   dcopClient->detach();
00200   delete dcopClient;
00201 
00202   mCalendarURL = 0;
00203 
00204   calcFolderURLs();
00205 
00206   // TODO: Remove this busy loop
00207   QApplication::setOverrideCursor( KCursor::waitCursor() );
00208   do {
00209     qApp->processEvents();
00210   } while ( !mCalendarURL && !mError );
00211   QApplication::restoreOverrideCursor();
00212 
00213   return !mError;
00214 }
00215 
00216 void ExchangeAccount::calcFolderURLs()
00217 {
00218   kdDebug() << "ExchangeAccount::calcFolderURLs" << endl;
00219   QDomDocument doc;
00220   QDomElement root = addElement( doc, doc, "DAV:", "propfind" );
00221   QDomElement prop = addElement( doc, root, "DAV:", "prop" );
00222   addElement( doc, prop, "urn:schemas:httpmail:", "calendar" );
00223 // For later use:
00224 // urn:schemas:httpmail:contacts Contacts 
00225 // urn:schemas:httpmail:deleteditems Deleted Items 
00226 // urn:schemas:httpmail:drafts Drafts 
00227 // urn:schemas:httpmail:inbox Inbox 
00228 // urn:schemas:httpmail:journal Journal 
00229 // urn:schemas:httpmail:notes Notes 
00230 // urn:schemas:httpmail:outbox Outbox 
00231 // urn:schemas:httpmail:sentitems Sent Items 
00232 // urn:schemas:httpmail:tasks Tasks 
00233 // urn:schemas:httpmail:sendmsg Exchange Mail Submission URI 
00234 // urn:schemas:httpmail:msgfolderroot Mailbox folder (root) 
00235 
00236   kdDebug() << "calcFolderUrls(): " << baseURL() << endl;
00237 
00238   mError = false;
00239 
00240   KIO::DavJob* job = KIO::davPropFind( baseURL(), doc, "0", false );
00241   job->addMetaData( "errorPage", "false" );
00242   connect( job, SIGNAL( result( KIO::Job * ) ),
00243            SLOT( slotFolderResult( KIO::Job * ) ) );
00244 }
00245 
00246 void ExchangeAccount::slotFolderResult( KIO::Job *job )
00247 {
00248   kdDebug() << "ExchangeAccount::slotFolderResult()" << endl;
00249   if ( job->error() ) {
00250     kdError() << "Error: Cannot get well-know folder names; " << job->error() << endl;
00251     QString text = i18n("ExchangeAccount\nError accessing '%1': %2")
00252                    .arg( baseURL().prettyURL() ).arg( job->errorString() );
00253     KMessageBox::error( 0, text );
00254     mError = true;
00255     return;
00256   }
00257   QDomDocument &response = static_cast<KIO::DavJob *>( job )->response();
00258 
00259   QDomElement prop = response.documentElement().namedItem( "response" )
00260                      .namedItem( "propstat" ).namedItem( "prop" ).toElement();
00261  
00262   QDomElement calElement = prop.namedItem( "calendar" ).toElement();
00263   if ( calElement.isNull() ) {
00264     kdError() << "Error: no calendar URL in Exchange server reply" << endl;
00265     mError = true;
00266     return;
00267   }
00268   QString calendar = calElement.text();
00269 
00270   kdDebug() << "ExchangeAccount: response calendarURL: " << calendar << endl;
00271 
00272   mCalendarURL = toDAV( new KURL( calendar ) );
00273   kdDebug() << "Calendar URL: " << mCalendarURL->url() << endl;
00274 }
00275 
00276 QString ExchangeAccount::tryFindMailbox( const QString& host, const QString& port, const QString& user, const QString& password )
00277 {
00278   kdDebug() << "Entering ExchangeAccount::tryFindMailbox()" << endl;
00279 
00280   KURL url("http://" + host + "/exchange");
00281   if (!port.isEmpty()) url.setPort(port.toInt());
00282   
00283   QString result = tryMailbox( url.url(), user, password );
00284   if ( result.isNull() )
00285   {
00286     url.setProtocol("https");
00287     result = tryMailbox( url.url(), user, password );
00288   }
00289   return result;
00290 }
00291   
00292 QString ExchangeAccount::tryMailbox( const QString &_url, const QString &user,
00293                                      const QString &password )
00294 {
00295   KURL url = KURL( _url );
00296   url.setUser( user );
00297   url.setPass( password );
00298 
00299   QString tmpFile;
00300   if ( !KIO::NetAccess::download( url, tmpFile, 0 ) ) {
00301     kdWarning() << "Trying to find mailbox failed: not able to download " << url.prettyURL() << endl;
00302     return QString::null;
00303   }
00304   QFile file( tmpFile );
00305   if ( !file.open( IO_ReadOnly ) ) {
00306     kdWarning() << "Trying to find mailbox failed: not able to open temp file " << tmpFile << endl;
00307     KIO::NetAccess::removeTempFile( tmpFile );
00308     return QString::null;
00309   }
00310 
00311   QTextStream stream( &file );
00312   QString line;
00313   QString result;
00314   while ( !stream.eof() ) {
00315       line = stream.readLine(); // line of text excluding '\n'
00316       int pos = line.find( "<BASE href=\"", 0, FALSE );
00317       if ( pos < 0 )
00318         continue;
00319       int end = line.find( "\"", pos+12, FALSE );
00320       if ( pos < 0 ) {
00321         kdWarning() << "Strange, found no closing quote in " << line << endl;
00322         continue;
00323       } 
00324       QString mailboxString = line.mid( pos+12, end-pos-12 );
00325       KURL mailbox( mailboxString );
00326       if ( mailbox.isEmpty() ) {
00327         kdWarning() << "Strange, could not get URL from " << mailboxString << " in line " << line << endl;
00328         continue;
00329       }
00330       result = toDAV( mailbox ).prettyURL( -1 ); // Strip ending slash from URL, if present
00331       kdDebug() << "Found mailbox: " << result << endl;
00332     }
00333     file.close();
00334 
00335     KIO::NetAccess::removeTempFile( tmpFile );
00336     return result;
00337 }
00338 
00339 #include "exchangeaccount.moc"
KDE Logo
This file is part of the documentation for libkpimexchange Library Version 3.3.2.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Thu Aug 23 18:20:56 2007 by doxygen 1.4.2 written by Dimitri van Heesch, © 1997-2003