diff options
Diffstat (limited to 'kresources/lib')
42 files changed, 5709 insertions, 0 deletions
diff --git a/kresources/lib/Makefile.am b/kresources/lib/Makefile.am new file mode 100644 index 000000000..0b3f29b6e --- /dev/null +++ b/kresources/lib/Makefile.am @@ -0,0 +1,39 @@ +INCLUDES = -I$(top_srcdir) \ +-I$(top_srcdir)/libkcal/libical/src/libical -I$(top_srcdir)/libkcal/libical/src/libicalss \ + -I$(top_builddir)/libkcal/libical/src/libical -I$(top_builddir)/libkcal/libical/src/libicalss \ + $(all_includes) + +lib_LTLIBRARIES = libkgroupwarebase.la libkgroupwaredav.la + +libkgroupwarebase_la_SOURCES = folderlister.cpp folderconfig.cpp folderlistview.cpp folderselectdialog.cpp \ + groupwaredataadaptor.cpp groupwaredownloadjob.cpp \ + calendaradaptor.cpp addressbookadaptor.cpp groupwareresourcejob.cpp \ + groupwareuploadjob.cpp kcal_resourcegroupwarebase.cpp kabc_resourcegroupwarebase.cpp \ + kresources_groupwareprefs.kcfgc \ + kcal_resourcegroupwarebaseconfig.cpp kabc_resourcegroupwarebaseconfig.cpp \ + kcal_cachesettingsdlg.cpp +libkgroupwarebase_la_LDFLAGS = $(all_libraries) -no-undefined +libkgroupwarebase_la_LIBADD = $(top_builddir)/libkcal/libkcal.la \ + $(top_builddir)/libkdepim/libkdepim.la + +libkgroupwaredav_la_SOURCES = davcalendaradaptor.cpp davaddressbookadaptor.cpp webdavhandler.cpp \ + davgroupwareglobals.cpp +libkgroupwaredav_la_LDFLAGS = $(all_libraries) -no-undefined +libkgroupwaredav_la_LIBADD = $(top_builddir)/libkcal/libkcal.la \ + $(top_builddir)/libkdepim/libkdepim.la libkgroupwarebase.la + +METASOURCES = AUTO + +### We use three (or more) namespaces here in here - KPIM, KABC and KCal. +### When using multiple "using namespace foo" declarations, namespaced +### definitions cannot be resolved properly; we could use namespace foo { } +### instead, but this breaks on KConfigXT generated code, which still uses +### "using namespace" and can't be fixed due to our backwards-compatibility +### requirements. This is only fatal when doing --enable-final, since only +### then do all the namespaces get mixed together. +KDE_OPTIONS = nofinal + +messages: rc.cpp + $(XGETTEXT) *.cpp -o $(podir)/kdepimresources.pot + +webdavhandler.lo: ../../libkcal/libical/src/libical/ical.h diff --git a/kresources/lib/TODO b/kresources/lib/TODO new file mode 100644 index 000000000..1a1b4cdbf --- /dev/null +++ b/kresources/lib/TODO @@ -0,0 +1,45 @@ +kresources/lib (general): +=============== +-) http result code handling (404, 200, etc.) +-) conflict resolution +-) Error handling in the folder lister (cannot connect to host, timeout, etc.) +-) turn the flat folder list into a folder tree +-) Restore folder subscriptions on folder list refresh +-) If the user cancels, we need to reset the mUploadJob variable to 0 in the + abook resource. +-) if there's an item in the local cache that cannot be bound on the server and + in the idMapper, mark it as added and try to upload it on save! +-) reload libkcal resources in korganizer when config changes +-) Use the username / password entered into the config dlg. For some reason + each ioslave asks again with a password dialog... +-) If upload fails, mark the item as changed/added/deleted again +-) Don't ask immediately for uploading in korganizer, wait at least a + QTimer::singleShot +-) Better progress bar messages + + +kresources/newexchange: +======================= +-) handling of errors returned in a valid dav response (Exchange) +-) recurrences on exchange +-) timezone for exchange +-) exdate on exchange +-) notifications from the server (old exchange resource has it!) +-) In Exchange abook: if an address is removed, store the empty string to the + server to delete the data from the server +-) Journal upload not working + + +kresources/groupdav: +==================== +-) recurrences on ogo +-) uploading abook entries don't work (server doesn't implement it yet) +-) Overview and Calendar have the same items -> downloaded every time (same + uid, different href, only one of them can be in the local cache -> the other + one is downloaded and replaces the current item, so on next folder sync the + first item is downloaded again and replaces the other one...) + + +kresources/blogging: +==================== +-) Upload of blog posts diff --git a/kresources/lib/addressbookadaptor.cpp b/kresources/lib/addressbookadaptor.cpp new file mode 100644 index 000000000..f698e5430 --- /dev/null +++ b/kresources/lib/addressbookadaptor.cpp @@ -0,0 +1,130 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "addressbookadaptor.h" + +#include <kabc/addressee.h> +#include <kabc/vcardconverter.h> +#include <libkdepim/kabcresourcecached.h> +#include <kio/job.h> + + +using namespace KABC; + + +AddressBookUploadItem::AddressBookUploadItem( + KPIM::GroupwareDataAdaptor *adaptor, + KABC::Addressee addr, + GroupwareUploadItem::UploadType type ) + : GroupwareUploadItem( type ) +{ + mItemType = KPIM::FolderLister::Contact; + setUrl( addr.custom( adaptor->identifier(), "storagelocation" ) ); + setUid( addr.uid() ); + KABC::VCardConverter vcard; + setData( vcard.createVCard( addr ) ); +} + + + +AddressBookAdaptor::AddressBookAdaptor() +{ +} + +QString AddressBookAdaptor::mimeType() const +{ + return "text/x-vcard"; +} + +bool AddressBookAdaptor::localItemExists( const QString &localId ) +{ + KABC::Addressee a = mResource->findByUid( localId ); + return !a.isEmpty(); +} + +bool AddressBookAdaptor::localItemHasChanged( const QString &localId ) +{ + KABC::Addressee::List addressees = mResource->deletedAddressees(); + KABC::Addressee::List::ConstIterator it; + for( it = addressees.begin(); it != addressees.end(); ++it ) { + if ( (*it).uid() == localId ) return true; + } + + addressees = mResource->changedAddressees(); + for( it = addressees.begin(); it != addressees.end(); ++it ) { + if ( (*it).uid() == localId ) return true; + } + + return false; +} + + +void AddressBookAdaptor::deleteItem( const QString &localId ) +{ + KABC::Addressee a = mResource->findByUid( localId ); + if ( !a.isEmpty() ) { + mResource->removeAddressee( a ); + mResource->clearChange( a.uid() ); + } +} + +void AddressBookAdaptor::addItem( KABC::Addressee addr ) +{ + if ( !addr.isEmpty() ) { + addr.setResource( mResource ); + mResource->insertAddressee( addr ); + clearChange( addr.uid() ); + } +} + +void AddressBookAdaptor::addressbookItemDownloaded( KABC::Addressee addr, + const QString &newLocalId, const KURL &remoteId, const QString &fingerprint, + const QString &storagelocation ) +{ + // remove the currently existing item from the cache + deleteItem( newLocalId ); + QString localId = idMapper()->localId( remoteId.path() ); + if ( !localId.isEmpty() ) deleteItem( localId ); + + // add the new item + addr.insertCustom( identifier(), "storagelocation", storagelocation ); + if ( !localId.isEmpty() ) addr.setUid( localId ); + addItem( addr ); + + // update the fingerprint and the ids in the idMapper + idMapper()->removeRemoteId( localId ); + idMapper()->removeRemoteId( newLocalId ); + emit itemDownloaded( addr.uid(), remoteId, fingerprint ); +} + + +void AddressBookAdaptor::clearChange( const QString &uid ) +{ + mResource->clearChange( uid ); +} + +KPIM::GroupwareUploadItem *AddressBookAdaptor::newUploadItem( + KABC::Addressee addr, KPIM::GroupwareUploadItem::UploadType type ) +{ + return new AddressBookUploadItem( this, addr, type ); +} diff --git a/kresources/lib/addressbookadaptor.h b/kresources/lib/addressbookadaptor.h new file mode 100644 index 000000000..fb9f2971d --- /dev/null +++ b/kresources/lib/addressbookadaptor.h @@ -0,0 +1,92 @@ + /* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KABC_ADDRESSBOOKADAPTOR_H +#define KABC_ADDRESSBOOKADAPTOR_H + +#include "groupwaredataadaptor.h" + +#include <kabc/addressee.h> +#include <kdepimmacros.h> +#include <kurl.h> + +namespace KABC { +class ResourceCached; + +class AddressBookUploadItem : public KPIM::GroupwareUploadItem +{ + public: + AddressBookUploadItem( KPIM::GroupwareDataAdaptor *adaptor, + KABC::Addressee addr, UploadType type ); + virtual ~AddressBookUploadItem() {} + protected: + AddressBookUploadItem( UploadType type ) + : KPIM::GroupwareUploadItem( type ) {} +}; + +class KDE_EXPORT AddressBookAdaptor : public KPIM::GroupwareDataAdaptor +{ + public: + AddressBookAdaptor(); + + QValueList<KPIM::FolderLister::ContentType> supportedTypes() + { + QValueList<KPIM::FolderLister::ContentType> types; + types << KPIM::FolderLister::Contact; + return types; + } + + /** + Set resource. + */ + void setResource( KABC::ResourceCached *v ) + { + mResource = v; + } + /** + Get resource. See setResource(). + */ + KABC::ResourceCached *resource() const + { + return mResource; + } + + QString mimeType() const; + bool localItemExists( const QString &localId ); + bool localItemHasChanged( const QString &localId ); + void deleteItem( const QString &localId ); + void addItem( KABC::Addressee addr ); + void clearChange( const QString &uid ); + + virtual KPIM::GroupwareUploadItem *newUploadItem( KABC::Addressee addr, + KPIM::GroupwareUploadItem::UploadType type ); + virtual void addressbookItemDownloaded( KABC::Addressee addr, + const QString &newLocalId, const KURL &remoteId, + const QString &fingerprint, const QString &storagelocation ); + + private: + KABC::ResourceCached *mResource; +}; + +} + +#endif diff --git a/kresources/lib/calendaradaptor.cpp b/kresources/lib/calendaradaptor.cpp new file mode 100644 index 000000000..ddba9961c --- /dev/null +++ b/kresources/lib/calendaradaptor.cpp @@ -0,0 +1,150 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "calendaradaptor.h" + +#include <libkcal/incidence.h> +#include <libkcal/calendar.h> +#include <libkcal/resourcecached.h> +#include <libkcal/icalformat.h> + +#include <kio/job.h> + +#include <kdebug.h> + +using namespace KCal; + + +CalendarUploadItem::CalendarUploadItem( CalendarAdaptor *adaptor, KCal::Incidence *incidence, KPIM::GroupwareUploadItem::UploadType type ) + : GroupwareUploadItem( type ) +{ + if ( incidence && adaptor ) { + if ( incidence->type() == "Event" ) mItemType = KPIM::FolderLister::Event; + else if ( incidence->type() == "Todo" ) mItemType = KPIM::FolderLister::Todo; + else if ( incidence->type() == "Journal" ) mItemType = KPIM::FolderLister::Journal; + + setUrl( incidence->customProperty( adaptor->identifier(), "storagelocation" ) ); + setUid( incidence->uid() ); + + ICalFormat format; + format.setTimeZone( adaptor->resource()->timeZoneId(), true ); + setData( format.toICalString( incidence ) ); + } +} + + + +CalendarAdaptor::CalendarAdaptor() +{ +} + +QString CalendarAdaptor::mimeType() const +{ + return "text/calendar"; +} + +bool CalendarAdaptor::localItemExists( const QString &localId ) +{ + KCal::Incidence *i = mResource->incidence( localId ); + return i; +} + +bool CalendarAdaptor::localItemHasChanged( const QString &localId ) +{ + KCal::Incidence *i = mResource->incidence( localId ); + if ( !i ) return false; + + if ( !mResource->deletedIncidences().isEmpty() && + mResource->deletedIncidences().find( i ) + != mResource->deletedIncidences().end() ) + return true; + if ( !mResource->changedIncidences().isEmpty() && + mResource->changedIncidences().find( i ) + != mResource->changedIncidences().end() ) + return true; + + return false; +} + +void CalendarAdaptor::deleteItem( const QString &localId ) +{ + mResource->disableChangeNotification(); + KCal::Incidence *i = mResource->incidence( localId ); + if ( i ) { + mResource->deleteIncidence( i ); + mResource->clearChange( i ); + } + mResource->enableChangeNotification(); +} + +void CalendarAdaptor::addItem( KCal::Incidence *i) +{ + if ( i ) { + mResource->disableChangeNotification(); + Incidence *existing = mResource->incidence( i->uid() ); + if ( existing ) { + mResource->deleteIncidence( i ); + } + mResource->addIncidence( i ); + mResource->clearChange( i ); + mResource->enableChangeNotification(); + } +} + + +void CalendarAdaptor::calendarItemDownloaded( KCal::Incidence *inc, + const QString &newLocalId, const KURL &remoteId, const QString &fingerprint, + const QString &storagelocation ) +{ +kdDebug() << "CalendarAdaptor::calendarItemDownloaded, inc=" << inc->summary() << ", local=" << newLocalId << ", remote=" << remoteId.url() << ", fpr=" << fingerprint << ", storagelocation="<< storagelocation << endl; + // remove the currently existing item from the cache + deleteItem( newLocalId ); + QString localId = idMapper()->localId( remoteId.path() ); + if ( !localId.isEmpty() ) deleteItem( localId ); + + // add the new item + inc->setCustomProperty( identifier(), "storagelocation", storagelocation ); + if ( !localId.isEmpty() ) inc->setUid( localId ); + addItem( inc ); + + // update the fingerprint and the ids in the idMapper + idMapper()->removeRemoteId( localId ); + idMapper()->removeRemoteId( newLocalId ); + + emit itemDownloaded( inc->uid(), remoteId, fingerprint ); +} + + +void CalendarAdaptor::clearChange( const QString &uid ) +{ + KCal::Incidence *i = mResource->incidence( uid ); + mResource->clearChange( i ); +} + +KPIM::GroupwareUploadItem *CalendarAdaptor::newUploadItem( KCal::Incidence*it, + KPIM::GroupwareUploadItem::UploadType type ) +{ + return new CalendarUploadItem( this, it, type ); +} + +#include "calendaradaptor.moc" diff --git a/kresources/lib/calendaradaptor.h b/kresources/lib/calendaradaptor.h new file mode 100644 index 000000000..6ef338d18 --- /dev/null +++ b/kresources/lib/calendaradaptor.h @@ -0,0 +1,109 @@ + /* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KCAL_CALENDARADAPTOR_H +#define KCAL_CALENDARADAPTOR_H + +#include "groupwaredataadaptor.h" + + +#include <libkcal/incidence.h> +#include <kdepimmacros.h> +#include <kurl.h> + +namespace KPIM { +class GroupwareUploadItem; +} + +namespace KCal { +class ResourceCached; +class CalendarAdaptor; + +class CalendarUploadItem : public KPIM::GroupwareUploadItem +{ + public: + CalendarUploadItem( CalendarAdaptor *adaptor, KCal::Incidence *incidence, UploadType type ); + virtual ~CalendarUploadItem() {} + + protected: + CalendarUploadItem( UploadType type ) : KPIM::GroupwareUploadItem( type ) {} +}; + + +class KDE_EXPORT CalendarAdaptor : public KPIM::GroupwareDataAdaptor +{ + Q_OBJECT + public: + CalendarAdaptor(); + + QValueList<KPIM::FolderLister::ContentType> supportedTypes() + { + QValueList<KPIM::FolderLister::ContentType> types; + types << KPIM::FolderLister::Event; + types << KPIM::FolderLister::Todo; + types << KPIM::FolderLister::Journal; + return types; + } + + /** + Set resource. + */ + void setResource( KCal::ResourceCached *v ) + { + mResource = v; + } + /** + Get resource. See setResource(). + */ + KCal::ResourceCached *resource() const + { + return mResource; + } + + virtual QString mimeType() const; + bool localItemExists( const QString &localId ); + bool localItemHasChanged( const QString &localId ); + void deleteItem( const QString &localId ); + void clearChange( const QString &uid ); + + virtual KPIM::GroupwareUploadItem *newUploadItem( KCal::Incidence*it, + KPIM::GroupwareUploadItem::UploadType type ); + + public slots: + /** newLocalId is the new id that was (randomly) assigned to the item */ + virtual void calendarItemDownloaded( KCal::Incidence *inc, + const QString &newLocalId, const KURL &remoteId, + const QString &fingerprint, const QString &storagelocation ); + + protected: + void addItem( KCal::Incidence *i ); + private: + KCal::ResourceCached *mResource; + + QStringList mAddedItems; + QStringList mChangedItems; + QStringList mDeletedItems; +}; + +} + +#endif diff --git a/kresources/lib/davaddressbookadaptor.cpp b/kresources/lib/davaddressbookadaptor.cpp new file mode 100644 index 000000000..1ce009654 --- /dev/null +++ b/kresources/lib/davaddressbookadaptor.cpp @@ -0,0 +1,61 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "davaddressbookadaptor.h" +// #include "ogoglobals.h" +// #include "davgroupwareglobals.h" +// #include "webdavhandler.h" + +// #include <kabc/addressee.h> +// #include <kabc/vcardconverter.h> +// #include <kabcresourcecached.h> + +#include <kio/davjob.h> +// #include <kio/job.h> +#include <kdebug.h> + +using namespace KABC; + +void DavAddressBookAdaptor::interpretListFoldersJob( KIO::Job *job, KPIM::FolderLister */*folderLister*/ ) +{ + KIO::DavJob *davjob = dynamic_cast<KIO::DavJob*>( job ); + Q_ASSERT( davjob ); + if ( !davjob ) return; + + QDomDocument doc = davjob->response(); + kdDebug(7000) << " Doc: " << doc.toString() << endl; + + QDomElement docElement = doc.documentElement(); + QDomNode n; + for( n = docElement.firstChild(); !n.isNull(); n = n.nextSibling() ) { + QDomNode n2 = n.namedItem( "propstat" ); + QDomNode n3 = n2.namedItem( "prop" ); + + KURL href( n.namedItem( "href" ).toElement().text() ); + QString displayName = n3.namedItem( "displayname" ).toElement().text(); + KPIM::FolderLister::ContentType type = getContentType( n3 ); + + emit folderInfoRetrieved( href, displayName, type ); + emit folderSubitemRetrieved( href, getFolderHasSubs( n3 ) ); + } +} diff --git a/kresources/lib/davaddressbookadaptor.h b/kresources/lib/davaddressbookadaptor.h new file mode 100644 index 000000000..ef5c04077 --- /dev/null +++ b/kresources/lib/davaddressbookadaptor.h @@ -0,0 +1,52 @@ + /* + This file is part of kdepim. + + Copyright (C) 2004 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KABC_DAVADDRESSBOOKADAPTOR_H +#define KCAL_DAVADDRESSBOOKADAPTOR_H + +#include "addressbookadaptor.h" +#include "folderlister.h" +#include <qdom.h> +#include <kdepimmacros.h> + +namespace KABC { + +class KDE_EXPORT DavAddressBookAdaptor : public AddressBookAdaptor +{ + public: + DavAddressBookAdaptor() {} + + /** Interprets the results returned by the liste job (created by + createListFoldersJob(url) ). Typically, this adds an Entry to the mFolders list if + the job describes a folder of the appropriate type, by emitting + folderInfoRetrieved( href, displayName, type ). If the folder has + subfolders, just emit retrieveSubfolder( href ) for each of them. */ + virtual void interpretListFoldersJob( KIO::Job *job, KPIM::FolderLister *folderLister ); + /** Returns the type of folder retrieved in the dom node. Typically, you'll + compare the DAV:resourcetype property with some values. */ + virtual KPIM::FolderLister::ContentType getContentType( const QDomNode &folderNode ) = 0; + /** Extract from the dav response whether the folder has subitems that need + to be examined */ + virtual bool getFolderHasSubs( const QDomNode &folderNode ) = 0; +}; + +} + +#endif diff --git a/kresources/lib/davcalendaradaptor.cpp b/kresources/lib/davcalendaradaptor.cpp new file mode 100644 index 000000000..541b12bb8 --- /dev/null +++ b/kresources/lib/davcalendaradaptor.cpp @@ -0,0 +1,56 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "davcalendaradaptor.h" + +#include <kdebug.h> +#include <kio/davjob.h> +// #include <folderlister.h> + +// #include <qdom.h> + +using namespace KCal; + +// TODO: This is exactly the same code as for the DavAddressBookAdaptor::interpretListFoldersJob! +// But as this emits a signal, it needs to be located inside a QObject +void DavCalendarAdaptor::interpretListFoldersJob( KIO::Job *job, KPIM::FolderLister */*folderLister*/ ) +{ + KIO::DavJob *davjob = dynamic_cast<KIO::DavJob*>( job ); + Q_ASSERT( davjob ); + if ( !davjob ) return; + + QDomDocument doc = davjob->response(); + kdDebug(7000) << " Doc: " << doc.toString() << endl; + + QDomElement docElement = doc.documentElement(); + QDomNode n; + for( n = docElement.firstChild(); !n.isNull(); n = n.nextSibling() ) { + QDomNode n2 = n.namedItem( "propstat" ); + QDomNode n3 = n2.namedItem( "prop" ); + + KURL href( n.namedItem( "href" ).toElement().text() ); + QString displayName = n3.namedItem( "displayname" ).toElement().text(); + KPIM::FolderLister::ContentType type = getContentType( n3 ); + + emit folderInfoRetrieved( href, displayName, type ); + emit folderSubitemRetrieved( href, getFolderHasSubs( n3 ) ); + } +} diff --git a/kresources/lib/davcalendaradaptor.h b/kresources/lib/davcalendaradaptor.h new file mode 100644 index 000000000..3c4a7bc4f --- /dev/null +++ b/kresources/lib/davcalendaradaptor.h @@ -0,0 +1,52 @@ + /* + This file is part of kdepim. + + Copyright (C) 2004 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KCAL_DAVCALENDARADAPTOR_H +#define KCAL_DAVCALENDARADAPTOR_H + +#include "calendaradaptor.h" +#include "folderlister.h" +#include <qdom.h> +#include <kdepimmacros.h> + +namespace KCal { + +class KDE_EXPORT DavCalendarAdaptor : public CalendarAdaptor +{ + public: + DavCalendarAdaptor() {} + + /** Interprets the results returned by the liste job (created by + createListFoldersJob(url) ). Typically, this adds an Entry to the mFolders list if + the job describes a folder of the appropriate type, by emitting + folderInfoRetrieved( href, displayName, type ). If the folder has + subfolders, just emit retrieveSubfolder( href ) for each of them. */ + virtual void interpretListFoldersJob( KIO::Job *job, KPIM::FolderLister *folderLister ); + /** Returns the type of folder retrieved in the dom node. Typically, you'll + compare the DAV:resourcetype property with some values. */ + virtual KPIM::FolderLister::ContentType getContentType( const QDomNode &folderNode ) = 0; + /** Extract from the dav response whether the folder has subitems that need + to be examined */ + virtual bool getFolderHasSubs( const QDomNode &folderNode ) = 0; +}; + +} + +#endif diff --git a/kresources/lib/davgroupwareglobals.cpp b/kresources/lib/davgroupwareglobals.cpp new file mode 100644 index 000000000..5795c97ba --- /dev/null +++ b/kresources/lib/davgroupwareglobals.cpp @@ -0,0 +1,22 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004-2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "davgroupwareglobals.h" diff --git a/kresources/lib/davgroupwareglobals.h b/kresources/lib/davgroupwareglobals.h new file mode 100644 index 000000000..a899370fc --- /dev/null +++ b/kresources/lib/davgroupwareglobals.h @@ -0,0 +1,30 @@ + /* + This file is part of kdepim. + + Copyright (c) 2004-2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef DAVGROUPWAREGLOBALS_H +#define DAVGROUPWAREGLOBALS_H + +class DAVGroupwareGlobals +{ + public: + DAVGroupwareGlobals() {} +}; + +#endif diff --git a/kresources/lib/folderconfig.cpp b/kresources/lib/folderconfig.cpp new file mode 100644 index 000000000..b02654945 --- /dev/null +++ b/kresources/lib/folderconfig.cpp @@ -0,0 +1,173 @@ +/* + This file is part of libkcal. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "folderconfig.h" + +#include "folderlister.h" +#include "groupwaredataadaptor.h" +#include "folderlistview.h" + +#include <klistview.h> +#include <klocale.h> +#include <kdebug.h> +#include <kdialog.h> + +#include <qlayout.h> +#include <qgroupbox.h> +#include <qpushbutton.h> +#include <qcombobox.h> +#include <qhbox.h> +#include <qlabel.h> + +using namespace KPIM; + +FolderConfig::FolderConfig( QWidget *parent ) + : QWidget( parent ), mFolderLister( 0 ) +{ + QBoxLayout *topLayout = new QVBoxLayout( this ); + topLayout->addSpacing( KDialog::spacingHint() ); + + QGroupBox *topBox = new QGroupBox( 1, Horizontal, i18n("Folder Selection"), + this ); + topLayout->addWidget( topBox ); + + QPushButton *button = new QPushButton( i18n("Update Folder List"), topBox ); + connect( button, SIGNAL( clicked() ), SIGNAL( updateFoldersClicked() ) ); + + mFolderList = new FolderListView( topBox ); + +/* QHBox *writeBox = new QHBox( topBox ); + + new QLabel( i18n("Write to:"), writeBox ); + + mWriteCombo = new QComboBox( writeBox );*/ +} + +FolderConfig::~FolderConfig() +{ +} + +void FolderConfig::setFolderLister( FolderLister *f ) +{ + mFolderLister = f; + + QValueList<FolderListView::Property> types; + QValueList<FolderLister::ContentType> suptypes( mFolderLister->supportedTypes() ); + if ( suptypes.contains( FolderLister::Event ) ) types << FolderListView::Event; + if ( suptypes.contains( FolderLister::Todo ) ) types << FolderListView::Todo; + if ( suptypes.contains( FolderLister::Journal ) ) types << FolderListView::Journal; + if ( suptypes.contains( FolderLister::Contact ) ) types << FolderListView::Contact; + if ( suptypes.contains( FolderLister::All ) ) types << FolderListView::All; + if ( suptypes.contains( FolderLister::Unknown ) ) types << FolderListView::Unknown; + + mFolderList->setEnabledTypes( types ); + connect( mFolderLister, SIGNAL( foldersRead() ), SLOT( updateFolderList() ) ); +} + +void FolderConfig::retrieveFolderList( const KURL &url ) +{ + kdDebug(7000) << "FolderConfig::retrieveFolderList()" << endl; + if ( !mOldFolderListerURL.isEmpty() ) return; + + if ( mFolderLister->adaptor() ) { + mOldFolderListerURL = mFolderLister->adaptor()->baseURL(); + mFolderLister->adaptor()->setBaseURL( url ); + } + mFolderLister->retrieveFolders( url ); +} + +void FolderConfig::updateFolderList() +{ + mFolderList->clear(); + + QStringList write; + + if ( !mOldFolderListerURL.isEmpty() && mFolderLister->adaptor() ) { + mFolderLister->adaptor()->setBaseURL( mOldFolderListerURL ); + mOldFolderListerURL = KURL(); + } + + FolderLister::Entry::List folders = mFolderLister->folders(); + FolderLister::Entry::List::ConstIterator it; + for( it = folders.begin(); it != folders.end(); ++it ) { + FolderListItem *item = new FolderListItem( mFolderList, (*it) ); + if ( mFolderLister->writeDestinationId( FolderLister::Event ) == (*it).id ) { + item->setDefault( FolderListView::Event ); + } + if ( mFolderLister->writeDestinationId( FolderLister::Todo ) == (*it).id ) { + item->setDefault( FolderListView::Todo ); + } + if ( mFolderLister->writeDestinationId( FolderLister::Journal ) == (*it).id ) { + item->setDefault( FolderListView::Journal ); + } + if ( mFolderLister->writeDestinationId( FolderLister::Contact ) == (*it).id ) { + item->setDefault( FolderListView::Contact ); + } + if ( mFolderLister->writeDestinationId( FolderLister::All ) == (*it).id ) { + item->setDefault( FolderListView::All ); + } + if ( mFolderLister->writeDestinationId( FolderLister::Unknown ) == (*it).id ) { + item->setDefault( FolderListView::Unknown ); + } + } +} + +void FolderConfig::saveSettings() +{ + QPtrList<QListViewItem> lst; + + FolderLister::Entry::List folders; + + QListViewItemIterator it( mFolderList ); + while ( it.current() ) { + FolderListItem *item = dynamic_cast<FolderListItem *>( it.current() ); + if ( item ) { + FolderLister::Entry folder = item->folder(); + folder.active = item->isOn(); + folders.append( folder ); + if ( item->isDefault( FolderListView::Event ) ) { + mFolderLister->setWriteDestinationId( FolderLister::Event, folder.id ); + } + if ( item->isDefault( FolderListView::Todo ) ) { + mFolderLister->setWriteDestinationId( FolderLister::Todo, folder.id ); + } + if ( item->isDefault( FolderListView::Journal ) ) { + mFolderLister->setWriteDestinationId( FolderLister::Journal, folder.id ); + } + if ( item->isDefault( FolderListView::Contact ) ) { + mFolderLister->setWriteDestinationId( FolderLister::Contact, folder.id ); + } + if ( item->isDefault( FolderListView::All ) ) { + mFolderLister->setWriteDestinationId( FolderLister::All, folder.id ); + } + if ( item->isDefault( FolderListView::Unknown ) ) { + mFolderLister->setWriteDestinationId( FolderLister::Unknown, folder.id ); + } + } + ++it; + } + + mFolderLister->setFolders( folders ); +} + +#include "folderconfig.moc" diff --git a/kresources/lib/folderconfig.h b/kresources/lib/folderconfig.h new file mode 100644 index 000000000..5926392cc --- /dev/null +++ b/kresources/lib/folderconfig.h @@ -0,0 +1,65 @@ +/* + This file is part of libkcal. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KPIM_FOLDERCONFIG_H +#define KPIM_FOLDERCONFIG_H + +#include <kurl.h> +#include <kdepimmacros.h> +#include <qwidget.h> + +// class KListView; +class QComboBox; +class FolderListView; + +namespace KPIM { + +class FolderLister; + +class KDE_EXPORT FolderConfig : public QWidget +{ + Q_OBJECT + public: + FolderConfig( QWidget *parent ); + ~FolderConfig(); + + void setFolderLister( FolderLister * ); + + void saveSettings(); + + public slots: + void updateFolderList(); + void retrieveFolderList( const KURL & ); + + signals: + void updateFoldersClicked(); + + private: + FolderListView *mFolderList; + + FolderLister *mFolderLister; + KURL mOldFolderListerURL; +}; + +} + +#endif diff --git a/kresources/lib/folderlister.cpp b/kresources/lib/folderlister.cpp new file mode 100644 index 000000000..faf2204f7 --- /dev/null +++ b/kresources/lib/folderlister.cpp @@ -0,0 +1,372 @@ +/* + This file is part of libkcal. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2004 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "folderlister.h" +#include "groupwaredataadaptor.h" +#include "kresources_groupwareprefs.h" + +#include <kio/job.h> + +#include <kdebug.h> +#include <kconfig.h> +#include <qstringlist.h> + +using namespace KPIM; + +FolderLister::FolderLister( Type type ) + : mType( type ), mAdaptor( 0 ) +{ +} + +void FolderLister::setFolders( const FolderLister::Entry::List &folders ) +{ + mFolders = folders; +} + +void FolderLister::setWriteDestinationId( KPIM::FolderLister::ContentType type, const QString &id ) +{ + mWriteDestinationId[ type ] = id; +} + +QString FolderLister::writeDestinationId( KPIM::FolderLister::ContentType type ) const +{ + if ( mWriteDestinationId.contains( type ) ) { + return mWriteDestinationId[type]; + } else if ( mWriteDestinationId.contains( KPIM::FolderLister::All ) ) { + return mWriteDestinationId[ KPIM::FolderLister::All ]; + } else if ( mWriteDestinationId.contains( KPIM::FolderLister::Unknown ) ) { + return mWriteDestinationId[ KPIM::FolderLister::Unknown ]; + } else return QString::null; +} + + +KURL::List FolderLister::activeFolderIds() const +{ + KURL::List ids; + + FolderLister::Entry::List::ConstIterator it; + for( it = mFolders.begin(); it != mFolders.end(); ++it ) { + if ( (*it).active ) { + ids.append( KURL((*it).id) ); + } + } + + return ids; +} + +bool FolderLister::isActive( const QString &id ) const +{ + FolderLister::Entry::List::ConstIterator it; + for( it = mFolders.begin(); it != mFolders.end(); ++it ) { + if ( (*it).id == id ) return (*it).active; + } + return false; +} + +QStringList FolderLister::contentTypeToStrings( ContentType type ) +{ +kdDebug() << "FolderLister::contentTypeToStrings( type=" << type << ")" << endl; + QStringList cont; + if ( type == All ) { + cont << "All"; + } else if ( type == Unknown ) { + cont << "Unknown"; + } else { + if ( type & Contact ) cont << "Contact"; + if ( type & Event ) cont << "Event"; + if ( type & Todo ) cont << "Todo"; + if ( type & Journal ) cont << "Journal"; + if ( type & Message ) cont << "Message"; + if ( type & Memo ) cont << "Memo"; + if ( type & Folder ) cont << "Folder"; + } + return cont; +} + +FolderLister::ContentType FolderLister::contentTypeFromString( const QString &type ) +{ + if ( type == "All" ) return All; + if ( type == "Contact" ) return Contact; + if ( type == "Event" ) return Event; + if ( type == "Todo" ) return Todo; + if ( type == "Journal" ) return Journal; + if ( type == "Message" ) return Message; + if ( type == "Memo" ) return Memo; + if ( type == "Folder" ) return Folder; + return Unknown; +} + +QValueList<FolderLister::ContentType> FolderLister::supportedTypes() +{ + if ( adaptor() ) { + return adaptor()->supportedTypes(); + } else { + return QValueList<ContentType>(); + } +} + + + +void FolderLister::readConfig( KPIM::GroupwarePrefsBase *newprefs ) +{ + kdDebug(7000) << "FolderLister::readConfig()" << endl; + mFolders.clear(); + + QStringList active = newprefs->activeFolders(); + int nr = newprefs->folderNumber(); + + for ( int i=0; i<nr; ++i ) { + QStringList l( newprefs->folder( i ) ); +// QStringList l( cfgg.readListEntry( QString("Folder%1").arg( i ) ) ); + Entry e; + if ( l.count()>0 ) { + e.id = l.first(); + l.pop_front(); + } + if ( l.count()>1 ) { + e.name = l.first(); + l.pop_front(); + } + e.type = Unknown; + for ( QStringList::Iterator it = l.begin(); it != l.end(); ++it ) { + e.type = (FolderLister::ContentType)( e.type | contentTypeFromString( *it ) ); + } + if ( active.find( e.id ) != active.end() ) e.active = true; + mFolders.append( e ); + } + + QStringList destinations( newprefs->defaultDestinations() ); + + #define readDestination(type) \ + if ( destinations.count()>0 ) { \ + mWriteDestinationId[ type ] = destinations.first(); \ + destinations.pop_front(); \ + } + readDestination( FolderLister::Event ); + readDestination( FolderLister::Todo ); + readDestination( FolderLister::Journal ); + readDestination( FolderLister::Contact ); + readDestination( FolderLister::All ); + readDestination( FolderLister::Unknown ); + #undef readDestination +} + +void FolderLister::writeConfig( GroupwarePrefsBase *newprefs ) +{ + QStringList ids; + QStringList names; + QStringList active; + +// KConfigGroup cfgg( newprefs->config(), "Folders" ); + int nr = 0; + Entry::List::ConstIterator it; + for( it = mFolders.begin(); it != mFolders.end(); ++it ) { + QStringList lst; + lst << (*it).id; + lst << (*it).name; + lst += contentTypeToStrings( (*it).type ); + newprefs->setFolder( nr, lst ); +// cfgg.writeEntry( QString("Folder%1").arg( nr ), lst ); + if ( (*it).active ) active.append( (*it).id ); + nr++; + } + newprefs->setFolderNumber( nr ); + + newprefs->setActiveFolders( active ); + + QStringList defaultFolders; + #define writeDestination(type) \ + if ( mWriteDestinationId.contains( type ) ) \ + defaultFolders << mWriteDestinationId[type]; \ + else defaultFolders << QString::null; + writeDestination( KPIM::FolderLister::Event ); + writeDestination( KPIM::FolderLister::Todo ); + writeDestination( KPIM::FolderLister::Journal ); + writeDestination( KPIM::FolderLister::Contact ); + writeDestination( KPIM::FolderLister::All ); + writeDestination( KPIM::FolderLister::Unknown ); + #undef writeDestination + + newprefs->setDefaultDestinations( defaultFolders ); +} + +void FolderLister::setAdaptor( KPIM::GroupwareDataAdaptor *adaptor ) +{ + if ( mAdaptor ) { + disconnect( mAdaptor, 0, this, 0 ); + } + mAdaptor = adaptor; + connect( mAdaptor, SIGNAL( folderInfoRetrieved( const KURL &, + const QString &, KPIM::FolderLister::ContentType ) ), + this, SLOT( processFolderResult( const KURL &, const QString &, + KPIM::FolderLister::ContentType ) ) ); + connect( mAdaptor, SIGNAL( folderSubitemRetrieved( const KURL &, bool ) ), + this, SLOT( folderSubitemRetrieved( const KURL &, bool ) ) ); +} + +void FolderLister::folderSubitemRetrieved( const KURL &url, bool isFolder ) +{ + if ( isFolder ) + doRetrieveFolder( url ); + else { + KURL u( url ) ; + u.setUser( QString::null ); + u.setPass( QString::null ); + mProcessedPathes.append( url.path(-1) ); + } +} + +void FolderLister::retrieveFolders( const KURL &u ) +{ +kdDebug()<<"FolderLister::retrieveFolders( "<<u.url()<<" )"<<endl; + mUrls.clear(); + mProcessedPathes.clear(); + bool firstRetrieve = mFolders.isEmpty(); + mFolders = defaultFolders(); + Entry::List::Iterator it = mFolders.begin(); + + for ( ; it != mFolders.end(); ++it ) { + if ( firstRetrieve ) { + (*it).active = true; + } else { + (*it).active = isActive( (*it).id ); + } + } + + doRetrieveFolder( u ); +} + +void FolderLister::doRetrieveFolder( const KURL &u ) +{ + kdDebug(7000) << "FolderLister::doRetrieveFolder: " << u.prettyURL() << endl; + + KURL url( u ); + if ( adaptor() ) adaptor()->adaptDownloadUrl( url ); + if ( mUrls.contains( url ) || mProcessedPathes.contains( url.path(-1) ) ) { + kdDebug()<<"Item "<<u.path(-1)<<" is already being downloaded "<<endl; + } else { + + KIO::Job *listjob = createListFoldersJob( url ); + if ( listjob ) { + mUrls.append( url ); + + kdDebug(7000) << "FolderLister::retrieveFolders: adjustedURL=" + << url.prettyURL() << endl; + connect( listjob, SIGNAL( result( KIO::Job * ) ), + SLOT( slotListJobResult( KIO::Job * ) ) ); + } else { + // TODO: Indicate a problem to the user! + kdWarning() << "Unable to create the folder list job for the url " + << url.prettyURL() << endl; + } + } + if ( mUrls.isEmpty() ) { + kdDebug()<<"No more URLS to download, emitting foldersRead()"<<endl; + emit foldersRead(); + } +} + +FolderLister::Entry::List FolderLister::defaultFolders() +{ + if ( adaptor() ) { + return adaptor()->defaultFolders(); + } else { + return Entry::List(); + } +} + +void FolderLister::processFolderResult( const KURL &href, + const QString &displayName, + ContentType type ) +{ +kdDebug() << "FolderLister::processFolderResult( href=" << href.url() << ", displayName=" << displayName << ", type=" << int(type) << endl; + if ( ( mType == Calendar && ( type & ( Event | Todo |Journal) ) ) || + ( mType == AddressBook && (type & Contact ) ) ) { + + if ( !href.isEmpty() && !displayName.isEmpty() ) { + Entry entry; + entry.id = href.url(); + entry.name = displayName; + entry.type = type; + entry.active = isActive( entry.id ); + + mFolders.append( entry ); + } + kdDebug(7000) << "FOLDER: " << displayName << endl; +kdDebug()<<"mFolders.size="<<mFolders.size()<<endl; + } else { +kdDebug() << "Folder "<< href << " is not of correct type ("<<type<<")"<<endl; + } +} + +void FolderLister::slotListJobResult( KIO::Job *job ) +{ + kdDebug(7000) << "OpenGroupware::slotListJobResult(): " << endl; + kdDebug() << "URLS (" << mUrls.count() << "): " << mUrls.toStringList().join(" | ") << endl; + kdDebug() << "Processed URLS (" << mProcessedPathes.count() << "): " + << mProcessedPathes.join(" | ") << endl; + KIO::SimpleJob *j = dynamic_cast<KIO::SimpleJob*>(job); + if ( j ) { + mUrls.remove( j->url() ); + mProcessedPathes.append( j->url().path(-1) ); + } + + if ( job->error() ) { + kdError() << "Unable to retrieve folders." << endl; + } else { + interpretListFoldersJob( job ); + } + kdDebug() << "After URLS (" << mUrls.count() << "): " + << mUrls.toStringList().join(" | ") << endl; + kdDebug() << "After Processed URLS (" << mProcessedPathes.count() << "): " + << mProcessedPathes.join(" | ") << endl; + if ( mUrls.isEmpty() ) { + kdDebug()<<"No more URLS to download, emitting foldersRead()"<<endl; + emit foldersRead(); + } +} + +void FolderLister::interpretListFoldersJob( KIO::Job *job ) +{ + if ( adaptor() ) { + adaptor()->interpretListFoldersJob( job, this ); + } else { + // TODO: Error handling should show a message to the user! + kdError() << "The FolderLister does not have a GroupwareDataAdaptor, so " + "it cannot interpret the response!" << endl; + } +} + +KIO::Job *FolderLister::createListFoldersJob( const KURL &url ) +{ + if ( adaptor() ) { + return adaptor()->createListFoldersJob( url ); + } else { + // TODO: Error handling should show a message to the user! + kdError() << "The FolderLister does not have a GroupwareDataAdaptor, so " + "it cannot create the job for the folder list!" << endl; + return 0; + } +} + +#include "folderlister.moc" diff --git a/kresources/lib/folderlister.h b/kresources/lib/folderlister.h new file mode 100644 index 000000000..c8a70ef10 --- /dev/null +++ b/kresources/lib/folderlister.h @@ -0,0 +1,150 @@ +/* + This file is part of libkcal. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2004 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KPIM_FOLDERLISTER_H +#define KPIM_FOLDERLISTER_H + +// #include "kresources_groupwareprefs.h" +/*#include "groupwareresourcejob.h"*/ +#include <kurl.h> +#include <kdepimmacros.h> + +#include <qvaluelist.h> +#include <qstring.h> +#include <qstringlist.h> +#include <qobject.h> + +namespace KIO { +class Job; +} + +class KConfig; + +namespace KPIM { + +class GroupwareDataAdaptor; +class GroupwarePrefsBase; + + +class KDE_EXPORT FolderLister : public QObject +{ + Q_OBJECT + public: + enum Type { AddressBook, Calendar }; + enum ContentType { + Contact=0x1, Event=0x2, Todo=0x4, Journal=0x8, + Message=0x10, Memo=0x20, Folder=0x40, + Incidences=Event|Todo|Journal, All=Contact|Incidences, + Unknown=0x000 + }; + + class Entry + { + public: + Entry() : active( false ) {} + + typedef QValueList<Entry> List; + + QString id; + QString name; + ContentType type; + bool active; + }; + static QStringList contentTypeToStrings( ContentType ); + ContentType contentTypeFromString( const QString &type ); + + QValueList<ContentType> supportedTypes(); + + FolderLister( Type ); + + /** Initialize the retrieval with given root URL */ + virtual void retrieveFolders( const KURL & ); + + void setFolders( const Entry::List & ); + Entry::List folders() const { return mFolders; } + + void setAdaptor( KPIM::GroupwareDataAdaptor *adaptor ); + GroupwareDataAdaptor* adaptor() const { return mAdaptor; } + + KURL::List activeFolderIds() const; + bool isActive( const QString &id ) const; + + void setWriteDestinationId( KPIM::FolderLister::ContentType type, const QString &dest ); + QString writeDestinationId( KPIM::FolderLister::ContentType type ) const; + + void readConfig( KPIM::GroupwarePrefsBase *newprefs ); + void writeConfig( KPIM::GroupwarePrefsBase *newprefs ); + + + signals: + void foldersRead(); + + protected slots: + void slotListJobResult( KIO::Job * ); + /** Adds the folder with the given url and display name to the folder + * tree (if is has an appropriate type) */ + virtual void processFolderResult( const KURL &href, + const QString &displayName, + KPIM::FolderLister::ContentType type ); + /** Retrieve information about the folder u. If it has sub-folders, it + descends into the hierarchy */ + virtual void doRetrieveFolder( const KURL &u ); + /** A subitem was detected. If it's a folder, we need to descend, otherwise + we just add the url to the list of processed URLs. */ + void folderSubitemRetrieved( const KURL &url, bool isFolder ); + + protected: + /** Creates the job to retrieve information about the folder at the given + url. It's results will be interpreted by interpretFolderResult + */ + virtual KIO::Job *createListFoldersJob( const KURL &url ); + /** Interprets the results returned by the liste job (created by + * createJob(url) ). The default implementation calls + * interpretFolderListJob of the GroupwareDataAdaptor. Typically, + * this adds an Entry to the mFolders list if the job describes a + * folder of the appropriate type, by calling processsFolderResult. + * If the folder has subfolders, just call doRetrieveFolder(url) + * recursively. */ + virtual void interpretListFoldersJob( KIO::Job *job ); + /** List of folders that will always be included (subfolders won't!). + * Usually this is not needed as you should traverse the whole folder + * tree starting from the user's root dir. */ + virtual Entry::List defaultFolders(); + /** Type of this folder lister (i.e. AddressBook or Calendar) */ + Type getType() const { return mType; } + + + protected: + Type mType; + KURL::List mUrls; + QStringList mProcessedPathes; + Entry::List mFolders; + GroupwareDataAdaptor *mAdaptor; + private: + // TODO: We need multiple destinations for Events, Tasks and Journals + QMap<KPIM::FolderLister::ContentType, QString> mWriteDestinationId; + KURL mOldURL; +}; + +} + +#endif diff --git a/kresources/lib/folderlistview.cpp b/kresources/lib/folderlistview.cpp new file mode 100644 index 000000000..1ab593553 --- /dev/null +++ b/kresources/lib/folderlistview.cpp @@ -0,0 +1,296 @@ +/* This file is part of the KDE libraries + + Copyright (C) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + Taken in large parts from the kate highlighting list view kateschema.cpp: + Copyright (C) 2001-2003 Christoph Cullmann <cullmann@kde.org> + Copyright (C) 2002, 2003 Anders Lund <anders.lund@lund.tdcadsl.dk> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License version 2 as published by the Free Software Foundation. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "folderlistview.h" +#include "folderlister.h" + +#include <klistview.h> +#include <klocale.h> +#include <kiconloader.h> +#include <kpopupmenu.h> +#include <kdebug.h> + +#include <qlistview.h> +#include <qheader.h> +#include <qpainter.h> + +static const int BoxSize = 16; + + +//BEGIN FolderListView +FolderListView::FolderListView( QWidget *parent, const QValueList<Property> &types ) + : KListView( parent ) +{ + setEnabledTypes( types ); + + connect( this, SIGNAL(mouseButtonPressed(int, QListViewItem*, const QPoint&, int)), + this, SLOT(slotMousePressed(int, QListViewItem*, const QPoint&, int)) ); + connect( this, SIGNAL(spacePressed(QListViewItem*)), + this, SLOT(showPopupMenu(QListViewItem*)) ); +} + +void FolderListView::setEnabledTypes( const QValueList<Property> &types ) +{ +kdDebug() << "FolderListView::setEnabledTypes" << endl; + for ( int i = 0; i< columns(); ++i ) removeColumn( i ); + mTypes = types; + if ( !mTypes.contains( FolderName ) ) mTypes.prepend( FolderName ); + mColumnMap[FolderName] = addColumn( i18n("Folder") ); + mTypeMap[mColumnMap[FolderName]] = FolderName; + + + if ( mTypes.contains( Event ) ) { + mColumnMap[Event] = addColumn( i18n("Short column header meaning default for new events", "Events") ); + mTypeMap[mColumnMap[Event]] = Event; + } else mColumnMap[Event] = -1; + + if ( mTypes.contains( Todo ) ) { + mColumnMap[Todo] = addColumn( i18n("Short column header meaning default for new to-dos", "Todos") ); + mTypeMap[mColumnMap[Todo]] = Todo; + } else mColumnMap[Todo] = -1; + + if ( mTypes.contains( Journal ) ) { + mColumnMap[Journal] = addColumn( i18n("Short column header meaning default for new journals", "Journals") ); + mTypeMap[mColumnMap[Journal]] = Journal; + } else mColumnMap[Journal] = -1; + + if ( mTypes.contains( Contact ) ) { + mColumnMap[Contact] = addColumn( i18n("Short column header meaning default for new contacts", "Contacts") ); + mTypeMap[mColumnMap[Contact]] = Contact; + } else mColumnMap[Contact] = -1; + + if ( mTypes.contains( All ) ) { + mColumnMap[All] = addColumn( i18n("Short column header meaning default for all items", "All") ); + mTypeMap[mColumnMap[All]] = All; + } else mColumnMap[All] = -1; + + if ( mTypes.contains( Unknown ) ) { + mColumnMap[Unknown] = addColumn( i18n("Short column header meaning default for unknown new items", "Unknown") ); + mTypeMap[mColumnMap[Unknown]] = Unknown; + } else mColumnMap[Unknown] = -1; +} + +void FolderListView::showPopupMenu( FolderListItem *i, const QPoint &globalPos ) +{ + if ( !i ) return; + KPIM::FolderLister::Entry folder( i->folder() ); + + KPopupMenu m( this ); + int id; + + m.insertTitle( folder.name, 9999 ); + id = m.insertItem( i18n("&Enabled"), this, SLOT(slotPopupHandler(int)), 0, FolderName ); + m.setItemChecked( id, i->isOn() ); + m.insertSeparator(); + + if ( ( folder.type & KPIM::FolderLister::Event ) && (mTypes.contains( Event ) ) ) { + id = m.insertItem( i18n("Default for New &Events"), this, SLOT(slotPopupHandler(int)), 0, Event ); + m.setItemChecked( id, i->isDefault( Event ) ); + } + if ( ( folder.type & KPIM::FolderLister::Todo ) && (mTypes.contains( Todo ) ) ) { + id = m.insertItem( i18n("Default for New &Todos"), this, SLOT(slotPopupHandler(int)), 0, Todo ); + m.setItemChecked( id, i->isDefault( Todo ) ); + } + if ( ( folder.type & KPIM::FolderLister::Journal ) && (mTypes.contains( Journal ) ) ) { + id = m.insertItem( i18n("Default for New &Journals"), this, SLOT(slotPopupHandler(int)), 0, Journal ); + m.setItemChecked( id, i->isDefault( Journal ) ); + } + if ( ( folder.type & KPIM::FolderLister::Contact ) && (mTypes.contains( Contact ) ) ) { + id = m.insertItem( i18n("Default for New &Contacts"), this, SLOT(slotPopupHandler(int)), 0, Contact ); + m.setItemChecked( id, i->isDefault( Contact ) ); + } + if ( ( folder.type == KPIM::FolderLister::All ) && (mTypes.contains( All ) ) ) { + id = m.insertItem( i18n("Default for All New &Items"), this, SLOT(slotPopupHandler(int)), 0, All ); + m.setItemChecked( id, i->isDefault( All ) ); + } + if ( ( folder.type == KPIM::FolderLister::Unknown ) && (mTypes.contains( Unknown ) ) ) { + id = m.insertItem( i18n("Default for &Unknown New Items"), this, SLOT(slotPopupHandler(int)), 0, Unknown ); + m.setItemChecked( id, i->isDefault( Unknown ) ); + } + + m.exec( globalPos ); +} + +void FolderListView::showPopupMenu( QListViewItem *i ) +{ + if ( dynamic_cast<FolderListItem*>(i) ) + showPopupMenu( (FolderListItem*)i, viewport()->mapToGlobal(itemRect(i).topLeft()) ); +} + +void FolderListView::slotPopupHandler( int z ) +{ + ((FolderListItem*)currentItem())->changeProperty( (Property)z ); +} + +// Because QListViewItem::activatePos() is going to become deprecated, +// and also because this attempt offers more control, I connect mousePressed to this. +void FolderListView::slotMousePressed(int btn, QListViewItem* i, const QPoint& pos, int c) +{ + if ( dynamic_cast<FolderListItem*>(i) ) { + if ( btn == Qt::RightButton ) { + showPopupMenu( (FolderListItem*)i, /*mapToGlobal(*/pos/*)*/ ); + } + else if ( btn == Qt::LeftButton && c > 0 ) { + // map pos to item/column and call FolderListItem::activate(col, pos) + ((FolderListItem*)i)->activate( c, viewport()->mapFromGlobal( pos ) - QPoint( 0, itemRect(i).top() ) ); +// } else { +// KListView::slotMousePressed( btn, i, pos, c ); + } + } +} + +//END + +//BEGIN FolderListItem + +void FolderListItem::activate( int column, const QPoint &localPos ) +{ + if ( !mFolderListView ) return; + QListView *lv = listView(); + int x = 0; + for( int c = 0; c < column-1; c++ ) + x += lv->columnWidth( c ); + int w; + FolderListView::Property prop( mFolderListView->typeForColumn(column) ); + switch( prop ) { + case FolderListView::Event: + case FolderListView::Todo: + case FolderListView::Journal: + case FolderListView::Contact: + case FolderListView::All: + case FolderListView::Unknown: + w = BoxSize; + break; + default: + return; + } + if ( !QRect( x, 0, w, BoxSize ).contains( localPos ) ) + changeProperty( prop ); +} + +void FolderListItem::changeProperty( FolderListView::Property p ) +{ +kdDebug() << "FolderListItem::changeProperty( " << p << ")" << endl; + if ( p == FolderListView::FolderName ) { +kdDebug() << "it's folderName" << endl; + setOn( !isOn() ); + } else if ( typeSupported( p ) ) { + QListViewItemIterator it( listView() ); + while ( it.current() ) { + FolderListItem *item = dynamic_cast<FolderListItem*>( it.current() ); + if ( item ) { + item->setDefault( p, item==this ); + } + ++it; + } + } + listView()->triggerUpdate(); + ((FolderListView*)listView())->emitChanged(); +} + + +bool FolderListItem::typeSupported( FolderListView::Property prop ) +{ + return ( (prop==FolderListView::Event) && (mFolder.type & KPIM::FolderLister::Event) ) || + ( (prop==FolderListView::Todo) && (mFolder.type & KPIM::FolderLister::Todo) ) || + ( (prop==FolderListView::Journal)&& (mFolder.type & KPIM::FolderLister::Journal) ) || + ( (prop==FolderListView::Contact)&& (mFolder.type & KPIM::FolderLister::Contact) ) || + ( (prop==FolderListView::All) && (mFolder.type == KPIM::FolderLister::All) ) || + ( (prop==FolderListView::Unknown)&& (mFolder.type == KPIM::FolderLister::Unknown) ); +} + +bool FolderListItem::isDefault( FolderListView::Property prop ) +{ + if ( !typeSupported( prop ) || prop<0 || prop>=FolderListView::PROP_MAX ) return false; + else return mIsDefault[ prop ]; +} + +void FolderListItem::setDefault( FolderListView::Property prop, bool def ) +{ + if ( prop<0 || prop>=FolderListView::PROP_MAX ) return; + else mIsDefault[ prop ] = def; + +} + + +void FolderListItem::paintCell( QPainter *p, const QColorGroup &cg, int col, int width, int align ) +{ + if ( !p ) return; + + QListView *lv = listView(); + Q_ASSERT( lv ); //### + if ( !lv ) return; + + // use a private color group and set the text/highlighted text colors +// QColorGroup mcg = lv->viewport()->colorGroup(); + FolderListView::Property prop( mFolderListView->typeForColumn(col) ); + + if ( prop == FolderListView::FolderName ) { + // col 0 is drawn by the superclass method + super::paintCell( p, cg, col, width, align ); + return; + } else { + p->fillRect( 0, 0, width, height(), QBrush( cg.base() ) ); + } + + int marg = lv->itemMargin(); + QColor c; + + switch ( prop ) + { + case FolderListView::Event: + case FolderListView::Todo: + case FolderListView::Journal: + case FolderListView::Contact: + case FolderListView::All: + case FolderListView::Unknown: + { + if ( !typeSupported( prop ) ) break; + + int x = 0; + int y = (height() - BoxSize) / 2; + + if ( isEnabled() ) + p->setPen( QPen( cg.text(), 1 ) ); + else + p->setPen( QPen( lv->palette().color( QPalette::Disabled, QColorGroup::Text ), 1 ) ); + + p->drawEllipse( x+marg, y+2, BoxSize-4, BoxSize-4 ); + + if ( isDefault( prop ) ) { + if ( isEnabled() ) + p->setBrush( cg.text() ); + else + p->setBrush( lv->palette().color( QPalette::Disabled, QColorGroup::Text ) ); + p->drawEllipse( x + marg + 3, y + 5, BoxSize-10, BoxSize-10 ); + } + break; + } + default: + break; + } +} +//END + +#include "folderlistview.moc" +// kate: space-indent on; indent-width 2; replace-tabs on; diff --git a/kresources/lib/folderlistview.h b/kresources/lib/folderlistview.h new file mode 100644 index 000000000..d933402a3 --- /dev/null +++ b/kresources/lib/folderlistview.h @@ -0,0 +1,129 @@ +/* This file is part of the KDE libraries + + Copyright (C) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + Taken in large parts from the kate highlighting list view kateschema.h: + Copyright (C) 2001-2003 Christoph Cullmann <cullmann@kde.org> + Copyright (C) 2002, 2003 Anders Lund <anders.lund@lund.tdcadsl.dk> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License version 2 as published by the Free Software Foundation. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#ifndef FOLDERLISTVIEW_H +#define FOLDERLISTVIEW_H + +#include <klistview.h> +#include "folderlister.h" + +class FolderListItem; +class FolderListCaption; + + +/* + QListView that automatically adds columns for FolderListItems for selecting + the default destination and a slot to edit the destinations using the keyboard. +*/ +class FolderListView : public KListView +{ + Q_OBJECT + + friend class FolderListItem; + + public: + /* mainly for readability */ + enum Property { FolderName, Event, Todo, Journal, Contact, All, Unknown, PROP_MAX }; + + FolderListView( QWidget *parent, const QValueList<Property> &types = QValueList<Property>() ); + ~FolderListView() {}; + + /* Display a popupmenu for item i at the specified global position, eventually with a title, + promoting the context name of that item */ + void showPopupMenu( FolderListItem *i, const QPoint &globalPos ); + void emitChanged() { emit changed(); }; + void setEnabledTypes( const QValueList<Property> &types ); + + int columnForType( Property prop ) const { if ( mColumnMap.contains(prop) ) return mColumnMap[prop]; else return -1;} + Property typeForColumn( int col ) const { if ( mTypeMap.contains( col ) ) return mTypeMap[col]; else return Unknown; } + + private slots: + /* Display a popupmenu for item i at item position */ + void showPopupMenu( QListViewItem *i ); + /* call item to change a property, or display a menu */ + void slotMousePressed( int, QListViewItem*, const QPoint&, int ); + /* asks item to change the property in q */ + void slotPopupHandler( int z ); + + signals: + void changed(); + private: + QValueList<Property> mTypes; + QMap<Property,int> mColumnMap; + QMap<int,Property> mTypeMap; +}; + +/* + QListViewItem subclass to display/edit a folder on a groupware server. + Selection of default destinations will be done via radio items. +*/ +class FolderListItem : public QCheckListItem +{ + typedef QCheckListItem super; + public: + FolderListItem( FolderListItem *parent, const KPIM::FolderLister::Entry &folder ) + : QCheckListItem( parent, folder.name, QCheckListItem::CheckBoxController ), + mFolder( folder ), mFolderListView( parent?(parent->folderListView()):0 ) + { + setOn( mFolder.active ); + } + FolderListItem( FolderListView *listView, const KPIM::FolderLister::Entry &folder ) + : QCheckListItem( listView, folder.name, + QCheckListItem::CheckBoxController ), mFolder( folder ), mFolderListView( listView ) + { + setOn( mFolder.active ); + } + + KPIM::FolderLister::Entry folder() const + { + return mFolder; + } + + /* reimp */ +// int width ( const QFontMetrics & fm, const QListView * lv, int c ) const; + + bool typeSupported( FolderListView::Property prop ); + bool isDefault( FolderListView::Property prop ); + void setDefault( FolderListView::Property prop, bool def = true ); + + /* calls changeProperty() if it makes sense considering pos. */ + void activate( int column, const QPoint &localPos ); + /* Sets this item as default for property p a */ + void changeProperty( FolderListView::Property p ); + + FolderListView *folderListView() const { return mFolderListView; } + + protected: + /* reimp */ + void paintCell(QPainter *p, const QColorGroup& cg, int col, int width, int align); + + private: + KPIM::FolderLister::Entry mFolder; + bool mIsDefault[FolderListView::PROP_MAX]; + FolderListView *mFolderListView; +}; + + +#endif + +// kate: space-indent on; indent-width 2; replace-tabs on; diff --git a/kresources/lib/folderselectdialog.cpp b/kresources/lib/folderselectdialog.cpp new file mode 100644 index 000000000..07b8bc8fe --- /dev/null +++ b/kresources/lib/folderselectdialog.cpp @@ -0,0 +1,83 @@ +/* + This file is part of kdepim. + + Copyright (c) 2008 Kevin Ottens <ervin@kde.org> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. + + In addition, as a special exception, the copyright holders give + permission to link the code of this program with any edition of + the Qt library by Trolltech AS, Norway (or with modified versions + of Qt that use the same license as Qt), and distribute linked + combinations including the two. You must obey the GNU General + Public License in all respects for all of the code used other than + Qt. If you modify this file, you may extend this exception to + your version of the file, but you are not obligated to do so. If + you do not wish to do so, delete this exception statement from + your version. +*/ + +#include "folderselectdialog.h" + +#include <qlayout.h> +#include <qlabel.h> + +using namespace KPIM; + +FolderSelectDialog::FolderSelectDialog( const QString& caption, const QString& label, + const QStringList& list ) + : KDialogBase(0, 0, true, caption, Ok, Ok, true) +{ + QFrame* frame = makeMainWidget(); + QVBoxLayout* layout = new QVBoxLayout( frame, 0, spacingHint() ); + + QLabel* labelWidget = new QLabel( label, frame ); + layout->addWidget( labelWidget ); + + mListBox = new KListBox( frame ); + mListBox->insertStringList( list ); + mListBox->setSelected( 0, true ); + mListBox->ensureCurrentVisible(); + layout->addWidget( mListBox, 10 ); + + connect( mListBox, SIGNAL( doubleClicked( QListBoxItem * ) ), + SLOT( slotOk() ) ); + connect( mListBox, SIGNAL( returnPressed( QListBoxItem * ) ), + SLOT( slotOk() ) ); + + mListBox->setFocus(); + + layout->addStretch(); + + setMinimumWidth( 320 ); +} + +QString FolderSelectDialog::getItem( const QString &caption, const QString &label, + const QStringList& list ) +{ + FolderSelectDialog dlg( caption, label, list ); + + QString result; + if ( dlg.exec() == Accepted ) + result = dlg.mListBox->currentText(); + + return result; +} + +void FolderSelectDialog::closeEvent(QCloseEvent *event) +{ + event->ignore(); +} diff --git a/kresources/lib/folderselectdialog.h b/kresources/lib/folderselectdialog.h new file mode 100644 index 000000000..2211b6f8f --- /dev/null +++ b/kresources/lib/folderselectdialog.h @@ -0,0 +1,58 @@ +/* + This file is part of kdepim. + + Copyright (c) 2008 Kevin Ottens <ervin@kde.org> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. + + In addition, as a special exception, the copyright holders give + permission to link the code of this program with any edition of + the Qt library by Trolltech AS, Norway (or with modified versions + of Qt that use the same license as Qt), and distribute linked + combinations including the two. You must obey the GNU General + Public License in all respects for all of the code used other than + Qt. If you modify this file, you may extend this exception to + your version of the file, but you are not obligated to do so. If + you do not wish to do so, delete this exception statement from + your version. +*/ + +#ifndef FOLDERSELECTDIALOG_H +#define FOLDERSELECTDIALOG_H + +#include <kdialogbase.h> + +namespace KPIM { + +class FolderSelectDialog : public KDialogBase +{ +private: + FolderSelectDialog( const QString& caption, const QString& label, + const QStringList& list ); + +public: + static QString getItem( const QString& caption, const QString& label, + const QStringList& list ); + +protected: + virtual void closeEvent(QCloseEvent *event); +private: + KListBox* mListBox; +}; + +} + +#endif // FOLDERSELECTDIALOG_H diff --git a/kresources/lib/groupwaredataadaptor.cpp b/kresources/lib/groupwaredataadaptor.cpp new file mode 100644 index 000000000..aa83f4674 --- /dev/null +++ b/kresources/lib/groupwaredataadaptor.cpp @@ -0,0 +1,283 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "groupwaredataadaptor.h" +#include <kdebug.h> +#include <kio/job.h> +#include <libemailfunctions/idmapper.h> + +using namespace KPIM; + +GroupwareUploadItem::GroupwareUploadItem( UploadType type ) : mItemType( KPIM::FolderLister::Unknown ), mType( type ) +{ +} + +KURL GroupwareUploadItem::adaptNewItemUrl( GroupwareDataAdaptor *adaptor, + const KURL &baseurl ) +{ +kdDebug()<<"GroupwareUploadItem::adaptNewItemUrl, baseurl=" << baseurl.url() << endl; + if ( adaptor ) { + QString path( adaptor->defaultNewItemName( this ) ); +kdDebug() << "path=" << path << endl; + KURL u( baseurl ); + if ( path.isEmpty() ) return u; + else { + u.addPath( path ); +kdDebug() << "Final Path for new item: " << u.url() << endl; + return u; + } + } else return baseurl; +} + +KIO::TransferJob *GroupwareUploadItem::createRawUploadJob( + GroupwareDataAdaptor *adaptor, const KURL &/*baseurl*/ ) +{ + Q_ASSERT( adaptor ); + if ( !adaptor ) return 0; + const QString dta = data(); + //kdDebug(7000) << "Uploading: " << data << endl; + KURL upUrl( url() ); + if ( adaptor ) + adaptor->adaptUploadUrl( upUrl ); + kdDebug(7000) << "Uploading to: " << upUrl.prettyURL() << endl; + KIO::TransferJob *job = KIO::storedPut( dta.utf8(), upUrl, -1, true, + false, false ); + job->addMetaData( "PropagateHttpHeader", "true" ); + if ( adaptor ) { + job->addMetaData( "customHTTPHeader", "Content-Type: " + adaptor->mimeType() ); + } + return job; +} + +KIO::TransferJob *GroupwareUploadItem::createUploadNewJob( + GroupwareDataAdaptor *adaptor, const KURL &baseurl ) +{ +kdDebug()<<"GroupwareUploadItem::createUploadNewJob, baseurl=" << baseurl.url() << endl; + setUrl( adaptNewItemUrl( adaptor, baseurl ) ); + KIO::TransferJob *job = createRawUploadJob( adaptor, baseurl ); + if ( job ) { + kdDebug() << "Adding If-None-Match " << endl; + QString header; + if ( job->outgoingMetaData().contains("customHTTPHeader") ) { + header = job->outgoingMetaData()["customHTTPHeader"]; + header += "\r\n"; + } + header += "If-None-Match: *"; + job->addMetaData( "customHTTPHeader", header ); + } + return job; +} + +KIO::TransferJob *GroupwareUploadItem::createUploadJob( + GroupwareDataAdaptor *adaptor, const KURL &baseurl ) +{ +kdDebug()<<"GroupwareUploadItem::createUploadJob" << endl; + KIO::TransferJob *job = createRawUploadJob( adaptor, baseurl ); + if ( job && adaptor ) { + kdDebug()<<"Adding If-Match header: " << adaptor->idMapper()->fingerprint( uid() ) << endl; + QString header; + if ( job->outgoingMetaData().contains("customHTTPHeader") ) { + header = job->outgoingMetaData()["customHTTPHeader"]; + header += "\r\n"; + } +kdDebug()<<"old HEADER: " << header << endl; + header += "If-Match: " + adaptor->idMapper()->fingerprint( uid() ); +kdDebug()<<"new HEADER: " << header << endl; + job->addMetaData( "customHTTPHeader", header ); + } + return job; +} + + +GroupwareDataAdaptor::GroupwareDataAdaptor() + : QObject(), mFolderLister( 0 ), mIdMapper( 0 ) +{ +} + +GroupwareDataAdaptor::~GroupwareDataAdaptor() +{ +} + +void GroupwareDataAdaptor::setUserPassword( KURL &url ) +{ + kdDebug(5800) << "GroupwareDataAdaptor::setUserPassword, mUser=" + << mUser << endl; + url.setUser( mUser ); + url.setPass( mPassword ); +} + +FolderLister::Entry::List GroupwareDataAdaptor::defaultFolders() +{ + return FolderLister::Entry::List(); +} + +KIO::TransferJob *GroupwareDataAdaptor::createUploadJob( const KURL &url, + GroupwareUploadItem *item ) +{ + if ( item ) { + KIO::TransferJob *job = item->createUploadJob( this, url ); + setUidForJob( job, item->uid() ); + return job; + } else return 0; +} + +KIO::TransferJob *GroupwareDataAdaptor::createUploadNewJob( const KURL &url, + GroupwareUploadItem *item ) +{ +kdDebug()<<"GroupwareDataAdaptor::createUploadNewJob, url=" << url.url() << endl; + if ( item ) { + KIO::TransferJob *job = item->createUploadNewJob( this, url ); + setUidForJob( job, item->uid() ); + return job; + } else return 0; +} + +void GroupwareDataAdaptor::processDownloadListItem( const KURL &entry, + const QString &newFingerprint, KPIM::FolderLister::ContentType type ) +{ + bool download = false; + const QString &location = entry.path(); + + emit itemOnServer( entry ); + // if not locally present, download + const QString &localId = idMapper()->localId( location ); + kdDebug(5800) << "Looking up remote: " << location + << " found: " << localId << endl; + if ( localId.isEmpty() || !localItemExists( localId ) ) { + //kdDebug(7000) << "Not locally present, download: " << location << endl; + download = true; + } else { + kdDebug(5800) << "Locally present " << endl; + // locally present, let's check if it's newer than what we have + const QString &oldFingerprint = idMapper()->fingerprint( localId ); + if ( oldFingerprint != newFingerprint ) { + kdDebug(5800) << "Fingerprint changed old: " << oldFingerprint << + " new: " << newFingerprint << endl; + // something changed on the server, check if we also changed it locally + if ( localItemHasChanged( localId ) ) { + // TODO conflict resolution + kdDebug(5800) << "TODO conflict resolution" << endl; + download = true; + } else { + download = true; + } + } else { + kdDebug(5800) << "Fingerprint not changed, don't download this " << endl; + } + } + if ( download ) { + emit itemToDownload( entry, type ); + } +} + +bool GroupwareDataAdaptor::interpretRemoveJob( KIO::Job *job, const QString &/*jobData*/ ) +{ + if ( !job ) return false; + KIO::DeleteJob *deljob = dynamic_cast<KIO::DeleteJob*>(job); + bool error = job->error(); + const QString err = job->errorString(); + + if ( deljob ) { + KURL::List urls( deljob->urls() ); + for ( KURL::List::Iterator it = urls.begin(); it != urls.end(); ++it ) { + if ( error ) { + emit itemDeletionError( *it, err ); + } else { + // FIXME: Don't use QString::null here + emit itemDeleted( QString::null, *it ); + } + } + return true; + } else { + return false; + } +} + + +bool GroupwareDataAdaptor::interpretUploadJob( KIO::Job *job, const QString &/*jobData*/ ) +{ + kdDebug(7000) << "GroupwareDataAdaptor::interpretUploadJob " << endl; + KIO::TransferJob *trfjob = dynamic_cast<KIO::TransferJob*>(job); + bool error = job->error(); + const QString err = job->errorString(); + + if ( trfjob ) { + KURL url( trfjob->url() ); + if ( error ) { + emit itemUploadError( url, err ); + } else { + // We don't know the local id here (and we don't want to extract it from + // the idMapper, that's the task of the receiver + emit itemUploaded( uidFromJob( job ), url ); + } + return true; + } else { + return false; + } +} + +bool GroupwareDataAdaptor::interpretUploadNewJob( KIO::Job *job, const QString &/*jobData*/ ) +{ +// TODO: How does the incidence mapper know the old/new ids??? + kdDebug(7000) << "GroupwareDataAdaptor::interpretUploadNewJob " << endl; + KIO::TransferJob *trfjob = dynamic_cast<KIO::TransferJob*>(job); + bool error = job->error(); + const QString err = job->errorString(); + + if ( trfjob ) { + KURL url( trfjob->url() ); + if ( error ) { + emit itemUploadNewError( idMapper()->localId( url.path() ), err ); + } else { + // We don't know the local id here (and we don't want to extract it from + // the idMapper, that's the task of the receiver + emit itemUploadedNew( uidFromJob( job ), url ); + } + return true; + } else { + return false; + } +} + +QString GroupwareDataAdaptor::uidFromJob( KIO::Job *job ) const +{ +kdDebug()<<"GroupwareDataAdaptor::uidFromJob( "<<job<<")"<<endl; + if ( mJobUIDMap.contains( job ) ) { + kdDebug()<<" Contained: "<< mJobUIDMap[job] << endl; + return mJobUIDMap[ job ]; + } else { + return QString::null; + } +} + +void GroupwareDataAdaptor::setUidForJob( KIO::Job *job, const QString &uid ) +{ + if ( uid.isEmpty() ) { + mJobUIDMap.remove( job ); + } else { + mJobUIDMap[ job ] = uid; + } +} + + +#include "groupwaredataadaptor.moc" diff --git a/kresources/lib/groupwaredataadaptor.h b/kresources/lib/groupwaredataadaptor.h new file mode 100644 index 000000000..5e7aec49e --- /dev/null +++ b/kresources/lib/groupwaredataadaptor.h @@ -0,0 +1,363 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KPIM_GROUPWAREDATAADAPTOR_H +#define KPIM_GROUPWAREDATAADAPTOR_H + +#include <groupwareresourcejob.h> +#include <folderlister.h> +#include <kurl.h> +#include <qstring.h> +#include <libkcal/listbase.h> +#include <qobject.h> +#include <kdepimmacros.h> + + +namespace KIO { +class TransferJob; +class Job; +} + +namespace KPIM { + +class FolderLister; +class IdMapper; +class GroupwareDataAdaptor; +//class GroupwareJob; + +class KDE_EXPORT GroupwareUploadItem +{ + public: + typedef KCal::ListBase<GroupwareUploadItem> List; + enum UploadType { + Added, + Changed, + Deleted + }; + + GroupwareUploadItem( UploadType type ); + virtual ~GroupwareUploadItem() {} + KURL url() const { return mUrl; } + void setUrl( const KURL &url ) { mUrl = url; } + + QString uid() const { return mUid; } + void setUid( const QString &uid ) { mUid = uid; } + + QString fingerprint() const { return mFingerprint; } + void setFingerprint( const QString &fpr ) { mFingerprint = fpr; } + + virtual QString data() const { return mData; } + virtual void setData( const QString &data ) { mData = data; } + virtual KURL adaptNewItemUrl( GroupwareDataAdaptor *adaptor, + const KURL &url ); + + virtual KIO::TransferJob *createRawUploadJob( + GroupwareDataAdaptor *adaptor, const KURL &url ); + virtual KIO::TransferJob *createUploadNewJob( + GroupwareDataAdaptor *adaptor, const KURL &url ); + virtual KIO::TransferJob *createUploadJob( GroupwareDataAdaptor *adaptor, + const KURL &url ); + virtual KPIM::FolderLister::ContentType itemType() { return mItemType; } + protected: + KPIM::FolderLister::ContentType mItemType; + private: + KURL mUrl; + QString mUid; + QString mData; + QString mFingerprint; + UploadType mType; +}; + + +class KDE_EXPORT GroupwareDataAdaptor : public QObject +{ +Q_OBJECT + public: + GroupwareDataAdaptor(); + virtual ~GroupwareDataAdaptor(); + + void setFolderLister( FolderLister *folderLister ) + { + mFolderLister = folderLister; + } + FolderLister *folderLister() + { + return mFolderLister; + } + + /** + Set progress message shown by progress manager during download. It will + be interpreted as rich text, so it might have to be escaped. + */ + void setDownloadProgressMessage( const QString &v ) + { + mDownloadProgressMessage = v; + } + /** + Get download progress message. See setDownloadProgressMessage(). + */ + QString downloadProgressMessage() const + { + return mDownloadProgressMessage; + } + + /** + Set progress message shown by progress manager during upload. It will + be interpreted as rich text, so it might have to be escaped. + */ + void setUploadProgressMessage( const QString &v ) + { + mUploadProgressMessage = v; + } + /** + Get upload progress message. See setUploadProgressMessage(). + */ + QString uploadProgressMessage() const + { + return mUploadProgressMessage; + } + + /** + Set base URL. + */ + void setBaseURL( const KURL &url ) + { + mBaseURL = url; + } + /** + Get base URL. See setBaseURL(). + */ + KURL baseURL() const + { + return mBaseURL; + } + + /** + Set user name. + */ + void setUser( const QString &v ) + { + mUser = v; + } + /** + Get user. See setUser(). + */ + QString user() const + { + return mUser; + } + + /** + Set password of user. + */ + void setPassword( const QString &v ) + { + mPassword = v; + } + /** + Get password. See setPassword(). + */ + QString password() const + { + return mPassword; + } + + /** + Set id mapper. + */ + void setIdMapper( KPIM::IdMapper *v ) + { + mIdMapper = v; + } + /** + Get idMapper. See setIdMapper(). + */ + KPIM::IdMapper *idMapper() const + { + return mIdMapper; + } + + void setUserPassword( KURL &url ); + + /** Adapt the url for downloading. Sets the username and password and calls + * customAdaptDownloadUrl, which you can reimplement for custom adaptions. + */ + virtual void adaptDownloadUrl( KURL &url ) + { + setUserPassword( url ); + customAdaptDownloadUrl( url ); + } + /** Adapt the url for uploading. Sets the username and password and calls + * customAdaptUploadUrl, which you can reimplement for custom adaptions. */ + virtual void adaptUploadUrl( KURL &url ) + { + setUserPassword( url ); + customAdaptUploadUrl( url ); + } + /** Apply custom adaptions to the url for downloading. Reimplement this + * method if you want to use webdav:// instead of http:// URLs. */ + virtual void customAdaptDownloadUrl( KURL &/*url*/ ) {} + /** Apply custom adaptions to the url for uploading. Reimplement this + * method if you want to use webdav:// instead of http:// URLs. */ + virtual void customAdaptUploadUrl( KURL &/*url*/ ) {} + + /** Return the mime-type expected by the resource. */ + virtual QString mimeType() const = 0; + /** Identifier of the Resource. Used for the custom fields where + resource-specific information is stored. */ + virtual QCString identifier() const = 0; + + /** Returns whether the item with the given localId exists locally. */ + virtual bool localItemExists( const QString &localId ) = 0; + /** Returns whether the item was changed locally since the last download + from the server. */ + virtual bool localItemHasChanged( const QString &localId ) = 0; + /** Remove the item from the local cache. */ + virtual void deleteItem( const QString &localId ) = 0; + + /** Removed the changed flag for the item with the given uid. */ + virtual void clearChange( const QString &uid ) = 0; + + virtual FolderLister::Entry::List defaultFolders(); + virtual QValueList<FolderLister::ContentType> supportedTypes() = 0; + virtual bool supports( FolderLister::ContentType type ) { + return supportedTypes().contains( type ); + } + + + // Creating jobs + /** Creates the KIO::Job for logging in to the server. This is only + * called if the GroupwareDataAdaptor::GWResNeedsLogin flag is set + * for the resource. */ + virtual KIO::Job *createLoginJob( const KURL &, const QString &/*user*/, + const QString &/*password*/ ) { return 0; } + /** Creates the KIO::Job for logging off the server. This is only + * called if the GroupwareDataAdaptor::GWResNeedsLogoff flag is set + * for the resource. */ + virtual KIO::Job *createLogoffJob( const KURL &, const QString &/*user*/, + const QString &/*password*/ ) { return 0; } + /** Creates the KIO::Job for listing all subfolders of the given url. */ + virtual KIO::Job *createListFoldersJob ( const KURL & ) = 0; + /** Creates the KIO::TransferJob for listing all items in the given url. */ + virtual KIO::TransferJob *createListItemsJob( const KURL & ) = 0; + /** Creates the KIO::TransferJob for downloading one given item. */ + virtual KIO::TransferJob *createDownloadJob( const KURL &, + FolderLister::ContentType ) = 0; + /** Creates the KIO::TransferJob for downloading a list of items items. */ + virtual KIO::TransferJob *createDownloadJob( const QMap<KURL,FolderLister::ContentType> & ) { return 0; } + /** Create the job to remove the deletedItems from the server. The base + URL of the server is passed as uploadurl. */ + virtual KIO::Job *createRemoveJob( const KURL &, + const KPIM::GroupwareUploadItem::List &/*deletedItems*/ ) { return 0; } + /** Create the job to remove the item from the server. The base + URL of the server is passed as uploadurl. */ + virtual KIO::Job *createRemoveJob( const KURL &, + KPIM::GroupwareUploadItem */*deletedItem*/ ) { return 0; } + /** Create the job to change the item on the server (at the given URL) */ + virtual KIO::TransferJob *createUploadJob( const KURL &, + GroupwareUploadItem *item ); + /** Create the job to change the items on the server (at the given URL) */ + virtual KIO::TransferJob *createUploadJob( const KURL &, const GroupwareUploadItem::List &/*items*/ ) { return 0; } + /** Create the job to add the item to the server (at the given baseURL) */ + virtual KIO::TransferJob *createUploadNewJob( const KURL &, + GroupwareUploadItem *item ); + /** Create the job to add the items to the server (at the given baseURL) */ + virtual KIO::TransferJob *createUploadNewJob( const KURL &, const GroupwareUploadItem::List &/*items*/ ) { return 0; } + + + // Interpreting the result of the jobs + /** Extract the success information from the login job, created by + * createLoginJob. Return true, if the login was successfull, or false + * if the user could not be authenticated or something else went wrong. + * In that case the resource will not be marked as open. */ + virtual bool interpretLoginJobResult( KIO::Job * ) { return true; } + /** Extract the success information from the logoff job, created by + * createLogoffJob. */ + virtual bool interpretLogoffJobResult( KIO::Job * ) { return true; } + + virtual void interpretListFoldersJob( KIO::Job *, FolderLister *) = 0; + /** Extract the list of items on the server and the list of items to be + downloaded from the results of the job (the job was created by + createListitemsJob). */ + virtual bool interpretListItemsJob( KIO::Job *, const QString &jobData ) = 0; + virtual bool interpretDownloadItemsJob( KIO::Job *job, const QString &jobData ) = 0; + virtual bool interpretRemoveJob( KIO::Job *job, const QString &jobData ); + virtual bool interpretUploadJob( KIO::Job *job, const QString &/*jobData*/ ); + virtual bool interpretUploadNewJob( KIO::Job *job, const QString &/*jobData*/ ); + + virtual void processDownloadListItem( const KURL &entry, + const QString &newFingerprint, KPIM::FolderLister::ContentType type ); + /** Return the default file name for a new item. */ + virtual QString defaultNewItemName( GroupwareUploadItem * ) + { + return QString::null; + } + virtual QString uidFromJob( KIO::Job *job ) const; + virtual void setUidForJob( KIO::Job *job, const QString &uid ); + + + enum { + GWResBatchCreate = 0x0001, + GWResBatchModify = 0x0002, + GWResBatchDelete = 0x0004, + GWResBatchRequest = 0x0008, + GWResHandleSingleIncidences = 0x0020, + GWResNeedsLogon = 0x0040, + GWResNeedsLogoff = 0x0080 + }; + virtual long flags() const = 0; + + + signals: + void folderInfoRetrieved( const KURL &href, const QString &name, + KPIM::FolderLister::ContentType ); + void folderSubitemRetrieved( const KURL &, bool isFolder ); + + void itemToDownload( const KURL &remoteURL, KPIM::FolderLister::ContentType type ); + /** passed the whole remote url (including hostname) to the receiver */ + void itemOnServer( const KURL &remoteURL ); + + void itemDownloaded( const QString &localID, const KURL &remoteURL, + const QString &fingerprint ); + void itemDeleted( const QString &localID, const KURL &remoteURL ); + void itemUploaded( const QString &localID, const KURL &remoteURL ); + void itemUploadedNew( const QString &localID, const KURL &remoteURL ); + + void itemDownloadError( const KURL &remoteURL, const QString &error ); + void itemDeletionError( const KURL &remoteURL, const QString &error ); + void itemUploadError( const KURL &remoteURL, const QString &error ); + void itemUploadNewError( const QString &localID, const QString &error ); + + private: + FolderLister *mFolderLister; + QString mDownloadProgressMessage; + QString mUploadProgressMessage; + KURL mBaseURL; + QString mUser; + QString mPassword; + KPIM::IdMapper *mIdMapper; + QMap<KIO::Job*,QString> mJobUIDMap; +}; + +} + +#endif diff --git a/kresources/lib/groupwaredownloadjob.cpp b/kresources/lib/groupwaredownloadjob.cpp new file mode 100644 index 000000000..7acc1cd03 --- /dev/null +++ b/kresources/lib/groupwaredownloadjob.cpp @@ -0,0 +1,300 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "groupwaredownloadjob.h" + +#include "folderlister.h" +#include "groupwaredataadaptor.h" + +#include <kdebug.h> +#include <klocale.h> +#include <kurl.h> +#include <kio/job.h> +#include <libemailfunctions/idmapper.h> +#include <libkdepim/progressmanager.h> + +using namespace KPIM; + +GroupwareDownloadJob::GroupwareDownloadJob( GroupwareDataAdaptor *adaptor ) + : GroupwareJob( adaptor ), mProgress(0), + mDownloadJob(0), mListEventsJob(0) +{ +} + +void GroupwareDownloadJob::run() +{ + kdDebug(5800) << "GroupwareDownloadJob::run()" << endl; + + if ( !adaptor() ) { + error( i18n("Unable to initialize the download job.") ); + return; + } + + if ( adaptor()->folderLister() ){ + mFoldersForDownload = adaptor()->folderLister()->activeFolderIds(); + } else { + // TODO: If we don't have a folder lister, use the base URL (e.g. if all + // communication goes through one script on the server + } + + mItemsForDownload.clear(); + mCurrentlyOnServer.clear(); + connect( adaptor(), SIGNAL( itemToDownload( const KURL &, KPIM::FolderLister::ContentType ) ), + SLOT( slotItemToDownload( const KURL &, KPIM::FolderLister::ContentType ) ) ); + connect( adaptor(), SIGNAL( itemOnServer( const KURL & ) ), + SLOT( slotItemOnServer( const KURL & ) ) ); + connect( adaptor(), SIGNAL( itemDownloaded( const QString &, const KURL &, const QString & ) ), + SLOT( slotItemDownloaded( const QString &, const KURL &, const QString & ) ) ); + connect( adaptor(), SIGNAL( itemDownloadError( const KURL &, const QString & ) ), + SLOT( slotItemDownloadError( const KURL &, const QString & ) ) ); + + mProgress = KPIM::ProgressManager::instance()->createProgressItem( + KPIM::ProgressManager::getUniqueID(), + adaptor()->downloadProgressMessage() ); + connect( mProgress, + SIGNAL( progressItemCanceled( KPIM::ProgressItem * ) ), + SLOT( cancelLoad() ) ); + + listItems(); +} + +void GroupwareDownloadJob::listItems() +{ + if ( mFoldersForDownload.isEmpty() ) { + if ( mProgress ) { + mProgress->setTotalItems( mItemsForDownload.count() + 1 ); + mProgress->setCompletedItems( 1 ); + mProgress->updateProgress(); + } + + /* Delete incidences no longer present on the server */ + deleteIncidencesGoneFromServer(); + downloadItem(); + } else { + + //kdDebug(7000) << "props: " << props.toString() << endl; + KURL url = mFoldersForDownload.front(); + mFoldersForDownload.pop_front(); + kdDebug(5800) << "listItems: " << url.url() << endl; + + adaptor()->adaptDownloadUrl( url ); + kdDebug(5800) << "listItems, after adaptDownloadUrl: " << url.url() << endl; + + kdDebug(5800) << "OpenGroupware::listIncidences(): " << url << endl; + + mListItemsData = QString::null; + mListEventsJob = adaptor()->createListItemsJob( url ); + + connect( mListEventsJob, SIGNAL( result( KIO::Job * ) ), + SLOT( slotListItemsResult( KIO::Job * ) ) ); + connect( mListEventsJob, SIGNAL( data( KIO::Job *, const QByteArray & ) ), + SLOT( slotListItemsData( KIO::Job *, const QByteArray & ) ) ); + } +} + + +void GroupwareDownloadJob::slotListItemsData( KIO::Job *, const QByteArray &data ) +{ + kdDebug(5800) << "OpenGroupware::slotListItemsData()" << endl; + + mListItemsData.append( data.data() ); +} + + +void GroupwareDownloadJob::slotListItemsResult( KIO::Job *job ) +{ + kdDebug(5800) << "GroupwareDownloadJob::slotListItemsResult(): " << endl; + + if ( job->error() ) { + if ( mProgress ) { + mProgress->setComplete(); + mProgress = 0; + } + error( job->errorString() ); + } else { + adaptor()->interpretListItemsJob( job, mListItemsData ); + } + + mListItemsData = QString::null; + mListEventsJob = 0; + + listItems(); +} + +void GroupwareDownloadJob::deleteIncidencesGoneFromServer() +{ + QMap<QString, QString> remoteIds( adaptor()->idMapper()->remoteIdMap() ); + KURL::List::ConstIterator it = mCurrentlyOnServer.begin(); + while ( it != mCurrentlyOnServer.end() ) { + remoteIds.remove( (*it).path() ); + ++it; + } + QMap<QString, QString>::ConstIterator it2; + for (it2 = remoteIds.begin(); it2 != remoteIds.end(); ++it2) { + adaptor()->deleteItem( remoteIds[ it2.key() ] ); + } +} + +void GroupwareDownloadJob::downloadItem() +{ + kdDebug(7000) << " downloadItem " << endl; + if ( mItemsForDownload.isEmpty() ) { + if ( mProgress ) mProgress->setComplete(); + + mItemsForDownload.clear(); + mItemsDownloading.clear(); + mItemsDownloaded.clear(); + mItemsDownloadError.clear(); + + mProgress = 0; + success(); + } else { + if ( adaptor()->flags() & KPIM::GroupwareDataAdaptor::GWResBatchRequest ) { + mDownloadItemsData = QString::null; + mDownloadJob = adaptor()->createDownloadJob( mItemsForDownload ); + mItemsDownloading = mItemsForDownload; + mItemsForDownload.clear(); + } else { + // Download the first item of the list + QMap<KURL,KPIM::FolderLister::ContentType>::Iterator it = mItemsForDownload.begin(); + KURL href( it.key() ); + KPIM::FolderLister::ContentType ctype = it.data(); + mItemsDownloading.insert( it.key(), it.data() ); + mItemsForDownload.remove( it.key() ); + + adaptor()->adaptDownloadUrl( href ); + mDownloadItemsData = QString::null; + + mDownloadJob = adaptor()->createDownloadJob( href, ctype ); + } + connect( mDownloadJob, SIGNAL( result( KIO::Job * ) ), + SLOT( slotDownloadItemResult( KIO::Job * ) ) ); + connect( mDownloadJob, SIGNAL( data( KIO::Job *, const QByteArray & ) ), + SLOT( slotDownloadItemData( KIO::Job *, const QByteArray & ) ) ); + } +} + +void GroupwareDownloadJob::slotDownloadItemResult( KIO::Job *job ) +{ + kdDebug(5800) << "GroupwareDownloadJob::slotDownloadItemResult(): " << endl; + + KIO::TransferJob *trfjob = dynamic_cast<KIO::TransferJob*>(job); + if ( !trfjob ) return; + + if ( job->error() ) { + error( job->errorString() ); + } else { + adaptor()->interpretDownloadItemsJob( job, mDownloadItemsData ); + } + + if ( mProgress ) { + mProgress->incCompletedItems(); + mProgress->updateProgress(); + } + mDownloadItemsData = QString::null; + mDownloadJob = 0; + + downloadItem(); +} + +void GroupwareDownloadJob::slotDownloadItemData( KIO::Job *, const QByteArray &data ) +{ + kdDebug(5800) << "OpenGroupware::slotDownloadItemData()" << endl; + + mDownloadItemsData.append( QString::fromUtf8( data.data(), data.size() ) ); +} + +void GroupwareDownloadJob::slotItemToDownload( const KURL &remoteURL, + KPIM::FolderLister::ContentType type ) +{ + KURL url( remoteURL ); + adaptor()->adaptDownloadUrl( url ); + if ( !mItemsForDownload.contains( url ) && + !mItemsDownloading.contains( url ) && + !mItemsDownloaded.contains( url ) ) { + mItemsForDownload.insert( url, type ); + } +} + + +void GroupwareDownloadJob::slotItemOnServer( const KURL &remoteURL ) +{ +kdDebug()<<"GroupwareDownloadJob::slotItemOnServer( " << remoteURL.url() << ")" << endl; + if ( !mCurrentlyOnServer.contains( remoteURL ) ) { + mCurrentlyOnServer.append( remoteURL ); + } +} + + +void GroupwareDownloadJob::slotItemDownloadError( const KURL &remoteURL, const QString &/*error*/ ) +{ + // TODO: Error handling! + if ( mItemsDownloading.contains( remoteURL ) ) { + mItemsDownloadError[ remoteURL ] = mItemsDownloading[ remoteURL ]; + } else if ( mItemsForDownload.contains( remoteURL ) ) { + mItemsDownloadError[ remoteURL ] = mItemsForDownload[ remoteURL ]; + } +} + + +void GroupwareDownloadJob::slotItemDownloaded( const QString &localID, + const KURL &remoteURL, const QString &fingerprint ) +{ +kdDebug()<<"GroupwareDownloadJob::slotItemDownloaded( " << localID << ", " << remoteURL.url() << ", " << fingerprint << ")" << endl; + if ( mItemsForDownload.contains( remoteURL ) ) { + mItemsDownloaded[ remoteURL ] = mItemsForDownload[ remoteURL ]; + mItemsForDownload.remove( remoteURL ); + } + if ( mItemsDownloading.contains( remoteURL ) ) { + mItemsDownloaded[ remoteURL ] = mItemsDownloading[ remoteURL ]; + mItemsDownloading.remove( remoteURL ); + } + if ( !mItemsDownloaded.contains( remoteURL ) ) { + mItemsDownloaded[ remoteURL ] = KPIM::FolderLister::Unknown; + } + adaptor()->idMapper()->setRemoteId( localID, remoteURL.path() ); + adaptor()->idMapper()->setFingerprint( localID, fingerprint ); +} + + + +void GroupwareDownloadJob::kill() +{ + cancelLoad(); +} + + + +void GroupwareDownloadJob::cancelLoad() +{ + if ( mDownloadJob ) mDownloadJob->kill(); + mDownloadJob = 0; + if ( mListEventsJob ) mListEventsJob->kill(); + mListEventsJob = 0; + if ( mProgress ) mProgress->setComplete(); + + + mProgress = 0; +} + +#include "groupwaredownloadjob.moc" diff --git a/kresources/lib/groupwaredownloadjob.h b/kresources/lib/groupwaredownloadjob.h new file mode 100644 index 000000000..236ed3d56 --- /dev/null +++ b/kresources/lib/groupwaredownloadjob.h @@ -0,0 +1,94 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KPIM_GROUPWAREDOWNLOADJOB_H +#define KPIM_GROUPWAREDOWNLOADJOB_H + +#include "groupwareresourcejob.h" +#include <qstringlist.h> + +namespace KIO { + class Job; + class TransferJob; +} + +namespace KPIM { + +class GroupwareDataAdaptor; +class ProgressItem; + +/** + This class provides a resource for accessing a Groupware calendar with local caching. +*/ +class GroupwareDownloadJob : public GroupwareJob +{ + Q_OBJECT + public: + GroupwareDownloadJob( GroupwareDataAdaptor *adaptor ); + + void kill(); + + protected: + void listItems(); + void deleteIncidencesGoneFromServer(); + void downloadItem(); + + protected slots: + void run(); + + void cancelLoad(); + + void slotListItemsResult( KIO::Job * ); + void slotListItemsData( KIO::Job *, const QByteArray & ); + void slotDownloadItemResult( KIO::Job * ); + void slotDownloadItemData( KIO::Job *, const QByteArray & ); + + void slotItemToDownload( const KURL &remoteURL, + KPIM::FolderLister::ContentType type ); + void slotItemOnServer( const KURL &remoteURL ); + void slotItemDownloaded( const QString &localID, const KURL &remoteURL, + const QString &fingerprint ); + void slotItemDownloadError( const KURL &remoteURL, const QString &error ); + + private: + KURL::List mFoldersForDownload; + /** mCurrentlyOnServer is the list of pathes of all items on the server. + These pathes don't contain the server name! */ + KURL::List mCurrentlyOnServer; + + QMap<KURL,KPIM::FolderLister::ContentType> mItemsForDownload; + QMap<KURL,KPIM::FolderLister::ContentType> mItemsDownloading; + QMap<KURL,KPIM::FolderLister::ContentType> mItemsDownloaded; + QMap<KURL,KPIM::FolderLister::ContentType> mItemsDownloadError; + + KPIM::ProgressItem *mProgress; + + KIO::TransferJob *mDownloadJob; + KIO::TransferJob *mListEventsJob; + + QString mListItemsData; + QString mDownloadItemsData; +}; + +} + +#endif diff --git a/kresources/lib/groupwareresourcejob.cpp b/kresources/lib/groupwareresourcejob.cpp new file mode 100644 index 000000000..73c102c88 --- /dev/null +++ b/kresources/lib/groupwareresourcejob.cpp @@ -0,0 +1,59 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "groupwareresourcejob.h" + +#include <qtimer.h> + +using namespace KPIM; + +GroupwareJob::GroupwareJob( GroupwareDataAdaptor *adaptor ) + : mAdaptor( adaptor ) +{ + QTimer::singleShot( 0, this, SLOT( run() ) ); +} + +bool GroupwareJob::error() const +{ + return !mErrorString.isNull(); +} + +QString GroupwareJob::errorString() const +{ + return mErrorString; +} + +void GroupwareJob::success() +{ + mErrorString = QString::null; + emit( result( this ) ); +} + +void GroupwareJob::error( const QString &errorString ) +{ + mErrorString = errorString; + emit( result( this ) ); +} + + +#include "groupwareresourcejob.moc" diff --git a/kresources/lib/groupwareresourcejob.h b/kresources/lib/groupwareresourcejob.h new file mode 100644 index 000000000..2520466ea --- /dev/null +++ b/kresources/lib/groupwareresourcejob.h @@ -0,0 +1,68 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KPIM_GROUPWAREJOB_H +#define KPIM_GROUPWAREJOB_H + +#include <qobject.h> +#include <qstring.h> +#include "folderlister.h" + +namespace KPIM { + +class GroupwareDataAdaptor; + +/** + This class provides a resource for accessing a Groupware kioslave-based + calendar. +*/ +class GroupwareJob : public QObject +{ + Q_OBJECT + public: + GroupwareJob( GroupwareDataAdaptor *adaptor ); + + bool error() const; + QString errorString() const; + + virtual void kill() = 0; + + signals: + void result( KPIM::GroupwareJob * ); + + protected: + void success(); + void error( const QString & ); + GroupwareDataAdaptor *adaptor() { return mAdaptor; } + const GroupwareDataAdaptor *adaptor() const { return mAdaptor; } + + protected slots: + virtual void run() = 0; + + private: + QString mErrorString; + GroupwareDataAdaptor *mAdaptor; +}; + +} + +#endif diff --git a/kresources/lib/groupwareuploadjob.cpp b/kresources/lib/groupwareuploadjob.cpp new file mode 100644 index 000000000..bb3098fc2 --- /dev/null +++ b/kresources/lib/groupwareuploadjob.cpp @@ -0,0 +1,485 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "groupwareuploadjob.h" + +#include "folderlister.h" +#include "groupwaredataadaptor.h" + +#include <libemailfunctions/idmapper.h> +#include <libkdepim/progressmanager.h> + +#include <kdebug.h> +#include <kurl.h> +#include <kio/job.h> + +#include <qstringlist.h> +#include <qtimer.h> +#include <klocale.h> + +using namespace KPIM; + +GroupwareUploadJob::GroupwareUploadJob( GroupwareDataAdaptor *adaptor ) + : GroupwareJob( adaptor ), mUploadJob(0), + mDeletionJob(0), mUploadProgress(0) +{ +} + +void GroupwareUploadJob::run() +{ + deleteItem(); + mUploadProgress = KPIM::ProgressManager::instance()->createProgressItem( + KPIM::ProgressManager::getUniqueID(), + adaptor()->uploadProgressMessage() ); + connect( mUploadProgress, + SIGNAL( progressItemCanceled( KPIM::ProgressItem * ) ), + SLOT( cancelSave() ) ); + + connect( adaptor(), SIGNAL( itemDeletionError( const KURL &, const QString & ) ), + SLOT( slotItemDeleteError( const KURL &, const QString & ) ) ); + connect( adaptor(), SIGNAL( itemUploadError( const KURL &, const QString & ) ), + SLOT( slotItemUploadError( const KURL &, const QString & ) ) ); + connect( adaptor(), SIGNAL( itemUploadNewError( const QString &, const QString & ) ), + SLOT( slotItemUploadNewError( const QString &, const QString & ) ) ); + + connect( adaptor(), SIGNAL( itemDeleted( const QString &, const KURL & ) ), + SLOT( slotItemDeleted( const QString &, const KURL & ) ) ); + connect( adaptor(), SIGNAL( itemUploaded( const QString &, const KURL & ) ), + SLOT( slotItemUploaded( const QString &, const KURL & ) ) ); + connect( adaptor(), SIGNAL( itemUploadedNew( const QString &, const KURL& ) ), + SLOT( slotItemUploadedNew( const QString &, const KURL & ) ) ); + + + mUploadProgress->setTotalItems( mAddedItems.size() + mChangedItems.size() + + ((mChangedItems.isEmpty())?0:1) ); + mUploadProgress->updateProgress(); +} + + + +void GroupwareUploadJob::deleteItem() +{ + kdDebug(5800)<<"GroupwareUploadJob::deleteItem()"<<endl; + if ( mDeletedItems.isEmpty() ) { + QTimer::singleShot( 0, this, SLOT( uploadItem() ) ); + } else { + kdDebug(7000) << " Deleting " << mDeletedItems.size() << " items from the server " << endl; + + KURL url( adaptor()->baseURL() ); + adaptor()->adaptUploadUrl( url ); + if ( adaptor()->flags() & KPIM::GroupwareDataAdaptor::GWResBatchDelete ) { +kdDebug() << "Using batch delete " << endl; + mDeletionJob = adaptor()->createRemoveJob( url, mDeletedItems ); + mItemsUploading += mDeletedItems; + mDeletedItems.clear(); + } else { +kdDebug() << "Not using batch delete " << endl; + KPIM::GroupwareUploadItem *item = mDeletedItems.front(); + mDeletionJob = adaptor()->createRemoveJob( url, item ); + mItemsUploading.append( mDeletedItems.front() ); + mDeletedItems.pop_front(); + } + + if ( mDeletionJob ) { + mDeletionJobData = QString::null; + connect( mDeletionJob, SIGNAL( result( KIO::Job* ) ), + SLOT( slotDeletionJobResult( KIO::Job* ) ) ); +// connect( mDeletionJob, SIGNAL( data( KIO::Job *, const QByteArray & ) ), +// SLOT( slotDeletionJobData( KIO::Job *, const QByteArray & ) ) ); + } else { + deleteItem(); + } + } +} + + + +void GroupwareUploadJob::slotDeletionJobData( KIO::Job *, const QByteArray &data ) +{ + kdDebug(5800) << "OpenGroupware::slotDeletionData()" << endl; + + mDeletionJobData.append( data.data() ); +} + + + +void GroupwareUploadJob::slotDeletionJobResult( KIO::Job *job ) +{ + if ( job && adaptor() ) { + adaptor()->interpretRemoveJob( job, mDeletionJobData ); + } + mDeletionJob = 0; + QTimer::singleShot( 0, this, SLOT( deleteItem() ) ); +} + + + +void GroupwareUploadJob::uploadItem() +{ + kdDebug(5800)<<"GroupwareUploadJob::uploadItem()"<<endl; + if ( mChangedItems.isEmpty() ) { + QTimer::singleShot( 0, this, SLOT( uploadNewItem() ) ); + } else { + kdDebug(5800)<<"We still have "<<mChangedItems.count()<<" changed items to upload"<<endl; + + KURL url( adaptor()->baseURL() ); + adaptor()->adaptUploadUrl( url ); + if ( adaptor()->flags() & KPIM::GroupwareDataAdaptor::GWResBatchModify ) { +kdDebug() << "Using batch upload " << endl; + mUploadJob = adaptor()->createUploadJob( url, mChangedItems ); + mItemsUploading += mChangedItems; + mChangedItems.clear(); + } else { +kdDebug() << "Not using batch upload " << endl; + KPIM::GroupwareUploadItem *item = mChangedItems.front(); + mUploadJob = adaptor()->createUploadJob( url, item ); + mItemsUploading.append( mChangedItems.front() ); + mChangedItems.pop_front(); + } + + if ( mUploadJob ) { + mUploadJobData = QString::null; + connect( mUploadJob, SIGNAL( result( KIO::Job* ) ), + SLOT( slotUploadJobResult( KIO::Job* ) ) ); + connect( mUploadJob, SIGNAL( data( KIO::Job *, const QByteArray & ) ), + SLOT( slotUploadJobData( KIO::Job *, const QByteArray & ) ) ); + } else { + uploadItem(); + } + } +} + + +void GroupwareUploadJob::slotUploadJobData( KIO::Job *, const QByteArray &data ) +{ + kdDebug(5800) << "OpenGroupware::slotUploadData()" << endl; + + mUploadJobData.append( data.data() ); +} + + + +void GroupwareUploadJob::slotUploadJobResult( KIO::Job *job ) +{ + if ( job && adaptor() ) { + adaptor()->interpretUploadJob( job, mUploadJobData ); + } + mUploadJob = 0; + QTimer::singleShot( 0, this, SLOT( uploadItem() ) ); +} + + + + +void GroupwareUploadJob::uploadNewItem() +{ + kdDebug(5800)<<"GroupwareUploadJob::uploadNewItem()"<<endl; + if ( !mAddedItems.isEmpty() ) { + + if ( adaptor()->flags() & KPIM::GroupwareDataAdaptor::GWResBatchCreate ) { + KURL url( adaptor()->folderLister()->writeDestinationId( FolderLister::All ) ); + adaptor()->adaptUploadUrl( url ); +kdDebug() << "Using batch create to " << url.url() << endl; + mUploadJob = adaptor()->createUploadNewJob( url, mAddedItems ); + mItemsUploading += mAddedItems; + mAddedItems.clear(); + } else { + KPIM::GroupwareUploadItem *item = mAddedItems.front(); + KURL url( adaptor()->folderLister()->writeDestinationId( item->itemType() ) ); + adaptor()->adaptUploadUrl( url ); +kdDebug() << "Not using batch create to " << url.url() << " for item of type " << item->itemType() << endl; + if ( !url.isEmpty() ) { + mUploadJob = adaptor()->createUploadNewJob( url, item ); + mItemsUploading.append( mAddedItems.front() ); + } + mAddedItems.pop_front(); + } + + if ( mUploadJob ) { + mUploadNewJobData = QString::null; + connect( mUploadJob, SIGNAL( result( KIO::Job* ) ), + SLOT( slotUploadNewJobResult( KIO::Job* ) ) ); + connect( mUploadJob, SIGNAL( data( KIO::Job *, const QByteArray & ) ), + SLOT( slotUploadNewJobData( KIO::Job *, const QByteArray & ) ) ); + } else { + uploadNewItem(); + } + + } else { + kdDebug(5800)<<"We are finished uploading all items. Setting progress to completed."<<endl; + uploadCompleted(); + } +} + +void GroupwareUploadJob::slotUploadNewJobData( KIO::Job *, const QByteArray &data ) +{ + kdDebug(5800) << "OpenGroupware::slotUploadNewJobData()" << endl; + + mUploadNewJobData.append( data.data() ); +} + + + +void GroupwareUploadJob::slotUploadNewJobResult( KIO::Job *job ) +{ + if ( job && adaptor() ) { + adaptor()->interpretUploadNewJob( job, mUploadNewJobData ); + } + mUploadJob = 0; + QTimer::singleShot( 0, this, SLOT( uploadNewItem() ) ); +} + + +void GroupwareUploadJob::kill() +{ + cancelSave(); +} + +void GroupwareUploadJob::slotItemDeleted( const QString &/*localId*/, const KURL &remoteURL ) +{ + kdDebug() << "GroupwareUploadJob::slotItemDeleted, removal successful: "<< remoteURL.url() << endl; + + const QString &remote = remoteURL.path(); + const QString &local = adaptor()->idMapper()->localId( remote ); + if ( !local.isEmpty() ) { + // TODO: Is the deleted status reset in the resource? + adaptor()->deleteItem( local ); + } + + KPIM::GroupwareUploadItem::List allit( mDeletedItems ); + allit += mItemsUploading; + allit += mItemsUploadError; + + KPIM::GroupwareUploadItem::List::Iterator it = allit.begin(); + for ( ; it != allit.end(); ++it ) { + if ( (*it)->url().path() == remoteURL.path() ) { +kdDebug()<<"Found it in the list!"<<endl; + KPIM::GroupwareUploadItem *item = (*it); + mDeletedItems.remove( item ); + mItemsUploading.remove( item ); + mItemsUploadError.remove( item ); + mItemsUploaded.append( item ); + } + } + + if ( mUploadProgress ) { + mUploadProgress->incCompletedItems(); + mUploadProgress->updateProgress(); + } +} + + + +void GroupwareUploadJob::slotItemUploaded( const QString &/*localId*/, const KURL &remoteURL ) +{ + kdDebug() << "GroupwareUploadJob::slotItemUploaded, upload successful: "<< remoteURL.url() << endl; + + const QString &remote = remoteURL.path(); + const QString &local = adaptor()->idMapper()->localId( remote ); + if ( !local.isEmpty() ) { + // TODO: Is the deleted status reset in the resource? +// adaptor()->itemUploaded( local, remoteURL ); + } + + KPIM::GroupwareUploadItem::List allit( mChangedItems ); + allit += mAddedItems; + allit += mItemsUploading; + allit += mItemsUploadError; + + + KPIM::GroupwareUploadItem::List::Iterator it = allit.begin(); + for ( ; it != allit.end(); ++it ) { + if ( (*it)->url().path() == remoteURL.path() ) { +kdDebug()<<"Found it in the list!"<<endl; + KPIM::GroupwareUploadItem *item = (*it); + mChangedItems.remove( item ); + mAddedItems.remove( item ); + mItemsUploading.remove( item ); + mItemsUploadError.remove( item ); + mItemsUploaded.append( item ); + } + } + + if ( mUploadProgress ) { + mUploadProgress->incCompletedItems(); + mUploadProgress->updateProgress(); + } +} + + +void GroupwareUploadJob::slotItemUploadedNew( const QString &localId, const KURL &remoteURL ) +{ + kdDebug() << "GroupwareUploadJob::slotItemUploadedNew, upload successful: "<< remoteURL.url() << endl; + + const QString &remote = remoteURL.path(); + // TODO: For a new item this won't return anything, so we need to insert the + // local<=>remote id map when creating the upload job... And maybe + const QString &local = adaptor()->idMapper()->localId( remote ); + if ( !localId.isEmpty() ) { + adaptor()->deleteItem( localId ); + } + if ( !local.isEmpty() ) { +// adaptor()->itemUploadedNew( local, remoteURL ); + } + + KPIM::GroupwareUploadItem::List allit( mChangedItems ); + allit += mAddedItems; + allit += mItemsUploading; + allit += mItemsUploadError; + + + KPIM::GroupwareUploadItem::List::Iterator it = allit.begin(); + for ( ; it != allit.end(); ++it ) { + if ( (*it)->url().path() == remoteURL.path() ) { +kdDebug()<<"Found it in the list!"<<endl; + KPIM::GroupwareUploadItem *item = (*it); + mChangedItems.remove( item ); + mAddedItems.remove( item ); + mItemsUploading.remove( item ); + mItemsUploadError.remove( item ); + mItemsUploaded.append( item ); + } + } + + if ( mUploadProgress ) { + mUploadProgress->incCompletedItems(); + mUploadProgress->updateProgress(); + } +} + +void GroupwareUploadJob::slotItemDeleteError( const KURL &remoteURL, const QString &/*error*/ ) +{ + // TODO: Add to error list, remove from uploading and toUpload list + kdDebug() << "GroupwareUploadJob::slotItemDeleteError, removal not successful: "<< remoteURL.url() << endl; + KPIM::GroupwareUploadItem::List allit( mDeletedItems ); + allit += mItemsUploading; + allit += mItemsUploaded; + + KPIM::GroupwareUploadItem::List::Iterator it = allit.begin(); + for ( ; it != allit.end(); ++it ) { + if ( (*it)->url().path() == remoteURL.path() ) { +kdDebug()<<"Found it in the list!"<<endl; + KPIM::GroupwareUploadItem *item = (*it); + mDeletedItems.remove( item ); + mItemsUploaded.remove( item ); + mItemsUploading.remove( item ); + mItemsUploadError.append( item ); + } + } + + if ( mUploadProgress ) { + mUploadProgress->incCompletedItems(); + mUploadProgress->updateProgress(); + } +} + +void GroupwareUploadJob::slotItemUploadError( const KURL &remoteURL, const QString &/*error*/ ) +{ + // TODO: Add to error list, remove from uploading and toUpload list + kdDebug() << "GroupwareUploadJob::slotItemUploadError, removal not successful: "<< remoteURL.url() << endl; + KPIM::GroupwareUploadItem::List allit( mChangedItems ); + allit += mItemsUploading; + allit += mItemsUploaded; + + KPIM::GroupwareUploadItem::List::Iterator it = allit.begin(); + for ( ; it != allit.end(); ++it ) { + if ( (*it)->url().path() == remoteURL.path() ) { +kdDebug()<<"Found it in the list!"<<endl; + KPIM::GroupwareUploadItem *item = (*it); + mChangedItems.remove( item ); + mItemsUploaded.remove( item ); + mItemsUploading.remove( item ); + mItemsUploadError.append( item ); + } + } + + if ( mUploadProgress ) { + mUploadProgress->incCompletedItems(); + mUploadProgress->updateProgress(); + } +} + +void GroupwareUploadJob::slotItemUploadNewError( const QString &/*localID*/, const QString &remoteURL ) +{ + kdDebug(5006) << "GroupwareUploadJob::slotItemUploadNewError, removal not successful: "<< remoteURL << endl; + KPIM::GroupwareUploadItem::List allit( mAddedItems ); + allit += mItemsUploading; + allit += mItemsUploaded; + const KURL &url( remoteURL ); + + KPIM::GroupwareUploadItem::List::Iterator it = allit.begin(); + for ( ; it != allit.end(); ++it ) { + if ( (*it)->url().path() == url.path() ) { +kdDebug()<<"Found it in the list!"<<endl; + KPIM::GroupwareUploadItem *item = (*it); + mAddedItems.remove( item ); + mItemsUploaded.remove( item ); + mItemsUploading.remove( item ); + mItemsUploadError.append( item ); + } + } + + if ( mUploadProgress ) { + mUploadProgress->incCompletedItems(); + mUploadProgress->updateProgress(); + } +} + + +void GroupwareUploadJob::cancelSave() +{ + if ( mUploadJob ) mUploadJob->kill(); + mUploadJob = 0; + if ( mUploadProgress ) mUploadProgress->setComplete(); + mUploadProgress = 0; +} + +void GroupwareUploadJob::uploadCompleted() +{ + if ( !mItemsUploadError.isEmpty() ) { + error( i18n("1 item could not be uploaded.", "%n items could not be uploaded.", mItemsUploadError.count() ) ); + } + KPIM::GroupwareUploadItem::List items( mAddedItems ); + items += mChangedItems; + items += mDeletedItems; + items += mItemsUploading; + items += mItemsUploaded; + items += mItemsUploadError; + + mAddedItems.clear(); + mChangedItems.clear(); + mDeletedItems.clear(); + mItemsUploading.clear(); + mItemsUploaded.clear(); + mItemsUploadError.clear(); + items.setAutoDelete( true ); + items.clear(); + + if ( mUploadProgress ) { + mUploadProgress->setComplete(); + mUploadProgress = 0; + } + success(); + +} +#include "groupwareuploadjob.moc" diff --git a/kresources/lib/groupwareuploadjob.h b/kresources/lib/groupwareuploadjob.h new file mode 100644 index 000000000..de87680f4 --- /dev/null +++ b/kresources/lib/groupwareuploadjob.h @@ -0,0 +1,130 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KPIM_GROUPWAREUPLOADJOB_H +#define KPIM_GROUPWAREUPLOADJOB_H + +#include "groupwareresourcejob.h" + +#include <kurl.h> +#include <qstringlist.h> +#include <groupwaredataadaptor.h> + +namespace KIO { + class Job; + class TransferJob; + class DeleteJob; +} + +namespace KPIM { + +class GroupwareDataAdaptor; +class ProgressItem; + +/** + This class provides a resource for accessing a Groupware kioslave-based + calendar. +*/ +class GroupwareUploadJob : public GroupwareJob +{ + Q_OBJECT + public: + GroupwareUploadJob( GroupwareDataAdaptor *adaptor ); + + KPIM::GroupwareUploadItem::List addedItems() const + { + return mAddedItems; + } + void setAddedItems( const KPIM::GroupwareUploadItem::List &items ) + { + mAddedItems = items; + } + KPIM::GroupwareUploadItem::List changedItems() const + { + return mChangedItems; + } + void setChangedItems( const KPIM::GroupwareUploadItem::List &items ) + { + mChangedItems = items; + } + KPIM::GroupwareUploadItem::List deletedItems() const + { + return mDeletedItems; + } + void setDeletedItems( const KPIM::GroupwareUploadItem::List &items ) + { + mDeletedItems = items; + } + + void kill(); + + protected slots: + void deleteItem(); + void uploadItem(); + void uploadNewItem(); + + protected slots: + void run(); + + void cancelSave(); + + void slotDeletionJobResult( KIO::Job *job ); + void slotDeletionJobData( KIO::Job *, const QByteArray & ); + void slotUploadJobResult( KIO::Job *job ); + void slotUploadJobData( KIO::Job *, const QByteArray & ); + void slotUploadNewJobResult( KIO::Job *job ); + void slotUploadNewJobData( KIO::Job *, const QByteArray & ); + + void slotItemDeleted( const QString &localID, const KURL &remoteURL ); + void slotItemUploaded( const QString &localID, const KURL &remoteURL ); + void slotItemUploadedNew( const QString &localID, const KURL &remoteURL ); + + void slotItemDeleteError( const KURL &remoteURL, const QString &error ); + void slotItemUploadError( const KURL &remoteURL, const QString &error ); + void slotItemUploadNewError( const QString &localID, const QString &error ); + + void uploadCompleted(); + + private: + KPIM::GroupwareUploadItem::List mAddedItems; + KPIM::GroupwareUploadItem::List mChangedItems; + KPIM::GroupwareUploadItem::List mDeletedItems; + + KPIM::GroupwareUploadItem::List mItemsUploading; + KPIM::GroupwareUploadItem::List mItemsUploaded; + KPIM::GroupwareUploadItem::List mItemsUploadError; + + QString mDeletionJobData; + QString mUploadJobData; + QString mUploadNewJobData; + + KIO::TransferJob *mUploadJob; + KIO::Job *mDeletionJob; + KPIM::ProgressItem *mUploadProgress; + +}; + +} + +#endif + + diff --git a/kresources/lib/kabc_resourcegroupwarebase.cpp b/kresources/lib/kabc_resourcegroupwarebase.cpp new file mode 100644 index 000000000..f087f4849 --- /dev/null +++ b/kresources/lib/kabc_resourcegroupwarebase.cpp @@ -0,0 +1,262 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (C) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + +#include "kabc_resourcegroupwarebase.h" +#include "kresources_groupwareprefs.h" + +#include "folderlister.h" +#include "addressbookadaptor.h" +#include "groupwaredownloadjob.h" +#include "groupwareuploadjob.h" + +#include <kabc/addressee.h> +#include <kabc/vcardconverter.h> +#include <klocale.h> + +using namespace KABC; + +ResourceGroupwareBase::ResourceGroupwareBase( const KConfig *config ) + : ResourceCached( config ), + mPrefs(0), mFolderLister(0), mAdaptor(0), mDownloadJob(0), mUploadJob(0) +{ + if ( config ) readConfig( config ); +} + +ResourceGroupwareBase::~ResourceGroupwareBase() +{ + delete mPrefs; + mPrefs = 0; +} + +KPIM::GroupwareDownloadJob *ResourceGroupwareBase::createDownloadJob( + AddressBookAdaptor *adaptor ) +{ + return new KPIM::GroupwareDownloadJob( adaptor ); +} + +KPIM::GroupwareUploadJob *ResourceGroupwareBase::createUploadJob( + AddressBookAdaptor *adaptor ) +{ + return new KPIM::GroupwareUploadJob( adaptor ); +} + +void ResourceGroupwareBase::setPrefs( KPIM::GroupwarePrefsBase *newprefs ) +{ + if ( !newprefs ) return; + if ( mPrefs ) delete mPrefs; + mPrefs = newprefs; + mPrefs->addGroupPrefix( identifier() ); + + mPrefs->readConfig(); + if ( mFolderLister ) mFolderLister->readConfig( mPrefs ); +} + +void ResourceGroupwareBase::setFolderLister( KPIM::FolderLister *folderLister ) +{ + if ( !folderLister ) return; + if ( mFolderLister ) delete mFolderLister; + mFolderLister = folderLister; + if ( mPrefs ) mFolderLister->readConfig( mPrefs ); + if ( mAdaptor ) { + mAdaptor->setFolderLister( mFolderLister ); + mFolderLister->setAdaptor( mAdaptor ); + } +} + +void ResourceGroupwareBase::setAdaptor( AddressBookAdaptor *adaptor ) +{ + if ( !adaptor ) return; + if ( mAdaptor ) delete mAdaptor; + mAdaptor = adaptor; + mAdaptor->setFolderLister( mFolderLister ); + if ( mFolderLister ) mFolderLister->setAdaptor( mAdaptor ); + mAdaptor->setDownloadProgressMessage( i18n("Downloading addressbook") ); + mAdaptor->setUploadProgressMessage( i18n("Uploading addressbook") ); + if ( prefs() ) { + mAdaptor->setBaseURL( prefs()->url() ); + mAdaptor->setUser( prefs()->user() ); + mAdaptor->setPassword( prefs()->password() ); + } + mAdaptor->setIdMapper( &idMapper() ); + mAdaptor->setResource( this ); +} + +void ResourceGroupwareBase::init() +{ + mDownloadJob = 0; +} + +KPIM::GroupwarePrefsBase *ResourceGroupwareBase::createPrefs() +{ + return new KPIM::GroupwarePrefsBase(); +} + + + +void ResourceGroupwareBase::readConfig( const KConfig */*config*/ ) +{ + kdDebug(5700) << "KABC::ResourceGroupwareBase::readConfig()" << endl; +// ResourceCached::readConfig( config ); + if ( mPrefs ) { + mPrefs->readConfig(); + if ( mFolderLister ) + mFolderLister->readConfig( mPrefs ); + } +} + +void ResourceGroupwareBase::writeConfig( KConfig *config ) +{ + Resource::writeConfig( config ); + + if ( mPrefs ) { + if ( mFolderLister ) + mFolderLister->writeConfig( mPrefs ); + mPrefs->writeConfig(); + } +} + +Ticket *ResourceGroupwareBase::requestSaveTicket() +{ + if ( !addressBook() ) { + kdDebug(5700) << "no addressbook" << endl; + return 0; + } + + return createTicket( this ); +} + +void ResourceGroupwareBase::releaseSaveTicket( Ticket *ticket ) +{ + delete ticket; +} + +bool ResourceGroupwareBase::doOpen() +{ + return true; +} + +void ResourceGroupwareBase::doClose() +{ + kdDebug(5800) << "ResourceGroupwareBase::doClose()" << endl; + + if ( mDownloadJob ) mDownloadJob->kill(); +} + +bool ResourceGroupwareBase::load() +{ + return asyncLoad(); +} + +bool ResourceGroupwareBase::asyncLoad() +{ + if ( mDownloadJob ) { + kdWarning() << "Download still in progress" << endl; + return false; + } + + mAddrMap.clear(); + loadCache(); + + mDownloadJob = createDownloadJob( mAdaptor ); + connect( mDownloadJob, SIGNAL( result( KPIM::GroupwareJob * ) ), + SLOT( slotDownloadJobResult( KPIM::GroupwareJob * ) ) ); + + return true; +} + +void ResourceGroupwareBase::slotDownloadJobResult( KPIM::GroupwareJob *job ) +{ + kdDebug(5800) << "ResourceGroupwareBase::slotJobResult(): " << endl; + + if ( job->error() ) { + kdError() << "job failed: " << job->errorString() << endl; + } else { + emit loadingFinished( this ); + if ( addressBook() ) + addressBook()->emitAddressBookChanged(); + } + + mDownloadJob = 0; +} + +bool ResourceGroupwareBase::save( Ticket *ticket ) +{ + return asyncSave( ticket ); +} + +bool ResourceGroupwareBase::asyncSave( Ticket* ) +{ + if ( mUploadJob ) { + // FIXME: If the user cancels, need to reset the mUploadJob variable to 0. + kdWarning() << "Upload still in progress." << endl; + return false; + } + + mUploadJob = createUploadJob( mAdaptor ); + connect( mUploadJob, SIGNAL( result( KPIM::GroupwareJob * ) ), + SLOT( slotUploadJobResult( KPIM::GroupwareJob * ) ) ); + + KABC::Addressee::List addr; + KABC::Addressee::List::Iterator it; + KPIM::GroupwareUploadItem::List addedItems, changedItems, deletedItems; + + addr = addedAddressees(); + for( it = addr.begin(); it != addr.end(); ++it ) { + addedItems.append( adaptor()->newUploadItem( *it, + KPIM::GroupwareUploadItem::Added ) ); + } + // TODO: Check if the item has changed on the server... + // In particular, check if the version we based our change on is still current + // on the server + addr = changedAddressees(); + for( it = addr.begin(); it != addr.end(); ++it ) { + changedItems.append( adaptor()->newUploadItem( *it, + KPIM::GroupwareUploadItem::Changed ) ); + } + addr = deletedAddressees(); + for( it = addr.begin(); it != addr.end(); ++it ) { + deletedItems.append( adaptor()->newUploadItem( *it, + KPIM::GroupwareUploadItem::Deleted ) ); + } + + mUploadJob->setAddedItems( addedItems ); + mUploadJob->setChangedItems( changedItems ); + mUploadJob->setDeletedItems( deletedItems ); + + return true; +} + +void ResourceGroupwareBase::slotUploadJobResult( KPIM::GroupwareJob *job ) +{ + kdDebug(5800) << "ResourceGroupwareBase::slotJobResult(): " << endl; + + if ( job->error() ) { + kdError() << "job failed: " << job->errorString() << endl; + } else { + // FIXME + } + + mUploadJob = 0; +} + + +#include "kabc_resourcegroupwarebase.moc" diff --git a/kresources/lib/kabc_resourcegroupwarebase.h b/kresources/lib/kabc_resourcegroupwarebase.h new file mode 100644 index 000000000..d7381a92f --- /dev/null +++ b/kresources/lib/kabc_resourcegroupwarebase.h @@ -0,0 +1,98 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (C) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ +#ifndef KABC_RESOURCEGROUPWARE_H +#define KABC_RESOURCEGROUPWARE_H + +#include <kurl.h> +#include <kabcresourcecached.h> +#include <kdepimmacros.h> + +class KConfig; + +namespace KPIM { +class GroupwareJob; +class GroupwareDownloadJob; +class GroupwareUploadJob; +class FolderLister; +class GroupwarePrefsBase; +} + +namespace KABC { + +class AddressBookAdaptor; + +class KDE_EXPORT ResourceGroupwareBase : public ResourceCached +{ + Q_OBJECT + + public: + ResourceGroupwareBase( const KConfig * ); + ~ResourceGroupwareBase(); + + void readConfig( const KConfig * ); + void writeConfig( KConfig * ); + + KPIM::GroupwarePrefsBase *prefs() const { return mPrefs; } + void setPrefs( KPIM::GroupwarePrefsBase *prefs ); + + KPIM::FolderLister *folderLister() const { return mFolderLister; } + void setFolderLister( KPIM::FolderLister *folderLister ); + + AddressBookAdaptor *adaptor() const { return mAdaptor; } + void setAdaptor( AddressBookAdaptor *adaptor ); + + bool doOpen(); + void doClose(); + + Ticket *requestSaveTicket(); + void releaseSaveTicket( Ticket* ); + + bool load(); + bool asyncLoad(); + bool save( Ticket * ); + bool asyncSave( Ticket * ); + + protected: + void init(); + + KPIM::GroupwarePrefsBase *createPrefs(); + virtual KPIM::GroupwareDownloadJob *createDownloadJob( + AddressBookAdaptor *adaptor ); + virtual KPIM::GroupwareUploadJob *createUploadJob( + AddressBookAdaptor *adaptor ); + + private slots: + void slotDownloadJobResult( KPIM::GroupwareJob * ); + void slotUploadJobResult( KPIM::GroupwareJob * ); + + private: + KPIM::GroupwarePrefsBase *mPrefs; + KPIM::FolderLister *mFolderLister; + AddressBookAdaptor *mAdaptor; + + KPIM::GroupwareDownloadJob *mDownloadJob; + KPIM::GroupwareUploadJob *mUploadJob; +}; + +} + +#endif diff --git a/kresources/lib/kabc_resourcegroupwarebaseconfig.cpp b/kresources/lib/kabc_resourcegroupwarebaseconfig.cpp new file mode 100644 index 000000000..47b17ced5 --- /dev/null +++ b/kresources/lib/kabc_resourcegroupwarebaseconfig.cpp @@ -0,0 +1,117 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + +#include "kabc_resourcegroupwarebaseconfig.h" + +#include "kabc_resourcegroupwarebase.h" +#include "kresources_groupwareprefs.h" +#include "folderconfig.h" + +#include <kdebug.h> +#include <kdialog.h> +#include <klocale.h> +#include <klineedit.h> +#include <kurlrequester.h> + +#include <qlabel.h> +#include <qlayout.h> + +using namespace KABC; + +ResourceGroupwareBaseConfig::ResourceGroupwareBaseConfig( QWidget* parent, const char* name ) + : KRES::ConfigWidget( parent, name ) +{ + QGridLayout *mainLayout = new QGridLayout( this, 7, 2, 0, KDialog::spacingHint() ); + + QLabel *label = new QLabel( i18n( "URL:" ), this ); + mURL = new KURLRequester( this ); + + mainLayout->addWidget( label, 0, 0 ); + mainLayout->addWidget( mURL, 0, 1 ); + + label = new QLabel( i18n( "User:" ), this ); + mUser = new KLineEdit( this ); + + mainLayout->addWidget( label, 1, 0 ); + mainLayout->addWidget( mUser, 1, 1 ); + + label = new QLabel( i18n( "Password:" ), this ); + mPassword = new KLineEdit( this ); + mPassword->setEchoMode( QLineEdit::Password ); + + mainLayout->addWidget( label, 2, 0 ); + mainLayout->addWidget( mPassword, 2, 1 ); + + QFrame *hline = new QFrame( this ); + hline->setFrameStyle( QFrame::HLine | QFrame::Sunken ); + + mainLayout->addMultiCellWidget( hline, 3, 3, 0, 1 ); + + mFolderConfig = new KPIM::FolderConfig( this ); + connect( mFolderConfig, SIGNAL( updateFoldersClicked() ), + SLOT( updateFolders() ) ); + mainLayout->addMultiCellWidget( mFolderConfig, 4, 4, 0, 1 ); +} + +void ResourceGroupwareBaseConfig::loadSettings( KRES::Resource *res ) +{ + mResource = dynamic_cast<ResourceGroupwareBase*>( res ); + + if ( !mResource ) { + kdDebug(5700) << "ResourceGroupwareBaseConfig::loadSettings(): cast failed" << endl; + return; + } + + mURL->setURL( mResource->prefs()->url() ); + mUser->setText( mResource->prefs()->user() ); + mPassword->setText( mResource->prefs()->password() ); + + mFolderConfig->setFolderLister( mResource->folderLister() ); + mFolderConfig->updateFolderList(); +} + +void ResourceGroupwareBaseConfig::saveSettings( KRES::Resource *res ) +{ + ResourceGroupwareBase *resource = dynamic_cast<ResourceGroupwareBase*>( res ); + + if ( !resource ) { + kdDebug(5700) << "ResourceGroupwareBaseConfig::saveSettings(): cast failed" << endl; + return; + } + + resource->prefs()->setUrl( mURL->url() ); + resource->prefs()->setUser( mUser->text() ); + resource->prefs()->setPassword( mPassword->text() ); + + mFolderConfig->saveSettings(); +} + +void ResourceGroupwareBaseConfig::updateFolders() +{ + KURL url = mURL->url(); + url.setUser( mUser->text() ); + url.setPass( mPassword->text() ); + + mFolderConfig->retrieveFolderList( url ); +} + +#include "kabc_resourcegroupwarebaseconfig.moc" diff --git a/kresources/lib/kabc_resourcegroupwarebaseconfig.h b/kresources/lib/kabc_resourcegroupwarebaseconfig.h new file mode 100644 index 000000000..ba2ae1715 --- /dev/null +++ b/kresources/lib/kabc_resourcegroupwarebaseconfig.h @@ -0,0 +1,64 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ +#ifndef KABC_RESOURCEGROUPWAREBASECONFIG_H +#define KABC_RESOURCEGROUPWAREBASECONFIG_H + +#include <kresources/configwidget.h> +#include <kdepimmacros.h> + +class KLineEdit; +class KURLRequester; + +namespace KPIM { +class FolderConfig; +} + +namespace KABC { + +class ResourceGroupwareBase; + +class KDE_EXPORT ResourceGroupwareBaseConfig : public KRES::ConfigWidget +{ + Q_OBJECT + + public: + ResourceGroupwareBaseConfig( QWidget* parent = 0, const char* name = 0 ); + + public slots: + void loadSettings( KRES::Resource* ); + void saveSettings( KRES::Resource* ); + + protected slots: + void updateFolders(); + + private: + KURLRequester *mURL; + KLineEdit *mUser; + KLineEdit *mPassword; + KPIM::FolderConfig *mFolderConfig; + + ResourceGroupwareBase *mResource; +}; + +} + +#endif diff --git a/kresources/lib/kcal_cachesettingsdlg.cpp b/kresources/lib/kcal_cachesettingsdlg.cpp new file mode 100644 index 000000000..ea89dfa5d --- /dev/null +++ b/kresources/lib/kcal_cachesettingsdlg.cpp @@ -0,0 +1,89 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + +#include "kcal_cachesettingsdlg.h" + +#include "kcal_resourcegroupwarebase.h" +#include "kresources_groupwareprefs.h" + +#include <libkcal/resourcecachedconfig.h> + +#include <klocale.h> +#include <kdebug.h> +#include <klineedit.h> +#include <kdialog.h> + +#include <qlabel.h> +#include <qlayout.h> + + +using namespace KCal; + +CacheSettingsDialog::CacheSettingsDialog( QWidget* parent, const char* name ) + : KDialogBase( parent, name, true, i18n("Resource Cache Settings"), KDialogBase::Close ) +{ + QWidget *mainWidget = new QWidget( this ); + setMainWidget( mainWidget ); + + QGridLayout *mainLayout = new QGridLayout( mainWidget, 2, 2 ); + mainLayout->setSpacing( KDialog::spacingHint() ); + + mReloadConfig = new KCal::ResourceCachedReloadConfig( mainWidget ); + mainLayout->addMultiCellWidget( mReloadConfig, 1, 3, 2, 2 ); + + mSaveConfig = new KCal::ResourceCachedSaveConfig( mainWidget ); + mainLayout->addMultiCellWidget( mSaveConfig, 4, 4, 2, 2 ); +} + +void CacheSettingsDialog::loadSettings( KRES::Resource *resource ) +{ + kdDebug(7000) << "KCal::CacheSettingsDialog::loadSettings()" << endl; + + ResourceGroupwareBase *res = static_cast<ResourceGroupwareBase *>( resource ); + if ( res ) { + if ( !res->prefs() ) { + kdError() << "No PREF" << endl; + return; + } + + mReloadConfig->loadSettings( res ); + mSaveConfig->loadSettings( res ); + + } else { + kdError(5700) << "CacheSettingsDialog::loadSettings(): " + "no ResourceGroupwareBase, cast failed" << endl; + } +} + +void CacheSettingsDialog::saveSettings( KRES::Resource *resource ) +{ + ResourceGroupwareBase *res = static_cast<ResourceGroupwareBase*>( resource ); + if ( res ) { + mReloadConfig->saveSettings( res ); + mSaveConfig->saveSettings( res ); + } else { + kdError(5700) << "CacheSettingsDialog::saveSettings(): " + "no ResourceGroupwareBase, cast failed" << endl; + } +} + +#include "kcal_cachesettingsdlg.moc" diff --git a/kresources/lib/kcal_cachesettingsdlg.h b/kresources/lib/kcal_cachesettingsdlg.h new file mode 100644 index 000000000..71ec6de28 --- /dev/null +++ b/kresources/lib/kcal_cachesettingsdlg.h @@ -0,0 +1,59 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ +#ifndef KCAL_CACHESETTINGSDLG_H +#define KCAL_CACHESETTINGSDLG_H + +#include <kdialogbase.h> +#include <kdepimmacros.h> + + +namespace KRES { +class Resource; +} + +namespace KCal { + +class ResourceCachedReloadConfig; +class ResourceCachedSaveConfig; + +/** + Configuration widget for groupware kioslave resource. + @see KCalOpenGroupware +*/ +class KDE_EXPORT CacheSettingsDialog : public KDialogBase +{ + Q_OBJECT + public: + CacheSettingsDialog( QWidget *parent = 0, const char *name = 0 ); + + public slots: + virtual void loadSettings( KRES::Resource *resource ); + virtual void saveSettings( KRES::Resource *resource ); + + private: + KCal::ResourceCachedReloadConfig *mReloadConfig; + KCal::ResourceCachedSaveConfig *mSaveConfig; +}; + +} + +#endif diff --git a/kresources/lib/kcal_resourcegroupwarebase.cpp b/kresources/lib/kcal_resourcegroupwarebase.cpp new file mode 100644 index 000000000..aaf471218 --- /dev/null +++ b/kresources/lib/kcal_resourcegroupwarebase.cpp @@ -0,0 +1,410 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ + +#include "kcal_resourcegroupwarebase.h" +#include "kresources_groupwareprefs.h" + +#include "libkcal/confirmsavedialog.h" +#include "folderlister.h" +#include "calendaradaptor.h" +#include "groupwaredownloadjob.h" +#include "groupwareuploadjob.h" + +#include <libkcal/icalformat.h> +#include <kio/job.h> +#include <klocale.h> + +#include <qapplication.h> + +using namespace KCal; + +ResourceGroupwareBase::ResourceGroupwareBase() + : ResourceCached( 0 ), mPrefs(0), mFolderLister(0), + mLock( true ), mAdaptor(0), mDownloadJob(0), mUploadJob(0) +{ +} + +ResourceGroupwareBase::ResourceGroupwareBase( const KConfig *config ) + : ResourceCached( config ), mPrefs(0), mFolderLister(0), + mLock( true ), mAdaptor(0), mDownloadJob(0), mUploadJob(0) +{ + if ( config ) readConfig( config ); +} + +ResourceGroupwareBase::~ResourceGroupwareBase() +{ + disableChangeNotification(); + + delete mPrefs; + mPrefs = 0; +} + +KPIM::GroupwarePrefsBase *ResourceGroupwareBase::createPrefs() +{ + return new KPIM::GroupwarePrefsBase(); +} + + +bool ResourceGroupwareBase::addEvent( Event *event ) +{ + if ( adaptor() && ( adaptor()->supports( KPIM::FolderLister::Event ) || + adaptor()->supports( KPIM::FolderLister::All ) ) ) { + return ResourceCached::addEvent( event ); + } else return false; +} + +bool ResourceGroupwareBase::addTodo( Todo *todo ) +{ + if ( adaptor() && ( adaptor()->supports( KPIM::FolderLister::Todo ) || + adaptor()->supports( KPIM::FolderLister::All ) ) ) { + return ResourceCached::addTodo( todo ); + } else return false; +} + +bool ResourceGroupwareBase::addJournal( Journal *journal ) +{ + if ( adaptor() && ( adaptor()->supports( KPIM::FolderLister::Journal ) || + adaptor()->supports( KPIM::FolderLister::All ) ) ) { + return ResourceCached::addJournal( journal ); + } else return false; +} + + +KPIM::GroupwareDownloadJob *ResourceGroupwareBase::createDownloadJob( + CalendarAdaptor *adaptor ) +{ + return new KPIM::GroupwareDownloadJob( adaptor ); +} + +KPIM::GroupwareUploadJob *ResourceGroupwareBase::createUploadJob( + CalendarAdaptor *adaptor ) +{ + return new KPIM::GroupwareUploadJob( adaptor ); +} + +void ResourceGroupwareBase::setPrefs( KPIM::GroupwarePrefsBase *newprefs ) +{ + if ( !newprefs ) return; + if ( mPrefs ) delete mPrefs; + mPrefs = newprefs; + mPrefs->addGroupPrefix( identifier() ); + + mPrefs->readConfig(); + if ( mFolderLister ) mFolderLister->readConfig( mPrefs ); +} + +void ResourceGroupwareBase::setFolderLister( KPIM::FolderLister *folderLister ) +{ + if ( !folderLister ) return; + if ( mFolderLister ) delete mFolderLister; + mFolderLister = folderLister; + if ( mPrefs ) mFolderLister->readConfig( mPrefs ); + if ( adaptor() ) { + adaptor()->setFolderLister( mFolderLister ); + mFolderLister->setAdaptor( adaptor() ); + } +} + +void ResourceGroupwareBase::setAdaptor( CalendarAdaptor *adaptor ) +{ + if ( !adaptor ) return; + if ( mAdaptor ) delete mAdaptor; + mAdaptor = adaptor; + mAdaptor->setFolderLister( mFolderLister ); + if ( mFolderLister ) mFolderLister->setAdaptor( mAdaptor ); + // TODO: Set the prgreess status in the up/download jobs, and set + // the resource name as the label. This should be done in the + // up/download jobs, but these don't have access to the resource's + // name, do they? +/* mAdaptor->setDownloadProgressMessage( i18n("Downloading calendar") ); + mAdaptor->setUploadProgressMessage( i18n("Uploading calendar") );*/ + if ( prefs() ) { + mAdaptor->setBaseURL( prefs()->url() ); + mAdaptor->setUser( prefs()->user() ); + mAdaptor->setPassword( prefs()->password() ); + } + mAdaptor->setIdMapper( &idMapper() ); + mAdaptor->setResource( this ); +} + +void ResourceGroupwareBase::init() +{ + mDownloadJob = 0; + mIsShowingError = false; + + enableChangeNotification(); +} + +KPIM::GroupwarePrefsBase *ResourceGroupwareBase::prefs() +{ + return mPrefs; +} + +void ResourceGroupwareBase::readConfig( const KConfig *config ) +{ + kdDebug(5800) << "KCal::ResourceGroupwareBase::readConfig()" << endl; + ResourceCached::readConfig( config ); + if ( mPrefs ) { + mPrefs->readConfig(); + if ( mFolderLister ) + mFolderLister->readConfig( mPrefs ); + } +} + +void ResourceGroupwareBase::writeConfig( KConfig *config ) +{ + kdDebug(5800) << "KCal::ResourceGroupwareBase::writeConfig()" << endl; + + ResourceCalendar::writeConfig( config ); + ResourceCached::writeConfig( config ); + + if ( mPrefs ) { + if ( mFolderLister ) + mFolderLister->writeConfig( mPrefs ); + mPrefs->writeConfig(); + } +} + +bool ResourceGroupwareBase::doOpen() +{ + if ( !adaptor() ) + return false; + if ( adaptor()->flags() & KPIM::GroupwareDataAdaptor::GWResNeedsLogon ) { + KIO::Job *loginJob = adaptor()->createLoginJob( prefs()->url(), prefs()->user(), prefs()->password() ); + if ( !loginJob ) { + return false; + } else { + mLoginFinished = false; + connect( loginJob, SIGNAL( result( KIO::Job * ) ), + SLOT( slotLoginJobResult( KIO::Job* ) ) ); + enter_loop(); + return mLoginFinished; + } + } + return true; +} + +// BEGIN:COPIED +// TODO: Get rid of this hack, which is copied from KIO::NetAccess, which is +// LGPL'ed and +// Copyright (C) 1997 Torben Weis (weis@kde.org) +// Copyright (C) 1998 Matthias Ettrich (ettrich@kde.org) +// Copyright (C) 1999 David Faure (faure@kde.org) +// If a troll sees this, he kills me +void qt_enter_modal( QWidget *widget ); +void qt_leave_modal( QWidget *widget ); + +void ResourceGroupwareBase::enter_loop() +{ + QWidget dummy(0,0,WType_Dialog | WShowModal); + dummy.setFocusPolicy( QWidget::NoFocus ); + qt_enter_modal(&dummy); + qApp->enter_loop(); + qt_leave_modal(&dummy); +} +// END:COPIED + +void ResourceGroupwareBase::slotLoginJobResult( KIO::Job *job ) +{ + if ( !adaptor() ) return; + mLoginFinished = adaptor()->interpretLoginJobResult( job ); + qApp->exit_loop(); +} + +void ResourceGroupwareBase::doClose() +{ + ResourceCached::doClose(); + if ( mDownloadJob ) mDownloadJob->kill(); + + if ( adaptor() && + adaptor()->flags() & KPIM::GroupwareDataAdaptor::GWResNeedsLogoff ) { + KIO::Job *logoffJob = adaptor()->createLogoffJob( prefs()->url(), prefs()->user(), prefs()->password() ); + connect( logoffJob, SIGNAL( result( KIO::Job * ) ), + SLOT( slotLogoffJobResult( KIO::Job* ) ) ); + // TODO: Do we really need to block while waiting for the job to return? + enter_loop(); + } +} + +void ResourceGroupwareBase::slotLogoffJobResult( KIO::Job *job ) +{ + if ( !adaptor() ) return; + adaptor()->interpretLogoffJobResult( job ); + // TODO: Do we really need to block while waiting for the job to return? + qApp->exit_loop(); +} + +bool ResourceGroupwareBase::doLoad() +{ + kdDebug(5800) << "ResourceGroupwareBase::load()" << endl; + + if ( mIsShowingError ) { + kdDebug(5800) << "Still showing error" << endl; + return true; + } + + if ( mDownloadJob ) { + kdWarning() << "Download still in progress" << endl; + return false; + } + + mCalendar.close(); + clearChanges(); + disableChangeNotification(); + loadCache(); + enableChangeNotification(); + emit resourceChanged( this ); + + mDownloadJob = createDownloadJob( adaptor() ); + connect( mDownloadJob, SIGNAL( result( KPIM::GroupwareJob * ) ), + SLOT( slotDownloadJobResult( KPIM::GroupwareJob * ) ) ); + + return true; +} + +void ResourceGroupwareBase::slotDownloadJobResult( KPIM::GroupwareJob *job ) +{ + kdDebug(5800) << "ResourceGroupwareBase::slotJobResult(): " << endl; + + if ( job->error() ) { + mIsShowingError = true; + loadError( job->errorString() ); + mIsShowingError = false; + } else { + kdDebug(5800) << "Successfully downloaded data" << endl; + + clearChanges(); + saveCache(); + enableChangeNotification(); + + emit resourceChanged( this ); + emit resourceLoaded( this ); + } + + mDownloadJob = 0; +} + +bool ResourceGroupwareBase::doSave() +{ + kdDebug(5800) << "KCal::ResourceGroupwareBase::doSave()" << endl; + + saveCache(); + + if ( !hasChanges() ) { + kdDebug(5800) << "No changes" << endl; + return true; + } + // TODO: Implement confirming of single changes i.e. it should be possible + // to upload only certain changes and discard the rest. This is + // particularly important for resources like the blogging resource, + // where uploading would mean a republication of the blog, not only + // a modifications. + if ( !confirmSave() ) return false; + + mUploadJob = createUploadJob( adaptor() ); + connect( mUploadJob, SIGNAL( result( KPIM::GroupwareJob * ) ), + SLOT( slotUploadJobResult( KPIM::GroupwareJob * ) ) ); + + Incidence::List inc; + Incidence::List::Iterator it; + KPIM::GroupwareUploadItem::List addedItems, changedItems, deletedItems; + + inc = addedIncidences(); + for( it = inc.begin(); it != inc.end(); ++it ) { + addedItems.append( adaptor()->newUploadItem( *it, + KPIM::GroupwareUploadItem::Added ) ); + } + // TODO: Check if the item has changed on the server... + // In particular, check if the version we based our change on is still current + // on the server + inc = changedIncidences(); + for( it = inc.begin(); it != inc.end(); ++it ) { + changedItems.append( adaptor()->newUploadItem( *it, + KPIM::GroupwareUploadItem::Changed ) ); + } + inc = deletedIncidences(); + for( it = inc.begin(); it != inc.end(); ++it ) { + deletedItems.append( adaptor()->newUploadItem( *it, + KPIM::GroupwareUploadItem::Deleted ) ); + } + + mUploadJob->setAddedItems( addedItems ); + mUploadJob->setChangedItems( changedItems ); + mUploadJob->setDeletedItems( deletedItems ); + + // FIXME: Calling clearChanges() here is not the ideal way since the + // upload might fail, but there is no other place to call it... + clearChanges(); + return true; +} + +void ResourceGroupwareBase::slotUploadJobResult( KPIM::GroupwareJob *job ) +{ + kdDebug(5800) << "ResourceGroupwareBase::slotUploadJobResult(): " << endl; + + if ( job->error() ) { + mIsShowingError = true; + loadError( job->errorString() ); + mIsShowingError = false; + } else { + kdDebug(5800) << "Successfully uploaded data" << endl; + /* + * After the put the server might have expanded recurring events and will + * also change the uids of the uploaded events. Remove them from the cache + * and get the fresh delta and download. + */ + + if ( !mDownloadJob ) { + mDownloadJob = createDownloadJob( adaptor() ); + connect( mDownloadJob, SIGNAL( result( KPIM::GroupwareJob * ) ), + SLOT( slotDownloadJobResult( KPIM::GroupwareJob * ) ) ); + } else { + kdWarning() << k_funcinfo << "Download still in progress. " + "Can't happen. (TM)" << endl; + } + } + + mDownloadJob = 0; +} + +// FIXME: Put this into ResourceCached +bool ResourceGroupwareBase::confirmSave() +{ + if ( !hasChanges() ) return true; + + ConfirmSaveDialog dlg( resourceName(), 0 ); + + dlg.addIncidences( addedIncidences(), i18n("Added") ); + dlg.addIncidences( changedIncidences(), i18n("Changed") ); + dlg.addIncidences( deletedIncidences(), i18n("Deleted") ); + + int result = dlg.exec(); + return result == QDialog::Accepted; +} + +KABC::Lock *ResourceGroupwareBase::lock() +{ + return &mLock; +} + +#include "kcal_resourcegroupwarebase.moc" diff --git a/kresources/lib/kcal_resourcegroupwarebase.h b/kresources/lib/kcal_resourcegroupwarebase.h new file mode 100644 index 000000000..f0994a54e --- /dev/null +++ b/kresources/lib/kcal_resourcegroupwarebase.h @@ -0,0 +1,118 @@ + /* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +#ifndef KCAL_RESOURCEGROUPWAREBASE_H +#define KCAL_RESOURCEGROUPWAREBASE_H + +#include <kurl.h> +#include <libkcal/resourcecached.h> +#include <kdepimmacros.h> +#include <kabc/locknull.h> + +namespace KIO { +class Job; +} + +namespace KPIM { +class GroupwareJob; +class GroupwareDownloadJob; +class GroupwareUploadJob; +class FolderLister; +class GroupwarePrefsBase; +} + + +namespace KCal { + +class CalendarAdaptor; + +/** + This class provides a resource for accessing a Groupware kioslave-based + calendar. +*/ +class KDE_EXPORT ResourceGroupwareBase : public ResourceCached +{ + Q_OBJECT + public: + ResourceGroupwareBase(); + + ResourceGroupwareBase( const KConfig * ); + virtual ~ResourceGroupwareBase(); + + void readConfig( const KConfig *config ); + void writeConfig( KConfig *config ); + + KPIM::GroupwarePrefsBase *prefs(); + KPIM::FolderLister *folderLister() { return mFolderLister; } + + bool doOpen(); + void doClose(); + + bool doLoad(); + bool doSave(); + + KABC::Lock *lock(); + + bool addEvent( Event *event ); + bool addTodo( Todo *todo ); + bool addJournal( Journal *journal ); + + protected: + void init(); + + bool confirmSave(); + + KPIM::GroupwarePrefsBase *createPrefs(); + void setPrefs( KPIM::GroupwarePrefsBase *prefs ); + void setFolderLister( KPIM::FolderLister *folderLister ); + void setAdaptor( CalendarAdaptor *adaptor ); + CalendarAdaptor *adaptor() const { return mAdaptor; } + + virtual KPIM::GroupwareDownloadJob *createDownloadJob( CalendarAdaptor *adaptor ); + virtual KPIM::GroupwareUploadJob *createUploadJob( CalendarAdaptor *adaptor ); + + protected slots: + void slotLoginJobResult( KIO::Job *job ); + void slotLogoffJobResult( KIO::Job *job ); + void slotDownloadJobResult( KPIM::GroupwareJob * ); + void slotUploadJobResult( KPIM::GroupwareJob * ); + + private: + void enter_loop(); + + KPIM::GroupwarePrefsBase *mPrefs; + KPIM::FolderLister *mFolderLister; + KABC::LockNull mLock; + CalendarAdaptor *mAdaptor; + + KPIM::GroupwareDownloadJob *mDownloadJob; + KPIM::GroupwareUploadJob *mUploadJob; + + bool mIsShowingError; + + bool mLoginFinished; // temp variable for the login job + +}; + +} + +#endif diff --git a/kresources/lib/kcal_resourcegroupwarebaseconfig.cpp b/kresources/lib/kcal_resourcegroupwarebaseconfig.cpp new file mode 100644 index 000000000..2b4bc81be --- /dev/null +++ b/kresources/lib/kcal_resourcegroupwarebaseconfig.cpp @@ -0,0 +1,137 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + +#include "kcal_resourcegroupwarebaseconfig.h" + +#include "kcal_cachesettingsdlg.h" +#include "kcal_resourcegroupwarebase.h" +#include "kresources_groupwareprefs.h" +#include "folderconfig.h" + +#include <libkcal/resourcecachedconfig.h> + +#include <klocale.h> +#include <kdebug.h> +#include <klineedit.h> +#include <kdialog.h> +#include <kpushbutton.h> + +#include <qlabel.h> +#include <qlayout.h> +#include <qhbox.h> + + +using namespace KCal; + +ResourceGroupwareBaseConfig::ResourceGroupwareBaseConfig( QWidget* parent, + const char* name ) + : KRES::ConfigWidget( parent, name ) +{ + resize( 245, 115 ); + + QGridLayout *mainLayout = new QGridLayout( this, 2, 2 ); + mainLayout->setSpacing( KDialog::spacingHint() ); + + QLabel *label = new QLabel( i18n("URL:"), this ); + mainLayout->addWidget( label, 1, 0 ); + mUrl = new KLineEdit( this ); + mainLayout->addWidget( mUrl, 1, 1 ); + + label = new QLabel( i18n("User:"), this ); + mainLayout->addWidget( label, 2, 0 ); + mUserEdit = new KLineEdit( this ); + mainLayout->addWidget( mUserEdit, 2, 1 ); + + label = new QLabel( i18n("Password:"), this ); + mainLayout->addWidget( label, 3, 0 ); + mPasswordEdit = new KLineEdit( this ); + mainLayout->addWidget( mPasswordEdit, 3, 1 ); + mPasswordEdit->setEchoMode( KLineEdit::Password ); + + mFolderConfig = new KPIM::FolderConfig( this ); + connect( mFolderConfig, SIGNAL( updateFoldersClicked() ), + SLOT( updateFolders() ) ); + mainLayout->addMultiCellWidget( mFolderConfig, 4, 4, 0, 1 ); + + QHBox *hBox = new QHBox( this ); + mCacheSettingsButton = new KPushButton( i18n("Configure Cache Settings..."), hBox ); + mainLayout->addMultiCellWidget( hBox, 5, 5, 0, 1 ); + connect( mCacheSettingsButton, SIGNAL( clicked() ), + SLOT( showCacheSettings() ) ); + + mCacheDialog = new CacheSettingsDialog( this ); +} + +void ResourceGroupwareBaseConfig::loadSettings( KRES::Resource *resource ) +{ + kdDebug(7000) << "KCal::ResourceGroupwareBaseConfig::loadSettings()" << endl; + + ResourceGroupwareBase *res = static_cast<ResourceGroupwareBase *>( resource ); + if ( res ) { + if ( !res->prefs() ) { + kdError() << "No PREF" << endl; + return; + } + + mUrl->setText( res->prefs()->url() ); + mUserEdit->setText( res->prefs()->user() ); + mPasswordEdit->setText( res->prefs()->password() ); + if ( mCacheDialog ) mCacheDialog->loadSettings( res ); + + mFolderConfig->setFolderLister( res->folderLister() ); + mFolderConfig->updateFolderList(); + } else { + kdError(5700) << "KCalResourceGroupwareBaseConfig::loadSettings(): " + "no KCalOpenGroupware, cast failed" << endl; + } +} + +void ResourceGroupwareBaseConfig::saveSettings( KRES::Resource *resource ) +{ + ResourceGroupwareBase *res = static_cast<ResourceGroupwareBase*>( resource ); + if ( res ) { + res->prefs()->setUrl( mUrl->text() ); + res->prefs()->setUser( mUserEdit->text() ); + res->prefs()->setPassword( mPasswordEdit->text() ); + if ( mCacheDialog ) mCacheDialog->saveSettings( res ); + mFolderConfig->saveSettings(); + } else { + kdError(5700) << "KCalResourceGroupwareBaseConfig::saveSettings(): " + "no KCalOpenGroupware, cast failed" << endl; + } +} + +void ResourceGroupwareBaseConfig::updateFolders() +{ + KURL url = mUrl->text(); + url.setUser( mUserEdit->text() ); + url.setPass( mPasswordEdit->text() ); + + mFolderConfig->retrieveFolderList( url ); +} + +void ResourceGroupwareBaseConfig::showCacheSettings() +{ + if ( mCacheDialog ) mCacheDialog->exec(); +} + +#include "kcal_resourcegroupwarebaseconfig.moc" diff --git a/kresources/lib/kcal_resourcegroupwarebaseconfig.h b/kresources/lib/kcal_resourcegroupwarebaseconfig.h new file mode 100644 index 000000000..a88afbc56 --- /dev/null +++ b/kresources/lib/kcal_resourcegroupwarebaseconfig.h @@ -0,0 +1,73 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ +#ifndef KCAL_RESOURCEGROUPWAREBASECONFIG_H +#define KCAL_RESOURCEGROUPWAREBASECONFIG_H + +#include <kresources/configwidget.h> +#include <kdepimmacros.h> + +class KPushButton; +class KLineEdit; + +namespace KPIM { +class FolderConfig; +} +namespace KRES { +class Resource; +} + +namespace KCal { + +class CacheSettingsDialog; + +/** + Configuration widget for groupware kioslave resource. + + @see KCalOpenGroupware +*/ +class KDE_EXPORT ResourceGroupwareBaseConfig : public KRES::ConfigWidget +{ + Q_OBJECT + public: + ResourceGroupwareBaseConfig( QWidget *parent = 0, const char *name = 0 ); + + public slots: + virtual void loadSettings( KRES::Resource *resource ); + virtual void saveSettings( KRES::Resource *resource ); + + protected slots: + void updateFolders(); + void showCacheSettings(); + + private: + KLineEdit *mUrl; + KLineEdit *mUserEdit; + KLineEdit *mPasswordEdit; + KPushButton *mCacheSettingsButton; + + CacheSettingsDialog *mCacheDialog; + KPIM::FolderConfig *mFolderConfig; +}; + +} + +#endif diff --git a/kresources/lib/kresources_groupwareprefs.kcfg b/kresources/lib/kresources_groupwareprefs.kcfg new file mode 100644 index 000000000..a56c14d90 --- /dev/null +++ b/kresources/lib/kresources_groupwareprefs.kcfg @@ -0,0 +1,56 @@ +<?xml version="1.0" encoding="UTF-8"?> +<kcfg xmlns="http://www.kde.org/standards/kcfg/1.0" + xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" + xsi:schemaLocation="http://www.kde.org/standards/kcfg/1.0 + http://www.kde.org/standards/kcfg/1.0/kcfg.xsd" > + <kcfgfile name="kresources_groupwarerc"/> + <group name="General" > + <entry key="Url" type="String" > + <label>Server URL</label> + </entry> + <entry key="User" type="String" > + <label>User Name</label> + </entry> + <entry key="Password" type="String" > + <label>Password</label> + </entry> + </group> + <group name="Folders"> + <!--entry key="FolderIds" type="StringList"> + <label>All folder IDs on the server</label> + </entry> + <entry key="FolderNames" type="StringList"> + <label>All folder names on the server</label> + </entry--> + <entry key="ActiveFolders" type="StringList"> + <label>All active folders from the server</label> + </entry> + <entry key="FolderNumber" type="UInt"> + <label>Number of folders on the server and in the config file</label> + </entry> + <entry name="Folder$(nr)" type="StringList"> + <parameter name="nr" type="Int" max="100"/> + </entry> + <entry name="DefaultDestinations" type="StringList"> + <label>Default destinations for the various types</label> + <whatsthis>These are the default destinations for the different data +types in the following order: +Event, Todo, Journal, Contact, All, Unknown</whatsthis> +<!-- I tried using a parametrized entry using an enum, but the config +compiler from 3.3 is severely broken in that respect... --> +</entry> + <!--entry name="DefaultDestination$(Type)" type="String"> + <parameter name="Type" type="Enum"> + <values> + <value>Event</value> + <value>Todo</value> + <value>Journal</value> + <value>Contact</value> + <value>All</value> + <value>Unknown</value> + </values> + </parameter> + <default></default> + </entry--> + </group> +</kcfg> diff --git a/kresources/lib/kresources_groupwareprefs.kcfgc b/kresources/lib/kresources_groupwareprefs.kcfgc new file mode 100644 index 000000000..d67149d5f --- /dev/null +++ b/kresources/lib/kresources_groupwareprefs.kcfgc @@ -0,0 +1,8 @@ +ClassName=GroupwarePrefsBase +File=kresources_groupwareprefs.kcfg +GlobalEnums=false +IncludeFiles=libkdepim/kresourceprefs.h +Inherits=KResourcePrefs +Mutators=true +NameSpace=KPIM +Singleton=false diff --git a/kresources/lib/webdavhandler.cpp b/kresources/lib/webdavhandler.cpp new file mode 100644 index 000000000..e6c0a4937 --- /dev/null +++ b/kresources/lib/webdavhandler.cpp @@ -0,0 +1,194 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + + +#include <kdebug.h> + +#include <qdatetime.h> + +extern "C" { + #include <ical.h> +} + + +#include "webdavhandler.h" + +WebdavHandler::WebdavHandler() +{ +} + + +KURL WebdavHandler::toDAV( const KURL& url ) +{ + KURL result( url ); + + if ( result.protocol() == "http" ) { + if ( result.port() == 443 ) { + // OpenGroupware.org returns 'http://server:443' instead of 'https://server' + result.setProtocol( "webdavs" ); + result.setPort( 0 ); + } else + result.setProtocol( "webdav" ); + } else if ( result.protocol() == "https" ) + result.setProtocol( "webdavs" ); + + return result; +} + + + +QDomElement WebdavHandler::addElement( QDomDocument &doc, QDomNode &node, + const QString &tag, const QString &value ) +{ + QDomElement el = doc.createElement( tag ); + node.appendChild( el ); + if ( !value.isNull() ) { + QDomText txt = doc.createTextNode( value ); + el.appendChild( txt ); + } + return el; +} + +QDomElement WebdavHandler::addElementNS( QDomDocument &doc, QDomNode &node, + const QString &ns, const QString &tag, const QString &value ) +{ + QDomElement el = doc.createElementNS( ns, tag ); + node.appendChild( el ); + if ( !value.isNull() ) { + QDomText txt = doc.createTextNode( value ); + el.appendChild( txt ); + } + return el; +} + +QDomElement WebdavHandler::addDavElement( QDomDocument &doc, QDomNode &node, + const QString &tag, const QString &value ) +{ + return addElementNS( doc, node, "DAV:", tag, value ); +} + +bool WebdavHandler::extractBool( const QDomElement &node, const QString &entry, bool &value ) +{ + QDomElement element = node.namedItem( entry ).toElement(); + if ( !element.isNull() ) { + value = (element.text() != "0"); + return true; + } + return false; +} + +bool WebdavHandler::extractLong( const QDomElement &node, const QString &entry, long &value ) +{ + QDomElement element = node.namedItem( entry ).toElement(); + if ( !element.isNull() ) { + value = element.text().toLong(); + return true; + } + return false; +} + +bool WebdavHandler::extractFloat( const QDomElement &node, const QString &entry, float &value ) +{ + QDomElement element = node.namedItem( entry ).toElement(); + if ( !element.isNull() ) { + value = element.text().toFloat(); + return true; + } + return false; +} + +bool WebdavHandler::extractDateTime( const QDomElement &node, const QString &entry, QDateTime &value ) +{ + QDomElement element = node.namedItem( entry ).toElement(); + if ( !element.isNull() && !element.text().isEmpty() ) { + value = QDateTime::fromString( element.text(), Qt::ISODate ); + return true; + } + return false; +} + +bool WebdavHandler::extractString( const QDomElement &node, const QString &entry, QString &value ) +{ + QDomElement element = node.namedItem( entry ).toElement(); + if ( !element.isNull() ) { + value = element.text(); + return true; + } + return false; +} + +bool WebdavHandler::extractStringList( const QDomElement &node, const QString &entry, QStringList &value ) +{ + QDomElement element = node.namedItem( entry ).toElement(); + if ( !element.isNull() ) { + value.clear(); + QDomNodeList list = element.elementsByTagNameNS( "xml:", "v" ); + for( uint i=0; i < list.count(); i++ ) { + QDomElement item = list.item(i).toElement(); + value.append( item.text() ); + } + return true; + } + return false; +} + + +const QString WebdavHandler::getEtagFromHeaders( const QString& headers ) +{ + int start = headers.find( "etag:", 0, false ); + if ( start < 0 ) return QString(); + start += 6; + return headers.mid( start, headers.find( "\n", start ) - start ); +} + +//TODO: should not call libical functions directly -- better to make +// a new libkcal abstraction method. +QDateTime WebdavHandler::utcAsZone( const QDateTime& utc, const QString& timeZoneId ) +{ + int daylight; + QDateTime epoch; + epoch.setTime_t( 0 ); + time_t v = epoch.secsTo( utc ); + struct icaltimetype tt = + icaltime_from_timet_with_zone( v, 0 /*is_date*/, + icaltimezone_get_builtin_timezone( "UTC" ) ); + int offset = icaltimezone_get_utc_offset( + icaltimezone_get_builtin_timezone( timeZoneId.latin1() ), + &tt, &daylight ); +kdDebug() << "Calculated offset of: " << offset << " of timezone: " << timeZoneId << endl; + return utc.addSecs( offset ); +} + +//TODO: should not call libical functions directly -- better to make +// a new libkcal abstraction method. +QDateTime WebdavHandler::zoneAsUtc( const QDateTime& zone, const QString& timeZoneId ) +{ + int daylight; + QDateTime epoch; + epoch.setTime_t( 0 ); + time_t v = epoch.secsTo( zone ); + struct icaltimetype tt = icaltime_from_timet( v, 0 ); // 0: is_date=false + int offset = icaltimezone_get_utc_offset( + icaltimezone_get_builtin_timezone( timeZoneId.latin1() ), + &tt, &daylight ); + return zone.addSecs( - offset ); +} diff --git a/kresources/lib/webdavhandler.h b/kresources/lib/webdavhandler.h new file mode 100644 index 000000000..cdf616e9c --- /dev/null +++ b/kresources/lib/webdavhandler.h @@ -0,0 +1,78 @@ +/* + This file is part of kdepim. + + Copyright (c) 2004 Cornelius Schumacher <schumacher@kde.org> + Copyright (c) 2004 Till Adam <adam@kde.org> + Copyright (c) 2005 Reinhold Kainhofer <reinhold@kainhofer.com> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ +#ifndef WEBDAVHANDLER_H +#define WEBDAVHANDLER_H + +#include <qstring.h> +#include <qstringlist.h> +#include <qdom.h> +#include <qdatetime.h> +#include <kurl.h> +#include <kdepimmacros.h> + +class KDE_EXPORT WebdavHandler +{ + public: + WebdavHandler(); + + static KURL toDAV( const KURL& url ); + + + static QDomElement addElementNS( QDomDocument &doc, QDomNode &node, + const QString &ns, const QString &tag, + const QString &value = QString::null ); + static QDomElement addElement( QDomDocument &, QDomNode &, + const QString &tag, const QString &value = QString::null ); + static QDomElement addDavElement( QDomDocument &, QDomNode &, + const QString &tag, const QString &value = QString::null ); + + static bool extractBool( const QDomElement &node, + const QString &entry, bool &value ); + static bool extractLong( const QDomElement &node, + const QString &entry, long &value ); + static bool extractFloat( const QDomElement &node, + const QString &entry, float &value ); + static bool extractDateTime( const QDomElement &node, + const QString &entry, QDateTime &value ); + static bool extractString( const QDomElement &node, + const QString &entry, QString &value ); + static bool extractStringList( const QDomElement &node, + const QString &entry, QStringList &value ); + + /** + * Returns the value of the "etag" header if it can be found in the headers. + */ + static const QString getEtagFromHeaders( const QString& ); + + + /** + * Return the representation of utc time in the time zone indicated by timeZoneId + */ + static QDateTime utcAsZone( const QDateTime& utc, const QString& timeZoneId ); + + /** + * Return the UTC representation of local time in the time zone indicated by timeZoneId + */ + static QDateTime zoneAsUtc( const QDateTime& zone, const QString& timeZoneId ); +}; + +#endif |