diff options
author | toma <toma@283d02a7-25f6-0310-bc7c-ecb5cbfe19da> | 2009-11-25 17:56:58 +0000 |
---|---|---|
committer | toma <toma@283d02a7-25f6-0310-bc7c-ecb5cbfe19da> | 2009-11-25 17:56:58 +0000 |
commit | bcb704366cb5e333a626c18c308c7e0448a8e69f (patch) | |
tree | f0d6ab7d78ecdd9207cf46536376b44b91a1ca71 /kopete/protocols/groupwise/libgroupwise/tasks | |
download | tdenetwork-bcb704366cb5e333a626c18c308c7e0448a8e69f.tar.gz tdenetwork-bcb704366cb5e333a626c18c308c7e0448a8e69f.zip |
Copy the KDE 3.5 branch to branches/trinity for new KDE 3.5 features.
BUG:215923
git-svn-id: svn://anonsvn.kde.org/home/kde/branches/trinity/kdenetwork@1054174 283d02a7-25f6-0310-bc7c-ecb5cbfe19da
Diffstat (limited to 'kopete/protocols/groupwise/libgroupwise/tasks')
75 files changed, 5188 insertions, 0 deletions
diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/Makefile.am b/kopete/protocols/groupwise/libgroupwise/tasks/Makefile.am new file mode 100644 index 00000000..cf966ca2 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/Makefile.am @@ -0,0 +1,30 @@ +INCLUDES = -I$(top_srcdir)/protocols/groupwise/libgroupwise/qca/src \ + -I$(srcdir)/../../libgroupwise/ -I$(top_srcdir)/kopete/protocols/groupwise/libgroupwise/qca/src \ + $(all_includes) +METASOURCES = AUTO +noinst_LTLIBRARIES = libgroupwise_tasks.la + +libgroupwise_tasks_la_SOURCES = requesttask.cpp eventtask.cpp logintask.cpp \ + setstatustask.cpp statustask.cpp conferencetask.cpp createconferencetask.cpp \ + sendmessagetask.cpp getdetailstask.cpp getstatustask.cpp typingtask.cpp connectiontask.cpp \ + sendinvitetask.cpp joinconferencetask.cpp leaveconferencetask.cpp rejectinvitetask.cpp \ + keepalivetask.cpp createcontacttask.cpp modifycontactlisttask.cpp createfoldertask.cpp \ + movecontacttask.cpp updateitemtask.cpp createcontactinstancetask.cpp deleteitemtask.cpp \ + updatefoldertask.cpp updatecontacttask.cpp pollsearchresultstask.cpp privacyitemtask.cpp \ + needfoldertask.cpp searchchattask.cpp searchusertask.cpp searchusertask.h \ + getchatsearchresultstask.cpp chatcountstask.cpp chatpropertiestask.cpp joinchattask.cpp +noinst_HEADERS = requesttask.h eventtask.h logintask.h setstatustask.h \ + statustask.h conferencetask.h createconferencetask.h sendmessagetask.h \ + getdetailstask.h getstatustask.h typingtask.h connectiontask.h sendinvitetask.h \ + joinconferencetask.h leaveconferencetask.h rejectinvitetask.h createcontacttask.h \ + modifycontactlisttask.h createfoldertask.h movecontacttask.h updateitemtask.h deleteitemtask.h \ + updatefoldertask.h updatecontacttask.h pollsearchresultstask.h privacyitemtask.h \ + needfoldertask.h searchchattask.h getchatsearchresultstask.h searchusertask.h \ + chatcountstask.h joinchattask.h + + +libgroupwise_tasks_la_LDFLAGS = -no-undefined $(all_libraries) +libgroupwise_tasks_la_LIBADD = $(LIB_QT) + + + diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/chatcountstask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/chatcountstask.cpp new file mode 100644 index 00000000..9e9837f7 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/chatcountstask.cpp @@ -0,0 +1,87 @@ +/* + Kopete Groupwise Protocol + ChatCountsTask.cpp - Task to update chatroom participant counts + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include <qmap.h> +#include <kdebug.h> + +#include "gwfield.h" +#include "response.h" + +#include "chatcountstask.h" + +using namespace GroupWise; + +ChatCountsTask::ChatCountsTask(Task* parent): RequestTask(parent) +{ + Field::FieldList lst; + createTransfer( "chatcounts", lst ); +} + + +ChatCountsTask::~ChatCountsTask() +{ +} + +bool ChatCountsTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + setError( response->resultCode() ); + return true; + } + + Field::FieldList responseFields = response->fields(); + Field::MultiField * resultsArray = responseFields.findMultiField( NM_A_FA_RESULTS ); + if ( !resultsArray ) + { + setError( Protocol ); + return true; + } + Field::FieldList counts = resultsArray->fields(); + const Field::FieldListIterator end = counts.end(); + for ( Field::FieldListIterator it = counts.find( NM_A_FA_CHAT ); + it != end; + it = counts.find( ++it, NM_A_FA_CHAT ) ) + { + Field::MultiField * mf = static_cast<Field::MultiField *>( *it ); + Field::FieldList chat = mf->fields(); + QString roomName; + int participants; + // read the supplied fields, set metadata and status. + Field::SingleField * sf; + if ( ( sf = chat.findSingleField ( NM_A_DISPLAY_NAME ) ) ) + roomName = sf->value().toString(); + if ( ( sf = chat.findSingleField ( NM_A_UD_PARTICIPANTS ) ) ) + participants = sf->value().toInt(); + + m_results.insert( roomName, participants ); + } + return true; +} + +QMap< QString, int > ChatCountsTask::results() +{ + return m_results; +} + +#include "chatcountstask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/chatcountstask.h b/kopete/protocols/groupwise/libgroupwise/tasks/chatcountstask.h new file mode 100644 index 00000000..c80a219a --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/chatcountstask.h @@ -0,0 +1,49 @@ +/* + Kopete Groupwise Protocol + chatcountstask.cpp - Task to update chatroom participant counts + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CHATCOUNTSTASK_H +#define CHATCOUNTSTASK_H + +#include <qvaluelist.h> + +#include "gwerror.h" +#include "gwfield.h" + +#include "requesttask.h" + +/** +Get the current number of users in each chat on the server + +@author SUSE Linux Products GmbH + */ +class ChatCountsTask : public RequestTask +{ + Q_OBJECT + public: + ChatCountsTask(Task* parent); + ~ChatCountsTask(); + bool take( Transfer * transfer ); + /** + * Contains a list of all the chatrooms that have participants on the server. If a chatroom exists but is empty, this task does not return a result, so update the participants count to 0. + */ + QMap< QString, int > results(); + private: + QMap< QString, int > m_results; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/chatpropertiestask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/chatpropertiestask.cpp new file mode 100644 index 00000000..66b2da42 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/chatpropertiestask.cpp @@ -0,0 +1,139 @@ +/* + Kopete Groupwise Protocol + ChatPropertiesTask.cpp - Task to update chatroom participant counts + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include <kdebug.h> + +#include "gwfield.h" +#include "response.h" + +#include "chatpropertiestask.h" + +using namespace GroupWise; + +ChatPropertiesTask::ChatPropertiesTask(Task* parent): RequestTask(parent) +{ +} + + +ChatPropertiesTask::~ChatPropertiesTask() +{ +} + +void ChatPropertiesTask::setChat( const QString &displayName ) +{ + Field::FieldList lst; + m_chat = displayName; + lst.append( new Field::SingleField( NM_A_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, m_chat ) ); + createTransfer( "chatproperties", lst ); +} + +bool ChatPropertiesTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + setError( response->resultCode() ); + return true; + } + + Field::FieldList responseFields = response->fields(); + Field::MultiField * resultsArray = responseFields.findMultiField( NM_A_FA_CHAT ); + if ( !resultsArray ) + { + setError( Protocol ); + return true; + } + + Field::FieldList lst = resultsArray->fields(); + const Field::FieldListIterator end = lst.end(); + for ( Field::FieldListIterator it = lst.begin(); + it != end; + ++it ) + { + Field::SingleField * sf = dynamic_cast<Field::SingleField *>( *it ); + if ( sf ) + { + if ( sf->tag() == NM_A_DISPLAY_NAME ) + continue; + else if ( sf->tag() == NM_A_CHAT_OWNER_DN ) + m_ownerDn = sf->value().toString(); + else if ( sf->tag() == NM_A_CHAT_CREATOR_DN ) + m_creatorDn= sf->value().toString(); + else if ( sf->tag() == NM_A_DESCRIPTION ) + m_description = sf->value().toString(); + else if ( sf->tag() == NM_A_DISCLAIMER ) + m_disclaimer = sf->value().toString(); + else if ( sf->tag() == NM_A_QUERY ) + m_query = sf->value().toString(); + else if ( sf->tag() == NM_A_ARCHIVE ) + m_archive = sf->value().toString(); + else if ( sf->tag() == NM_A_SZ_TOPIC ) + m_topic = sf->value().toString(); + else if ( sf->tag() == NM_A_CREATION_TIME ) + m_creationTime.setTime_t( sf->value().toInt() ); + else if ( sf->tag() == NM_A_UD_CHAT_RIGHTS ) + m_rights = sf->value().toInt(); + + } + else + { + Field::MultiField * mf = dynamic_cast<Field::MultiField *>( *it ); + if ( mf ) + { + if ( mf->tag() == NM_A_FA_CHAT_ACL ) + { + Field::FieldList acl = mf->fields(); + const Field::FieldListIterator aclEnd = acl.end(); + for ( Field::FieldListIterator aclIt = acl.begin(); + aclIt != aclEnd; + ++aclIt ) + { + Field::MultiField * aclEntryFields = dynamic_cast<Field::MultiField *>( *aclIt ); + if ( aclEntryFields ) + { + ChatContact entry; + Field::FieldList entryFields = aclEntryFields->fields(); + Field::SingleField * sf; + if ( ( sf = entryFields.findSingleField ( NM_A_SZ_DN ) ) ) + entry.dn = sf->value().toString(); + if ( ( sf = entryFields.findSingleField ( NM_A_SZ_ACCESS_FLAGS ) ) ) + entry.chatRights = sf->value().toInt(); + kdDebug ( GROUPWISE_DEBUG_GLOBAL ) << "got acl entry: " << entry.dn << ", " << entry.chatRights << endl; + m_aclEntries.append( entry ); + } + + } + } + } + } + } + kdDebug ( GROUPWISE_DEBUG_GLOBAL ) << "Got chatroom properties: " << m_chat << " : " << m_ownerDn << ", " << m_description << ", " << m_disclaimer << ", " << m_query << ", " << m_archive << ", " << m_topic << ", " << m_creatorDn << ", " << m_creationTime.toString() << ", " << m_rights << endl; + finished(); + return true; +} + +QValueList< ChatContact > ChatPropertiesTask::aclEntries() +{ + return m_aclEntries; +} + +#include "chatpropertiestask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/chatpropertiestask.h b/kopete/protocols/groupwise/libgroupwise/tasks/chatpropertiestask.h new file mode 100644 index 00000000..c9f890dd --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/chatpropertiestask.h @@ -0,0 +1,64 @@ +/* + Kopete Groupwise Protocol + chatcountstask.cpp - Task to update chatroom participant counts + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CHATPROPERTIESTASK_H +#define CHATPROPERTIESTASK_H + +#include <qdatetime.h> +#include <qvaluelist.h> +#include "gwchatrooms.h" +#include "gwerror.h" +#include "gwfield.h" + +#include "requesttask.h" + +/** +Get the current number of users in each chat on the server + +@author SUSE Linux Products GmbH + */ +class ChatPropertiesTask : public RequestTask +{ + Q_OBJECT + public: + ChatPropertiesTask(Task* parent); + ~ChatPropertiesTask(); + /** + * Specify which chatroom to get properties for + */ + void setChat( const QString & ); + bool take( Transfer * transfer ); + /** + * Contains a list of the ACL entries for the specified chatroom + */ + QValueList< GroupWise::ChatContact > aclEntries(); + QString m_chat; + QString m_ownerDn; + QString m_description; + QString m_disclaimer; + QString m_query; + QString m_archive; + QString m_maxUsers; + QString m_topic; + QString m_creatorDn; + QDateTime m_creationTime; + uint m_rights; + QValueList< GroupWise::ChatContact > m_aclEntries; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/conferencetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/conferencetask.cpp new file mode 100644 index 00000000..9773a622 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/conferencetask.cpp @@ -0,0 +1,230 @@ +/* + Kopete Groupwise Protocol + conferencetask.cpp - Event Handling task responsible for all conference related events + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "userdetailsmanager.h" + +#include "conferencetask.h" + +ConferenceTask::ConferenceTask( Task* parent ) + : EventTask( parent ) +{ + // register all the events that this task monitors + registerEvent( GroupWise::ConferenceClosed ); + registerEvent( GroupWise::ConferenceJoined ); + registerEvent( GroupWise::ConferenceLeft ); + registerEvent( GroupWise::ReceiveMessage ); + registerEvent( GroupWise::UserTyping ); + registerEvent( GroupWise::UserNotTyping ); + registerEvent( GroupWise::ConferenceInvite ); + registerEvent( GroupWise::ConferenceInviteNotify ); + registerEvent( GroupWise::ConferenceReject ); + registerEvent( GroupWise::ReceiveAutoReply ); + // GW7 + registerEvent( GroupWise::ReceivedBroadcast ); + registerEvent( GroupWise::ReceivedSystemBroadcast ); + + // listen to the UserDetailsManager telling us that user details are available + connect( client()->userDetailsManager(), SIGNAL( gotContactDetails( const GroupWise::ContactDetails & ) ), + SLOT( slotReceiveUserDetails( const GroupWise::ContactDetails & ) ) ); +} + + +ConferenceTask::~ConferenceTask() +{ +} + +void ConferenceTask::dumpConferenceEvent( ConferenceEvent & evt ) +{ + client()->debug( QString( "Conference Event - guid: %1 user: %2 timestamp: %3:%4:%5" ).arg + ( evt.guid ).arg( evt.user.ascii() ).arg( evt.timeStamp.time().hour() ).arg + ( evt.timeStamp.time().minute() ).arg( evt.timeStamp.time().second() ) ); + client()->debug( QString( " flags: %1" ).arg( evt.flags, 8 ) ); +} + +bool ConferenceTask::take( Transfer * transfer ) +{ + EventTransfer * incomingEvent; + if ( forMe( transfer, incomingEvent ) ) + { + client()->debug( "Got a conference event:" ); + ConferenceEvent event; + event.type = (GroupWise::Event)( incomingEvent->eventType() ); + event.timeStamp = incomingEvent->timeStamp(); + event.user = incomingEvent->source(); + event.flags = 0; + Q_ASSERT( incomingEvent->hasGuid() ); + event.guid = incomingEvent->guid(); + + switch ( event.type ) + { + case GroupWise::ConferenceClosed: + // extra debug - we never see these events, against spec. + client()->debug( "********************" ); + client()->debug( "* ConferenceClosed *" ); + client()->debug( "* ConferenceClosed *" ); + client()->debug( "* ConferenceClosed *" ); + client()->debug( "********************" ); + emit closed( event ); + break; + case GroupWise::ConferenceJoined: + Q_ASSERT( incomingEvent->hasFlags() ); + event.flags = incomingEvent->flags(); + client()->debug( "ConferenceJoined" ); + if ( !queueWhileAwaitingData( event ) ) + emit joined( event ); + break; + case GroupWise::ConferenceLeft: + Q_ASSERT( incomingEvent->hasFlags() ); + event.flags = incomingEvent->flags(); + client()->debug( "ConferenceLeft" ); + emit left( event ); + break; + case GroupWise::ReceiveMessage: + Q_ASSERT( incomingEvent->hasFlags() ); + event.flags = incomingEvent->flags(); + Q_ASSERT( incomingEvent->hasMessage() ); + event.message = incomingEvent->message(); + client()->debug( "ReceiveMessage" ); + client()->debug( QString( "message: %1" ).arg( event.message ) ); + if ( !queueWhileAwaitingData( event ) ) + emit message( event ); + break; + case GroupWise::UserTyping: + client()->debug( "UserTyping" ); + emit typing( event ); + break; + case GroupWise::UserNotTyping: + client()->debug( "UserNotTyping" ); + emit notTyping( event ); + break; + case GroupWise::ConferenceInvite: + Q_ASSERT( incomingEvent->hasMessage() ); + event.message = incomingEvent->message(); + client()->debug( "ConferenceInvite" ); + client()->debug( QString( "message: %1" ).arg( event.message ) ); + if ( !queueWhileAwaitingData( event ) ) + emit invited( event ); + break; + case GroupWise::ConferenceInviteNotify: + client()->debug( "ConferenceInviteNotify" ); + if ( !queueWhileAwaitingData( event ) ) + emit otherInvited( event ); + break; + case GroupWise::ConferenceReject: + client()->debug( "ConferenceReject" ); + if ( !queueWhileAwaitingData( event ) ) + emit invitationDeclined( event ); + break; + case GroupWise::ReceiveAutoReply: + Q_ASSERT( incomingEvent->hasFlags() ); + event.flags = incomingEvent->flags(); + Q_ASSERT( incomingEvent->hasMessage() ); + event.message = incomingEvent->message(); + client()->debug( "ReceiveAutoReply" ); + client()->debug( QString( "message: %1" ).arg( event.message.ascii() ) ); + emit autoReply( event ); + break; + case GroupWise::ReceivedBroadcast: + Q_ASSERT( incomingEvent->hasMessage() ); + event.message = incomingEvent->message(); + client()->debug( "ReceivedBroadCast" ); + client()->debug( QString( "message: %1" ).arg( event.message ) ); + if ( !queueWhileAwaitingData( event ) ) + emit broadcast( event ); + break; + case GroupWise::ReceivedSystemBroadcast: + Q_ASSERT( incomingEvent->hasMessage() ); + event.message = incomingEvent->message(); + client()->debug( "ReceivedSystemBroadCast" ); + client()->debug( QString( "message: %1" ).arg( event.message ) ); + emit systemBroadcast( event ); + break; + default: + client()->debug( QString( "WARNING: didn't handle registered event %1, on conference %2" ).arg( incomingEvent->eventType() ).arg( event.guid.ascii() ) ); + } + dumpConferenceEvent( event ); + + return true; + } + return false; +} + +void ConferenceTask::slotReceiveUserDetails( const GroupWise::ContactDetails & details ) +{ + client()->debug( "ConferenceTask::slotReceiveUserDetails()" ); + + // dequeue any events which are deliverable now we have these details + QValueListIterator< ConferenceEvent > end = m_pendingEvents.end(); + QValueListIterator< ConferenceEvent > it = m_pendingEvents.begin(); + while ( it != end ) + { + QValueListIterator< ConferenceEvent > current = it; + ++it; + // if the details relate to event, try again to handle it + if ( details.dn == (*current).user ) + { + client()->debug( QString( " - got details for event involving %1" ).arg( (*current).user ) ); + switch ( (*current).type ) + { + case GroupWise::ConferenceJoined: + client()->debug( "ConferenceJoined" ); + emit joined( *current ); + break; + case GroupWise::ReceiveMessage: + client()->debug( "ReceiveMessage" ); + emit message( *current ); + break; + case GroupWise::ConferenceInvite: + client()->debug( "ConferenceInvite" ); + emit invited( *current ); + break; + case GroupWise::ConferenceInviteNotify: + client()->debug( "ConferenceInviteNotify" ); + emit otherInvited( *current ); + break; + default: + client()->debug( "Queued an event while waiting for more data, but didn't write a handler for the dequeue!" ); + } + m_pendingEvents.remove( current ); + client()->debug( QString( "Event handled - now %1 pending events" ).arg + ( (uint)m_pendingEvents.count() ) ); + } + } +} + + +bool ConferenceTask::queueWhileAwaitingData( const ConferenceEvent & event ) +{ + if ( client()->userDetailsManager()->known( event.user ) ) + { + client()->debug( "ConferenceTask::queueWhileAwaitingData() - source is known!" ); + return false; + } + else + { + client()->debug( QString( "ConferenceTask::queueWhileAwaitingData() - queueing event involving %1" ).arg( event.user ) ); + client()->userDetailsManager()->requestDetails( event.user ); + m_pendingEvents.append( event ); + return true; + } +} + +#include "conferencetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/conferencetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/conferencetask.h new file mode 100644 index 00000000..42f4fc2b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/conferencetask.h @@ -0,0 +1,74 @@ +/* + Kopete Groupwise Protocol + conferencetask.h - Event Handling task responsible for all conference related events + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CONFERENCETASK_H +#define CONFERENCETASK_H + +#include "gwerror.h" +#include "eventtask.h" + +/** + * This Task is responsible for handling all conference related events, and signalling them up to @ref GroupWiseAccount + * Implementation note: It would be fit the model more cleanly to have each of these in their own Task, but the amount + * of code they share is quite large, and the differences in the way each event uses it are small + * @author SUSE AG + */ + +using namespace GroupWise; + +class ConferenceTask : public EventTask +{ +Q_OBJECT +public: + ConferenceTask( Task* parent ); + ~ConferenceTask(); + bool take( Transfer * transfer ); +signals: + void typing( const ConferenceEvent & ); + void notTyping( const ConferenceEvent & ); + void joined( const ConferenceEvent & ); + void left( const ConferenceEvent &); + void invited( const ConferenceEvent & ); + void otherInvited( const ConferenceEvent & ); + void invitationDeclined( const ConferenceEvent & ); + void closed( const ConferenceEvent & ); + void message( const ConferenceEvent &); + void autoReply( const ConferenceEvent & ); + // GW7 + void broadcast( const ConferenceEvent &); + void systemBroadcast( const ConferenceEvent &); +protected slots: + void slotReceiveUserDetails( const GroupWise::ContactDetails & ); +protected: + Q_UINT32 readFlags( QDataStream & din ); + QString readMessage( QDataStream & din ); + /** + * Checks to see if we need more data from the client before we can propagate this event + * and queues the event if so + * @return whether the event was queued pending more data + */ + bool queueWhileAwaitingData( const ConferenceEvent & event ); + void dumpConferenceEvent( ConferenceEvent & evt ); +private: + // A list of events which are waiting for more data from the server before they can be exposed to the client + QValueList< ConferenceEvent > m_pendingEvents; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/connectiontask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/connectiontask.cpp new file mode 100644 index 00000000..3d041208 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/connectiontask.cpp @@ -0,0 +1,55 @@ +/* + Kopete Groupwise Protocol + connectiontask.cpp - Event Handling task responsible for all connection related events + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ +#include "client.h" + +#include "connectiontask.h" + +ConnectionTask::ConnectionTask(Task* parent): EventTask(parent) +{ + registerEvent( GroupWise::UserDisconnect ); + registerEvent( GroupWise::ServerDisconnect ); +} + + +ConnectionTask::~ConnectionTask() +{ +} + +bool ConnectionTask::take( Transfer * transfer ) +{ + EventTransfer * incomingEvent; + if ( forMe( transfer, incomingEvent ) ) + { + client()->debug( "Got a connection event:" ); + switch ( incomingEvent->eventType() ) + { + case GroupWise::UserDisconnect: + emit connectedElsewhere(); + break; + case GroupWise::ServerDisconnect: + emit serverDisconnect(); + break; + } + return true; + } + return false; +} + +#include "connectiontask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/connectiontask.h b/kopete/protocols/groupwise/libgroupwise/tasks/connectiontask.h new file mode 100644 index 00000000..95df34f9 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/connectiontask.h @@ -0,0 +1,43 @@ +/* + Kopete Groupwise Protocol + connectiontask.h - Event Handling task responsible for all connection related events + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CONNECTIONTASK_H +#define CONNECTIONTASK_H + +#include "eventtask.h" + +/** +This task monitors connection related events, currently 'connected elsewhere' disconnects and server disconnect notification. + +@author Kopete Developers +*/ +class ConnectionTask : public EventTask +{ +Q_OBJECT +public: + ConnectionTask(Task* parent); + ~ConnectionTask(); + bool take( Transfer * transfer ); +signals: + void connectedElsewhere(); + void serverDisconnect(); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createconferencetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/createconferencetask.cpp new file mode 100644 index 00000000..8be16888 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createconferencetask.cpp @@ -0,0 +1,85 @@ +/* + Kopete Groupwise Protocol + createconferencetask.cpp - Request task that creates conferences on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "response.h" + + +#include "createconferencetask.h" + +CreateConferenceTask::CreateConferenceTask(Task* parent): RequestTask(parent), m_confId( 0 ), m_guid( BLANK_GUID ) +{ + +} + +CreateConferenceTask::~CreateConferenceTask() +{ +} + +void CreateConferenceTask::conference( const int confId, const QStringList &participants ) +{ + m_confId = confId; + Field::FieldList lst, tmp; + // list containing blank GUID + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, m_guid ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + // series of participants (may be empty ) + QValueListConstIterator<QString> end = participants.end(); + for ( QValueListConstIterator<QString> it = participants.begin(); it != end; ++it ) + lst.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_DN, *it ) ); + lst.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_DN, client()->userDN() ) ); + createTransfer( "createconf", lst ); +} + +bool CreateConferenceTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + + // if the createconf was successful, read the GUID and store it + Field::FieldList responseFields = response->fields(); + if ( response->resultCode() == GroupWise::None ) + { + Field::MultiField * listField = responseFields.findMultiField( NM_A_FA_CONVERSATION ); + Field::FieldList guidList = listField->fields(); + Field::SingleField * guidField = guidList.findSingleField( NM_A_SZ_OBJECT_ID ); + m_guid = guidField->value().toString(); + setSuccess(); + } + else + setError( response->resultCode() ); + return true; + +} + +GroupWise::ConferenceGuid CreateConferenceTask::conferenceGUID() const +{ + return m_guid; +} + +int CreateConferenceTask::clientConfId() const +{ + return m_confId; +} + +#include "createconferencetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createconferencetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/createconferencetask.h new file mode 100644 index 00000000..48d5702e --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createconferencetask.h @@ -0,0 +1,54 @@ +/* + Kopete Groupwise Protocol + createconferencetask.h - Request task that creates conferences on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CREATECONFERENCETASK_H +#define CREATECONFERENCETASK_H + +#include "requesttask.h" + +/** +This task is responsible for creating a conference at the server, and confirming that the server allowed the conference to be created. + +@author SUSE AG +*/ +class CreateConferenceTask : public RequestTask +{ +Q_OBJECT +public: + CreateConferenceTask(Task* parent); + ~CreateConferenceTask(); + /** + * Set up a create conference request + * @param confId The client-unique conference Id. + * @param participants A list of Novell DNs of the people taking part in the conference. + */ + void conference( const int confId, const QStringList &participants ); + bool take( Transfer * transfer ); + int clientConfId() const; + GroupWise::ConferenceGuid conferenceGUID() const; + +signals: + void created( const GroupWise::ConferenceGuid & guid ); +private: + int m_confId; // the conference id given us before making the request + ConferenceGuid m_guid; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createcontactinstancetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/createcontactinstancetask.cpp new file mode 100644 index 00000000..832b5900 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createcontactinstancetask.cpp @@ -0,0 +1,97 @@ +/* + Kopete Groupwise Protocol + createcontactinstancetask.h - Request Task that creates an instance of a contact on the server side contact list + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ +#include "client.h" + +#include "createcontactinstancetask.h" + +CreateContactInstanceTask::CreateContactInstanceTask(Task* parent) : NeedFolderTask(parent) +{ + // make the client tell the client app (Kopete) when we receive a contact + connect( this, SIGNAL( gotContactAdded( const ContactItem & ) ), client(), SIGNAL( contactReceived( const ContactItem & ) ) ); +} + +CreateContactInstanceTask::~CreateContactInstanceTask() +{ +} + +void CreateContactInstanceTask::contactFromUserId( const QString & userId, const QString & displayName, const int parentFolder ) +{ + contact( new Field::SingleField( NM_A_SZ_USERID, 0, NMFIELD_TYPE_UTF8, userId ), displayName, parentFolder ); +} + +void CreateContactInstanceTask::contactFromUserIdAndFolder( const QString & userId, const QString & displayName, const int folderSequence, const QString & folderDisplayName ) +{ + // record the user details + m_userId = userId; + m_displayName = displayName; + // record the folder details + m_folderSequence = folderSequence; + m_folderDisplayName = folderDisplayName; +} + +void CreateContactInstanceTask::contactFromDN( const QString & dn, const QString & displayName, const int parentFolder ) +{ + contact( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, dn ), displayName, parentFolder ); +} + +void CreateContactInstanceTask::contactFromDNAndFolder( const QString & dn, const QString & displayName, const int folderSequence, const QString & folderDisplayName ) +{ + // record the user details + m_dn = dn; + m_displayName = displayName; + // record the folder details + m_folderSequence = folderSequence; + m_folderDisplayName = folderDisplayName; +} + +void CreateContactInstanceTask::contact( Field::SingleField * id, const QString & displayName, const int parentFolder ) +{ + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, QString::number( parentFolder ) ) ); + // this is either a user Id or a DN + lst.append( id ); + if ( displayName.isEmpty() ) // fallback so that the contact is created + lst.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, m_dn ) ); + else + lst.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, displayName ) ); + createTransfer( "createcontact", lst ); +} + +void CreateContactInstanceTask::onGo() +{ + // are we creating a folder first or can we just proceed as normal? + if ( m_folderDisplayName.isEmpty() ) + RequestTask::onGo(); + else // create the folder, when the folder has been created, onFolderCreated gets called and creates the contact + createFolder(); +} + +void CreateContactInstanceTask::onFolderCreated() +{ + // now the folder exists, perform the requested type of contact instance creation + if ( m_userId.isEmpty() ) + contact( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, m_dn ), m_displayName, m_folderId ); + else + contact( new Field::SingleField( NM_A_SZ_USERID, 0, NMFIELD_TYPE_UTF8, m_userId ), m_displayName, m_folderId ); + // send the transfer immediately + RequestTask::onGo(); +} + +#include "createcontactinstancetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createcontactinstancetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/createcontactinstancetask.h new file mode 100644 index 00000000..d6be5933 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createcontactinstancetask.h @@ -0,0 +1,54 @@ +/* + Kopete Groupwise Protocol + createcontactinstancetask.h - Request Task that creates an instance of a contact on the server side contact list + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CreateContactInstanceTask_H +#define CreateContactInstanceTask_H + +#include "needfoldertask.h" + +/** +Creates a contact on the server. The response to this action is handled by its parent + +@author SUSE AG +*/ +class CreateContactInstanceTask : public NeedFolderTask +{ +Q_OBJECT +public: + CreateContactInstanceTask(Task* parent); + ~CreateContactInstanceTask(); + /** + * Sets up the request message. + */ + void contactFromUserId( const QString & userId, const QString & displayName, const int parentFolder ); + void contactFromDN( const QString & dn, const QString & displayName, const int parentFolder ); + void contactFromUserIdAndFolder( const QString & userId, const QString & displayName, const int folderSequence, const QString & folderDisplayName ); + void contactFromDNAndFolder( const QString & dn, const QString & displayName, const int folderSequence, const QString & folderDisplayName ); + void onGo(); +protected: + void contact( Field::SingleField * id, const QString & displayName, const int parentFolder ); + void onFolderCreated(); +private: + QString m_userId; + QString m_dn; + QString m_displayName; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createcontacttask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/createcontacttask.cpp new file mode 100644 index 00000000..aac16042 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createcontacttask.cpp @@ -0,0 +1,144 @@ +/* + Kopete Groupwise Protocol + createcontacttask.cpp - high level task responsible for creating both a contact and any folders it belongs to locally, on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "createfoldertask.h" +#include "createcontactinstancetask.h" + +#include "createcontacttask.h" + +CreateContactTask::CreateContactTask(Task* parent): Task(parent) +{ +} + +CreateContactTask::~CreateContactTask() +{ +} + +QString CreateContactTask::userId() +{ + return m_userId; +} + +QString CreateContactTask::dn() +{ + return m_dn; +} + +QString CreateContactTask::displayName() +{ + return m_displayName; +} + +bool CreateContactTask::take( Transfer * transfer ) +{ + Q_UNUSED( transfer ); + return false; +} + +void CreateContactTask::contactFromUserId( const QString & userId, const QString & displayName, const int firstSeqNo, const QValueList< FolderItem > folders, bool topLevel ) +{ + m_userId = userId; + m_displayName = displayName; + m_firstSequenceNumber = firstSeqNo; + m_folders = folders; + m_topLevel = topLevel; +} + +void CreateContactTask::onGo() +{ + client()->debug( "CreateContactTask::onGo() - Welcome to the Create Contact Task Show!"); + QValueList<FolderItem>::ConstIterator it = m_folders.begin(); + const QValueList<FolderItem>::ConstIterator end = m_folders.end(); + + // create contacts on the server + for ( ; it != end; ++it ) + { + client()->debug( QString( " - contact is in folder %1 with id %2" ).arg( (*it).name ).arg( (*it).id ) ); + CreateContactInstanceTask * ccit = new CreateContactInstanceTask( client()->rootTask() ); + // the add contact action may cause other contacts' sequence numbers to change + // CreateContactInstanceTask signals these changes, so we propagate the signal via the Client, to the GroupWiseAccount + // This updates our local versions of those contacts using the same mechanism by which they are updated at login. + connect( ccit, SIGNAL( gotContactAdded( const ContactItem & ) ), SLOT( slotContactAdded( const ContactItem & ) ) ); + connect( ccit, SIGNAL( finished() ), SLOT( slotCheckContactInstanceCreated() ) ); + if ( (*it).id == 0 ) // caller asserts that this isn't on the server... + { + ccit->contactFromDNAndFolder( m_userId, m_displayName, m_firstSequenceNumber++, ( *it ).name ); + } + else + ccit->contactFromDN( m_userId, m_displayName, (*it).id ); + + ccit->go( true ); + } + + if ( m_topLevel ) + { + client()->debug( " - contact is in top level folder " ); + CreateContactInstanceTask * ccit = new CreateContactInstanceTask( client()->rootTask() ); + connect( ccit, SIGNAL( gotContactAdded( const ContactItem & ) ), SLOT( slotContactAdded( const ContactItem & ) ) ); + connect( ccit, SIGNAL( finished() ), SLOT( slotCheckContactInstanceCreated() ) ); + ccit->contactFromDN( m_userId, m_displayName, 0 ); + ccit->go( true ); + } + client()->debug( "CreateContactTask::onGo() - DONE" ); +} + +void CreateContactTask::slotContactAdded( const ContactItem & addedContact ) +{ + client()->debug( "CreateContactTask::slotContactAdded()" ); + // as each contact instance has been added on the server, + // remove the folderitem it belongs in. + // once the list is empty, we have been successful + + if ( addedContact.displayName != m_displayName ) + { + client()->debug( " - addedContact is not the one we were trying to add, ignoring it ( Account will update it )" ); + return; + } + client()->debug( QString( "CreateContactTask::slotContactAdded() - Contact Instance %1 was created on the server, with objectId %2 in folder %3" ).arg + ( addedContact.displayName ).arg( addedContact.id ).arg( addedContact.parentId ) ); + + if ( m_dn.isEmpty() ) + m_dn = addedContact.dn; + + + if ( !m_folders.isEmpty() ) + m_folders.pop_back(); + + // clear the topLevel flag once the corresponding server side entry has been successfully created + if ( addedContact.parentId == 0 ) + m_topLevel = false; + + if ( m_folders.isEmpty() && !m_topLevel ) + { + client()->debug( "CreateContactTask::slotContactAdded() - All contacts were created on the server, we're finished!" ); + setSuccess(); + } +} +void CreateContactTask::slotCheckContactInstanceCreated() +{ + CreateContactInstanceTask * ccit = ( CreateContactInstanceTask * )sender(); + if ( !ccit->success() ) + { + setError( ccit->statusCode(), ccit->statusString() ); + } +} + +#include "createcontacttask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createcontacttask.h b/kopete/protocols/groupwise/libgroupwise/tasks/createcontacttask.h new file mode 100644 index 00000000..a9e4ab06 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createcontacttask.h @@ -0,0 +1,88 @@ +/* + Kopete Groupwise Protocol + createcontacttask.cpp - high level task responsible for creating both a contact and any folders it belongs to locally, on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CREATECONTACTTASK_H +#define CREATECONTACTTASK_H + +#include <qvaluelist.h> + +#include "gwerror.h" + +#include "task.h" + +using namespace GroupWise; + +/** + Creates a contact on the server, as well as any folders that do not exist on the server, and add the contact to those folders. + This is a meta-task to suit Kopete. If you maintain your own copy of the server side contact list and follow the server's + contact semantics (contact instances rather than contacts in the contact list), you can just use CreateContactInstanceTask. + This task causes the @ref Client to emit folderReceived() and contactReceived() as the task proceeds. Kopete processes these + signals as usual, because it created the contact optimistically, before invoking this task. + + The finished() signal indicates the whole procedure has completed and the sender can be queried for success as usual +@author SUSE AG +*/ +class CreateContactTask : public Task +{ +Q_OBJECT +public: + CreateContactTask(Task* parent); + ~CreateContactTask(); + /** + * Get the userId of the contact just created + */ + QString userId(); + /** + * Get the DN of the contact just created + */ + QString dn(); + QString displayName(); + + /** + * Sets up the task. + * @param userId the user Id of the contact to create + * @param displayName the display name we should give to this contact + * @param firstSeqNo Used to create the folders - the first unused folder sequence number we know of + * @param folders A list of folders that the contact should belong to - any folders that do not exist on the server should have a objectId of 0, and will be created + * @param topLevel is the folder also in the top level folder? + */ + void contactFromUserId( const QString & userId, const QString & displayName, const int firstSeqNo, const QValueList< FolderItem > folders, bool topLevel ); + //void contactFromDN( const QString & dn, const QString & displayName, const int parentFolder ); + /** + * This task doesn't do any I/O itself, so this take prints an error and returns false; + */ + bool take( Transfer * ); + /** + * Starts off the whole process + */ + void onGo(); +protected slots: + void slotContactAdded( const ContactItem & ); + void slotCheckContactInstanceCreated(); +private: + int m_firstSequenceNumber; + QString m_userId; + QString m_dn; + QString m_displayName; + QValueList< FolderItem > m_folders; + bool m_topLevel; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createfoldertask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/createfoldertask.cpp new file mode 100644 index 00000000..c7e9933b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createfoldertask.cpp @@ -0,0 +1,41 @@ +/* + Kopete Groupwise Protocol + createfoldertask.h - Request Task for creating a single folder on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "createfoldertask.h" + +CreateFolderTask::CreateFolderTask(Task* parent): ModifyContactListTask(parent) +{ +} + + +CreateFolderTask::~CreateFolderTask() +{ +} + +void CreateFolderTask::folder( const int parentId, const int sequence, const QString & displayName ) +{ + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, QString::number( parentId ) ) ); + lst.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, displayName ) ); + lst.append( new Field::SingleField( NM_A_SZ_SEQUENCE_NUMBER, 0, NMFIELD_TYPE_UTF8, QString::number( sequence ) ) ); + createTransfer( "createfolder", lst ); +} + +#include "createfoldertask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/createfoldertask.h b/kopete/protocols/groupwise/libgroupwise/tasks/createfoldertask.h new file mode 100644 index 00000000..f3c6ebb9 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/createfoldertask.h @@ -0,0 +1,40 @@ +/* + Kopete Groupwise Protocol + createfoldertask.h - Request Task for creating a single folder on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CREATEFOLDERTASK_H +#define CREATEFOLDERTASK_H + +#include "modifycontactlisttask.h" + +/** +Creates a folder on the server + +@author SUSE AG +*/ +class CreateFolderTask : public ModifyContactListTask +{ +Q_OBJECT +public: + CreateFolderTask(Task* parent); + ~CreateFolderTask(); + void folder( const int parentId, const int sequence, const QString & displayName ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/deleteitemtask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/deleteitemtask.cpp new file mode 100644 index 00000000..89480d10 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/deleteitemtask.cpp @@ -0,0 +1,46 @@ +/* + Kopete Groupwise Protocol + deleteitemtask.cpp - Delete a contact or folder on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "deleteitemtask.h" + +DeleteItemTask::DeleteItemTask(Task* parent): ModifyContactListTask(parent) +{ +} + + +DeleteItemTask::~DeleteItemTask() +{ +} + +void DeleteItemTask::item( const int parentFolder, const int objectId ) +{ + if ( objectId == 0 ) + { + setError( 1, "Can't delete the root folder" ); + return; + } + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, QString::number( parentFolder ) ) ); + // this is either a user Id or a DN + lst.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, QString::number( objectId ) ) ); + createTransfer( "deletecontact", lst ); +} + +#include "deleteitemtask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/deleteitemtask.h b/kopete/protocols/groupwise/libgroupwise/tasks/deleteitemtask.h new file mode 100644 index 00000000..f249c2f5 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/deleteitemtask.h @@ -0,0 +1,38 @@ +/* + Kopete Groupwise Protocol + deleteitemtask.h - Delete a contact or folder on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef DELETEITEMTASK_H +#define DELETEITEMTASK_H + +#include "modifycontactlisttask.h" + +/** +@author SUSE AG +*/ +class DeleteItemTask : public ModifyContactListTask +{ +Q_OBJECT +public: + DeleteItemTask(Task* parent); + ~DeleteItemTask(); + void item( const int parentFolder, const int objectId ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/eventtask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/eventtask.cpp new file mode 100644 index 00000000..c6bd2d85 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/eventtask.cpp @@ -0,0 +1,48 @@ +/* + Kopete Groupwise Protocol + eventtask.cpp - Ancestor of all Event Handling tasks + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "gwfield.h" +#include "eventtask.h" + +EventTask::EventTask( Task * parent ) +: Task( parent ) +{ +} + +void EventTask::registerEvent( GroupWise::Event e ) +{ + m_eventCodes.append( e ); +} + +bool EventTask::forMe( Transfer * transfer, EventTransfer*& event ) const +{ + // see if we can down-cast transfer to an EventTransfer + /*EventTransfer * */ + event = dynamic_cast<EventTransfer *>(transfer); + if ( event ) + { + // see if we are supposed to handle this kind of event + // consider speeding this up by having 1 handler per event + return ( m_eventCodes.find( event->eventType() ) != m_eventCodes.end() ); + } + return false; +} + +#include "eventtask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/eventtask.h b/kopete/protocols/groupwise/libgroupwise/tasks/eventtask.h new file mode 100644 index 00000000..50b84ac5 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/eventtask.h @@ -0,0 +1,43 @@ +/* + Kopete Groupwise Protocol + eventtask.h - Ancestor of all Event Handling tasks + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef GW_EVENTTASK_H +#define GW_EVENTTASK_H + +#include <qvaluelist.h> + +#include "eventtransfer.h" +#include "task.h" + +class Transfer; + +class EventTask : public Task +{ +Q_OBJECT + public: + EventTask( Task *parent ); + protected: + bool forMe( Transfer * transfer, EventTransfer *& event ) const; + void registerEvent( GroupWise::Event e ); + private: + QValueList<int> m_eventCodes; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/getchatsearchresultstask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/getchatsearchresultstask.cpp new file mode 100644 index 00000000..fe1d61f9 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/getchatsearchresultstask.cpp @@ -0,0 +1,122 @@ +/* + Kopete Groupwise Protocol + getchatsearchresultstask.cpp - Poll the server to see if it has processed our search yet. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include <kdebug.h> + +#include "gwfield.h" +#include "response.h" + +#include "logintask.h" + +#include "getchatsearchresultstask.h" + +using namespace GroupWise; + +GetChatSearchResultsTask::GetChatSearchResultsTask(Task* parent): RequestTask(parent) +{ +} + + +GetChatSearchResultsTask::~GetChatSearchResultsTask() +{ +} + +void GetChatSearchResultsTask::poll( int queryHandle ) +{ + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_UD_OBJECT_ID, 0, NMFIELD_TYPE_UDWORD, queryHandle ) ); + lst.append( new Field::SingleField( NM_A_UD_QUERY_COUNT, 0, NMFIELD_TYPE_UDWORD, 10 ) ); + createTransfer( "getchatsearchresults", lst ); +} + +bool GetChatSearchResultsTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + setError( response->resultCode() ); + return true; + } + + // look for the status code + Field::FieldList responseFields = response->fields(); + Field::SingleField * sf = responseFields.findSingleField( NM_A_UW_STATUS ); + m_queryStatus = (SearchResultCode)sf->value().toInt(); + + Field::MultiField * resultsArray = responseFields.findMultiField( NM_A_FA_RESULTS ); + if ( !resultsArray ) + { + setError( Protocol ); + return true; + } + Field::FieldList matches = resultsArray->fields(); + const Field::FieldListIterator end = matches.end(); + for ( Field::FieldListIterator it = matches.find( NM_A_FA_CHAT ); + it != end; + it = matches.find( ++it, NM_A_FA_CHAT ) ) + { + Field::MultiField * mf = static_cast<Field::MultiField *>( *it ); + Field::FieldList chat = mf->fields(); + GroupWise::ChatroomSearchResult cd = extractChatDetails( chat ); + m_results.append( cd ); + } + + if ( m_queryStatus != DataRetrieved ) + setError( m_queryStatus ); + else + { + kdDebug ( GROUPWISE_DEBUG_GLOBAL ) << " we won!" << endl; + setSuccess( m_queryStatus ); + } + return true; +} + +QValueList< GroupWise::ChatroomSearchResult > GetChatSearchResultsTask::results() +{ + return m_results; +} + +int GetChatSearchResultsTask::queryStatus() +{ + return m_queryStatus; +} + +GroupWise::ChatroomSearchResult GetChatSearchResultsTask::extractChatDetails( Field::FieldList & fields ) +{ + ChatroomSearchResult csr; + csr.participants = 0; + // read the supplied fields, set metadata and status. + Field::SingleField * sf; + if ( ( sf = fields.findSingleField ( NM_A_DISPLAY_NAME ) ) ) + csr.name = sf->value().toString(); + if ( ( sf = fields.findSingleField ( NM_A_CHAT_OWNER_DN ) ) ) + csr.ownerDN = sf->value().toString().lower(); // HACK: lowercased DN + if ( ( sf = fields.findSingleField ( NM_A_UD_PARTICIPANTS ) ) ) + csr.participants = sf->value().toInt(); + + kdDebug( GROUPWISE_DEBUG_GLOBAL ) << csr.name << ", " << csr.ownerDN << ", " << csr.participants << endl; + return csr; +} + +#include "getchatsearchresultstask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/getchatsearchresultstask.h b/kopete/protocols/groupwise/libgroupwise/tasks/getchatsearchresultstask.h new file mode 100644 index 00000000..31db19ed --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/getchatsearchresultstask.h @@ -0,0 +1,52 @@ +/* + Kopete Groupwise Protocol + getchatsearchresultstask.h - Poll the server once to see if it has processed our chatroom search yet. + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef CHATSEARCHRESULTSTASK_H +#define CHATSEARCHRESULTSTASK_H + +#include <qvaluelist.h> + +#include "gwchatrooms.h" + +#include "requesttask.h" + +/** +Search results are polled on the server, using the search handle returned by the server with the original query. This is a single poll request, which if successful, will retrieve the results. Otherwise, it will set a status code, so the SearchChatTask can decide whether to poll again. + +@author SUSE Linux Products GmbH + */ +class GetChatSearchResultsTask : public RequestTask +{ + Q_OBJECT + public: + enum SearchResultCode { Completed=2, Cancelled=4, Error=5, GettingData=8, DataRetrieved=9 }; + GetChatSearchResultsTask(Task* parent); + ~GetChatSearchResultsTask(); + void poll( int queryHandle); + bool take( Transfer * transfer ); + int queryStatus(); + QValueList< GroupWise::ChatroomSearchResult > results(); + private: + GroupWise::ChatroomSearchResult extractChatDetails( Field::FieldList & fields ); + SearchResultCode m_queryStatus; + QValueList< GroupWise::ChatroomSearchResult > m_results; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/getdetailstask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/getdetailstask.cpp new file mode 100644 index 00000000..0b37efb4 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/getdetailstask.cpp @@ -0,0 +1,136 @@ +/* + Kopete Groupwise Protocol + getdetailstask.cpp - fetch a contact's details from the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "response.h" +#include "userdetailsmanager.h" + +#include "getdetailstask.h" + +using namespace GroupWise; + +GetDetailsTask::GetDetailsTask( Task * parent ) + : RequestTask( parent ) +{ +} + + +GetDetailsTask::~GetDetailsTask() +{ +} + +void GetDetailsTask::userDNs( const QStringList & userDNs ) +{ + Field::FieldList lst; + for ( QStringList::ConstIterator it = userDNs.begin(); it != userDNs.end(); ++it ) + { + lst.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, *it ) ); + } + createTransfer( "getdetails", lst ); +} + +bool GetDetailsTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + + Field::FieldList detailsFields = response->fields(); + // parse received details and signal like billio + Field::MultiField * container = 0; + Field::FieldListIterator end = detailsFields.end(); + for ( Field::FieldListIterator it = detailsFields.find( NM_A_FA_RESULTS ); + it != end; + it = detailsFields.find( ++it, NM_A_FA_RESULTS ) ) + { + container = static_cast<Field::MultiField *>( *it ); + ContactDetails cd = extractUserDetails( container ); + emit gotContactUserDetails( cd ); + } + + return true; +} + +ContactDetails GetDetailsTask::extractUserDetails(Field::MultiField * details ) +{ + ContactDetails cd; + cd.status = GroupWise::Invalid; + cd.archive = false; + Field::FieldList fields = details->fields(); + // TODO: not sure what this means, ask Mike + Field::SingleField * sf; + if ( ( sf = fields.findSingleField ( NM_A_SZ_AUTH_ATTRIBUTE ) ) ) + cd.authAttribute = sf->value().toString(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_DN ) ) ) + cd.dn =sf->value().toString().lower(); // HACK: lowercased DN + if ( ( sf = fields.findSingleField ( "CN" ) ) ) + cd.cn = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Given Name" ) ) ) + cd.givenName = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Surname" ) ) ) + cd.surname = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "nnmArchive" ) ) ) + cd.archive = ( sf->value().toInt() == 1 ); + if ( ( sf = fields.findSingleField ( "Full Name" ) ) ) + cd.fullName = sf->value().toString(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_STATUS ) ) ) + cd.status = sf->value().toInt(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_MESSAGE_BODY ) ) ) + cd.awayMessage = sf->value().toString(); + Field::MultiField * mf; + QMap< QString, QString > propMap; + if ( ( mf = fields.findMultiField ( NM_A_FA_INFO_DISPLAY_ARRAY ) ) ) + { + Field::FieldList fl = mf->fields(); + const Field::FieldListIterator end = fl.end(); + for ( Field::FieldListIterator it = fl.begin(); it != end; ++it ) + { + Field::SingleField * propField = dynamic_cast<Field::SingleField *>( *it ); + if ( propField ) { + QString propName = propField->tag(); + QString propValue = propField->value().toString(); + propMap.insert( propName, propValue ); + } else { + Field::MultiField * mf2; + if ( ( mf2 = dynamic_cast<Field::MultiField *>( *it ) ) ) { + Field::FieldList fl2 = mf2->fields(); + const Field::FieldListIterator end = fl2.end(); + for ( Field::FieldListIterator it2 = fl2.begin(); it2 != end; ++it2 ) + { + propField = dynamic_cast<Field::SingleField *>( *it2 ); + if ( propField ) { + QString propName = propField->tag(); + QString propValue = propField->value().toString(); + propMap.insert( propName, propValue ); + } + } + } + } + } + } + if ( !propMap.empty() ) + { + cd.properties = propMap; + } + return cd; +} +#include "getdetailstask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/getdetailstask.h b/kopete/protocols/groupwise/libgroupwise/tasks/getdetailstask.h new file mode 100644 index 00000000..d263f50b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/getdetailstask.h @@ -0,0 +1,49 @@ +/* + Kopete Groupwise Protocol + getdetailstask.h - fetch a contact's details from the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef GETDETAILSTASK_H +#define GETDETAILSTASK_H + +#include "gwerror.h" +#include "requesttask.h" + +/** +This task fetches the details for a set of user IDs from the server. Sometimes we get an event that only has a DN, and we need other details before showing the event to the user. + +@author SUSE AG +*/ +using namespace GroupWise; + +class GetDetailsTask : public RequestTask +{ +Q_OBJECT +public: + GetDetailsTask( Task * parent ); + ~GetDetailsTask(); + bool take( Transfer * transfer ); + void userDNs( const QStringList & userDNs ); +signals: + void gotContactUserDetails( const GroupWise::ContactDetails & ); +protected: + GroupWise::ContactDetails extractUserDetails( Field::MultiField * details ); + +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/getstatustask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/getstatustask.cpp new file mode 100644 index 00000000..dde055a6 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/getstatustask.cpp @@ -0,0 +1,72 @@ +/* + Kopete Groupwise Protocol + getstatustask.cpp - fetch a contact's details from the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "response.h" + +#include "getstatustask.h" + +GetStatusTask::GetStatusTask(Task* parent): RequestTask(parent) +{ +} + +GetStatusTask::~GetStatusTask() +{ +} + +void GetStatusTask::userDN( const QString & dn ) +{ + m_userDN = dn; + // set up Transfer + Field::FieldList lst; + // changed from USERID to DN as per Gaim/GWIM + lst.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, m_userDN ) ); + createTransfer( "getstatus", lst ); +} + +bool GetStatusTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + + Field::FieldList responseFields = response->fields(); + responseFields.dump( true ); + // parse received details and signal like billio + Field::SingleField * sf = 0; + Q_UINT16 status; + sf = responseFields.findSingleField( NM_A_SZ_STATUS ); + if ( sf ) + { + // As of Sept 2004 the server always responds with 2 (Available) here, even if the sender is not + // This must be because the sender is not on our contact list but has sent us a message. + // TODO: Check that the change to sending DNs above has fixed this problem. + status = sf->value().toInt(); + // unfortunately getstatus doesn't give us an away message so we pass QString::null here + emit gotStatus( m_userDN, status, QString::null ); + setSuccess(); + } + else + setError(); + return true; +} + +#include "getstatustask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/getstatustask.h b/kopete/protocols/groupwise/libgroupwise/tasks/getstatustask.h new file mode 100644 index 00000000..59422342 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/getstatustask.h @@ -0,0 +1,44 @@ +/* + Kopete Groupwise Protocol + getstatustask.h - fetch a contact's details from the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef GETSTATUSTASK_H +#define GETSTATUSTASK_H + +#include "requesttask.h" + +/** + * Request the status for a specific contact (e.g. one who's not on our contact list) + * @author SUSE AG +*/ +class GetStatusTask : public RequestTask +{ +Q_OBJECT +public: + GetStatusTask(Task* parent); + ~GetStatusTask(); + void userDN( const QString & dn ); + bool take( Transfer * transfer ); +signals: + void gotStatus( const QString & contactId, Q_UINT16 status, const QString & statusText ); +private: + QString m_userDN; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/gwtasklogin.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/gwtasklogin.cpp new file mode 100644 index 00000000..e69de29b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/gwtasklogin.cpp diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/gwtasklogin.h b/kopete/protocols/groupwise/libgroupwise/tasks/gwtasklogin.h new file mode 100644 index 00000000..e69de29b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/gwtasklogin.h diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/joinchattask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/joinchattask.cpp new file mode 100644 index 00000000..4e9e4f57 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/joinchattask.cpp @@ -0,0 +1,131 @@ +/* + Kopete Groupwise Protocol + joinchattask.cpp - Join a Chat on the server, after having been invited. + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "gwerror.h" +#include "client.h" +#include "response.h" +#include "userdetailsmanager.h" + +#include "joinchattask.h" + +JoinChatTask::JoinChatTask(Task* parent): RequestTask(parent) +{ +} + +JoinChatTask::~JoinChatTask() +{ +} + +void JoinChatTask::join( const QString & displayName ) +{ + m_displayName = displayName; + Field::FieldList lst, tmp; + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, displayName ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + createTransfer( "joinchat", lst ); +} + +bool JoinChatTask::take( Transfer * transfer ) +{ + if ( forMe( transfer ) ) + { + client()->debug( "JoinChatTask::take()" ); + Response * response = dynamic_cast<Response *>( transfer ); + Field::FieldList responseFields = response->fields(); + // if the request was successful + if ( response->resultCode() == GroupWise::None ) + { + // extract the list of participants and store them + Field::MultiField * participants = responseFields.findMultiField( NM_A_FA_CONTACT_LIST ); + if ( participants ) + { + Field::SingleField * contact = 0; + Field::FieldList contactList = participants->fields(); + const Field::FieldListIterator end = contactList.end(); + for ( Field::FieldListIterator it = contactList.find( NM_A_SZ_DN ); + it != end; + it = contactList.find( ++it, NM_A_SZ_DN ) ) + { + contact = static_cast<Field::SingleField *>( *it ); + if ( contact ) + { + // HACK: lowercased DN + QString dn = contact->value().toString().lower(); + m_participants.append( dn ); + // need to ask for details for these contacts + } + } + } + else + setError( GroupWise::Protocol ); + + // now, extract the list of pending invites and store them + Field::MultiField * invitees = responseFields.findMultiField( NM_A_FA_RESULTS ); + if ( invitees ) + { + Field::SingleField * contact = 0; + Field::FieldList contactList = invitees->fields(); + const Field::FieldListIterator end = contactList.end(); + for ( Field::FieldListIterator it = contactList.find( NM_A_SZ_DN ); + it != end; + it = contactList.find( ++it, NM_A_SZ_DN ) ) + { + contact = static_cast<Field::SingleField *>( *it ); + if ( contact ) + { + // HACK: lowercased DN + QString dn = contact->value().toString().lower(); + m_invitees.append( dn ); + // need to ask for details for these contacts + if ( !client()->userDetailsManager()->known( dn ) ) + ; // don't request details for chatrooms, there could be too many + } + } + } + else + setError( GroupWise::Protocol ); + + client()->debug( "JoinChatTask::finished()" ); + finished(); + } + else + setError( response->resultCode() ); + return true; + } + else + return false; +} + +QStringList JoinChatTask::participants() const +{ + return m_participants; +} + +QStringList JoinChatTask::invitees() const +{ + return m_invitees; +} + +QString JoinChatTask::displayName() const +{ + return m_displayName; +} + +#include "joinchattask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/joinchattask.h b/kopete/protocols/groupwise/libgroupwise/tasks/joinchattask.h new file mode 100644 index 00000000..a7cc4119 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/joinchattask.h @@ -0,0 +1,52 @@ +/* + Kopete Groupwise Protocol + joinchattask.h - Join a chatroom on the server, after having been invited. + + Copyright (c) 2004 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef JOINCHATTASK_H +#define JOINCHATTASK_H + +#include "requesttask.h" + +using namespace GroupWise; + +/** +Sends Join Conference messages when the user accepts an invitation + +@author SUSE Linux Products GmbH + */ + +class JoinChatTask : public RequestTask +{ + Q_OBJECT + public: + JoinChatTask(Task* parent); + ~JoinChatTask(); + void join( const QString & displayName ); + bool take( Transfer * transfer ); + QStringList participants() const; + QStringList invitees() const; + QString displayName() const; + private: + ConferenceGuid m_displayName; + QStringList m_participants; + QStringList m_invitees; + QStringList m_unknowns; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/joinconferencetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/joinconferencetask.cpp new file mode 100644 index 00000000..c2cf0f02 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/joinconferencetask.cpp @@ -0,0 +1,175 @@ +/* + Kopete Groupwise Protocol + joinconferencetask.cpp - Join a conference on the server, after having been invited. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "gwerror.h" +#include "client.h" +#include "response.h" +#include "userdetailsmanager.h" + +#include "joinconferencetask.h" + +JoinConferenceTask::JoinConferenceTask(Task* parent): RequestTask(parent) +{ +} + +JoinConferenceTask::~JoinConferenceTask() +{ +} + +void JoinConferenceTask::join( const GroupWise::ConferenceGuid & guid ) +{ + m_guid = guid; + Field::FieldList lst, tmp; + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, guid ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + createTransfer( "joinconf", lst ); +} + +bool JoinConferenceTask::take( Transfer * transfer ) +{ + if ( forMe( transfer ) ) + { + client()->debug( "JoinConferenceTask::take()" ); + Response * response = dynamic_cast<Response *>( transfer ); + Field::FieldList responseFields = response->fields(); + // if the request was successful + if ( response->resultCode() == GroupWise::None ) + { + // extract the list of participants and store them + Field::MultiField * participants = responseFields.findMultiField( NM_A_FA_CONTACT_LIST ); + if ( participants ) + { + Field::SingleField * contact = 0; + Field::FieldList contactList = participants->fields(); + const Field::FieldListIterator end = contactList.end(); + for ( Field::FieldListIterator it = contactList.find( NM_A_SZ_DN ); + it != end; + it = contactList.find( ++it, NM_A_SZ_DN ) ) + { + contact = static_cast<Field::SingleField *>( *it ); + if ( contact ) + { + // HACK: lowercased DN + QString dn = contact->value().toString().lower(); + m_participants.append( dn ); + // need to ask for details for these contacts + if ( !client()->userDetailsManager()->known( dn ) ) + m_unknowns.append( dn ); + } + } + } + else + setError( GroupWise::Protocol ); + + // now, extract the list of pending invites and store them + Field::MultiField * invitees = responseFields.findMultiField( NM_A_FA_RESULTS ); + if ( invitees ) + { + Field::SingleField * contact = 0; + Field::FieldList contactList = invitees->fields(); + const Field::FieldListIterator end = contactList.end(); + for ( Field::FieldListIterator it = contactList.find( NM_A_SZ_DN ); + it != end; + it = contactList.find( ++it, NM_A_SZ_DN ) ) + { + contact = static_cast<Field::SingleField *>( *it ); + if ( contact ) + { + // HACK: lowercased DN + QString dn = contact->value().toString().lower(); + m_invitees.append( dn ); + // need to ask for details for these contacts + if ( !client()->userDetailsManager()->known( dn ) ) + m_unknowns.append( dn ); + } + } + } + else + setError( GroupWise::Protocol ); + + if ( m_unknowns.empty() ) // ready to chat + { + client()->debug( "JoinConferenceTask::finished()" ); + finished(); + } + else // need to get some more details first + { + client()->debug( "JoinConferenceTask::slotReceiveUserDetails(), requesting details" ); + connect( client()->userDetailsManager(), + SIGNAL( gotContactDetails( const GroupWise::ContactDetails & ) ), + SLOT( slotReceiveUserDetails( const GroupWise::ContactDetails & ) ) ); + client()->userDetailsManager()->requestDetails( m_unknowns ); + } + } + else + setError( response->resultCode() ); + return true; + } + else + return false; +} + +void JoinConferenceTask::slotReceiveUserDetails( const ContactDetails & details ) +{ + client()->debug( QString( "JoinConferenceTask::slotReceiveUserDetails() - got %1" ).arg( details.dn ) ); + QStringList::Iterator it = m_unknowns.begin(); + QStringList::Iterator end = m_unknowns.end(); + while( it != end ) + { + QString current = *it; + ++it; + client()->debug( QString( " - can we remove %1?" ).arg(current ) ); + if ( current == details.dn ) + { + client()->debug( " - it's gone!" ); + m_unknowns.remove( current ); + break; + } + } + client()->debug( QString( " - now %1 unknowns").arg( m_unknowns.count() ) ); + if ( m_unknowns.empty() ) + { + client()->debug( " - finished()" ); + finished(); + } +// would be better to count the number of received details and listen to the getdetails task's error signal. +// else +// { +// client()->debug( " - ERROR - we requested details for the list of chat participants/invitees, but the server did not send us all the details! - setting finished() anyway, so the chat can take place." ); +// finished(); +// } +} + +QStringList JoinConferenceTask::participants() const +{ + return m_participants; +} + +QStringList JoinConferenceTask::invitees() const +{ + return m_invitees; +} + +GroupWise::ConferenceGuid JoinConferenceTask::guid() const +{ + return m_guid; +} + +#include "joinconferencetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/joinconferencetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/joinconferencetask.h new file mode 100644 index 00000000..68316147 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/joinconferencetask.h @@ -0,0 +1,54 @@ +/* + Kopete Groupwise Protocol + joinconferencetask.h - Join a conference on the server, after having been invited. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef JOINCONFERENCETASK_H +#define JOINCONFERENCETASK_H + +#include "requesttask.h" + +using namespace GroupWise; + +/** +Sends Join Conference messages when the user accepts an invitation + +@author SUSE AG +*/ + +class JoinConferenceTask : public RequestTask +{ +Q_OBJECT +public: + JoinConferenceTask(Task* parent); + ~JoinConferenceTask(); + void join( const ConferenceGuid & guid ); + bool take( Transfer * transfer ); + QStringList participants() const; + QStringList invitees() const; + ConferenceGuid guid() const; +public slots: + void slotReceiveUserDetails( const GroupWise::ContactDetails & details ); +private: + ConferenceGuid m_guid; + QStringList m_participants; + QStringList m_invitees; + QStringList m_unknowns; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/keepalivetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/keepalivetask.cpp new file mode 100644 index 00000000..ac84ac2b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/keepalivetask.cpp @@ -0,0 +1,42 @@ +/* + Kopete Groupwise Protocol + keepalivetask.cpp - Send keepalive pings to the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + (c) 2006 Novell, Inc. + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "request.h" +#include "requestfactory.h" +#include "keepalivetask.h" + +KeepAliveTask::KeepAliveTask(Task* parent): RequestTask(parent) +{ +} + + +KeepAliveTask::~KeepAliveTask() +{ +} + +void KeepAliveTask::setup() +{ + Field::FieldList lst; + createTransfer( "ping", lst ); +} + +#include "keepalivetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/keepalivetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/keepalivetask.h new file mode 100644 index 00000000..04f9a352 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/keepalivetask.h @@ -0,0 +1,38 @@ +/* + Kopete Groupwise Protocol + keepalivetask.h - Send keepalive pings to the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef KEEPALIVETASK_H +#define KEEPALIVETASK_H + +#include "requesttask.h" + +/** +@author Kopete Developers +*/ +class KeepAliveTask : public RequestTask +{ +Q_OBJECT +public: + KeepAliveTask(Task* parent); + ~KeepAliveTask(); + void setup(); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/leaveconferencetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/leaveconferencetask.cpp new file mode 100644 index 00000000..d2d58b83 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/leaveconferencetask.cpp @@ -0,0 +1,40 @@ +/* + Kopete Groupwise Protocol + leaveconferencetask.cpp - Tell the server we are leaving a conference + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "leaveconferencetask.h" + +LeaveConferenceTask::LeaveConferenceTask(Task* parent): RequestTask(parent) +{ +} + + +LeaveConferenceTask::~LeaveConferenceTask() +{ +} + +void LeaveConferenceTask::leave( const GroupWise::ConferenceGuid & guid ) +{ + Field::FieldList lst, tmp; + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, guid ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + createTransfer( "leaveconf", lst ); +} + +#include "leaveconferencetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/leaveconferencetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/leaveconferencetask.h new file mode 100644 index 00000000..65ebe540 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/leaveconferencetask.h @@ -0,0 +1,40 @@ +/* + Kopete Groupwise Protocol + leaveconferencetask.h - Tell the server we are leaving a conference + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef LEAVECONFERENCETASK_H +#define LEAVECONFERENCETASK_H + +#include "requesttask.h" + +/** +Tells the server that you are leaving a conference (closed the chatwindow) + +@author SUSE AG +*/ +class LeaveConferenceTask : public RequestTask +{ +Q_OBJECT +public: + LeaveConferenceTask(Task* parent); + ~LeaveConferenceTask(); + void leave( const GroupWise::ConferenceGuid & guid ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/logintask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/logintask.cpp new file mode 100644 index 00000000..1f679a6c --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/logintask.cpp @@ -0,0 +1,360 @@ +/* + Kopete Groupwise Protocol + logintask.cpp - Send our credentials to the server and process the contact list and privacy details that it returns. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "response.h" +#include "privacymanager.h" +#include "userdetailsmanager.h" + +#include "logintask.h" + +LoginTask::LoginTask( Task * parent ) + : RequestTask( parent ) +{ +} + +LoginTask::~LoginTask() +{ +} + +void LoginTask::initialise() +{ + QString command = QString::fromLatin1("login:%1:%2").arg( client()->host() ).arg( client()->port() ); + + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_USERID, 0, NMFIELD_TYPE_UTF8, client()->userId() ) ); + lst.append( new Field::SingleField( NM_A_SZ_CREDENTIALS, 0, NMFIELD_TYPE_UTF8, client()->password() ) ); + lst.append( new Field::SingleField( NM_A_SZ_USER_AGENT, 0, NMFIELD_TYPE_UTF8, client()->userAgent() ) ); + lst.append( new Field::SingleField( NM_A_UD_BUILD, 0, NMFIELD_TYPE_UDWORD, client()->protocolVersion() ) ); + lst.append( new Field::SingleField( NM_A_IP_ADDRESS, 0, NMFIELD_TYPE_UTF8, client()->ipAddress() ) ); + createTransfer( command, lst ); +} + +bool LoginTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + setError( response->resultCode() ); + return true; + } + response->fields().dump( true ); + + // read in myself()'s metadata fields and emit signal + Field::FieldList loginResponseFields = response->fields(); + + ContactDetails cd = extractUserDetails( loginResponseFields ); + emit gotMyself( cd ); + + // read the privacy settings first, because this affects all contacts' apparent status + extractPrivacy( loginResponseFields ); + + extractCustomStatuses( loginResponseFields ); + + // CREATE CONTACT LIST + // locate contact list + Field::MultiField * contactList = loginResponseFields.findMultiField( NM_A_FA_CONTACT_LIST ); + if ( contactList ) + { + Field::FieldList contactListFields = contactList->fields(); + Field::MultiField * container; + // read folders + for ( Field::FieldListIterator it = contactListFields.find( NM_A_FA_FOLDER ); + it != contactListFields.end(); + it = contactListFields.find( ++it, NM_A_FA_FOLDER ) ) + { + container = static_cast<Field::MultiField *>( *it ); + extractFolder( container ); + } + + // read contacts + for ( Field::FieldListIterator it = contactListFields.find( NM_A_FA_CONTACT ); + it != contactListFields.end(); + it = contactListFields.find( ++it, NM_A_FA_CONTACT ) ) + { + container = static_cast<Field::MultiField *>( *it ); + extractContact( container ); + } + } + + extractKeepalivePeriod( loginResponseFields ); + + setSuccess(); + + return true; +} + +void LoginTask::extractFolder( Field::MultiField * folderContainer ) +{ + FolderItem folder; + Field::SingleField * current; + Field::FieldList fl = folderContainer->fields(); + // object id + current = fl.findSingleField( NM_A_SZ_OBJECT_ID ); + folder.id = current->value().toInt(); + // sequence number + current = fl.findSingleField( NM_A_SZ_SEQUENCE_NUMBER ); + folder.sequence = current->value().toInt(); + // name + current = fl.findSingleField( NM_A_SZ_DISPLAY_NAME ); + folder.name = current->value().toString(); + // parent + current = fl.findSingleField( NM_A_SZ_PARENT_ID ); + folder.parentId = current->value().toInt(); + + client()->debug( QString( "Got folder: %1, obj: %2, parent: %3, seq: %3." ).arg( folder.name ).arg( folder.id ).arg( folder.parentId ).arg( folder.sequence ) ); + // tell the world about it + emit gotFolder( folder ); +} + +void LoginTask::extractContact( Field::MultiField * contactContainer ) +{ + if ( contactContainer->tag() != NM_A_FA_CONTACT ) + return; + ContactItem contact; + Field::SingleField * current; + Field::FieldList fl = contactContainer->fields(); + // sequence number, object and parent IDs are a numeric values but are stored as strings... + current = fl.findSingleField( NM_A_SZ_OBJECT_ID ); + contact.id = current->value().toInt(); + current = fl.findSingleField( NM_A_SZ_PARENT_ID ); + contact.parentId = current->value().toInt(); + current = fl.findSingleField( NM_A_SZ_SEQUENCE_NUMBER ); + contact.sequence = current->value().toInt(); + current = fl.findSingleField( NM_A_SZ_DISPLAY_NAME ); + contact.displayName = current->value().toString(); + current = fl.findSingleField( NM_A_SZ_DN ); + contact.dn = current->value().toString().lower(); + emit gotContact( contact ); + Field::MultiField * details = fl.findMultiField( NM_A_FA_USER_DETAILS ); + if ( details ) // not all contact list contacts have these + { + Field::FieldList detailsFields = details->fields(); + ContactDetails cd = extractUserDetails( detailsFields ); + if ( cd.dn.isEmpty() ) + cd.dn = contact.dn; + // tell the UserDetailsManager that we have this contact's details + client()->userDetailsManager()->addDetails( cd ); + emit gotContactUserDetails( cd ); + } +} + +ContactDetails LoginTask::extractUserDetails( Field::FieldList & fields ) +{ + ContactDetails cd; + cd.status = GroupWise::Invalid; + cd.archive = false; + // read the supplied fields, set metadata and status. + Field::SingleField * sf; + if ( ( sf = fields.findSingleField ( NM_A_SZ_AUTH_ATTRIBUTE ) ) ) + cd.authAttribute = sf->value().toString(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_DN ) ) ) + cd.dn = sf->value().toString().lower(); // HACK: lowercased DN + if ( ( sf = fields.findSingleField ( "CN" ) ) ) + cd.cn = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Given Name" ) ) ) + cd.givenName = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Surname" ) ) ) + cd.surname = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Full Name" ) ) ) + cd.fullName = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "nnmArchive" ) ) ) + cd.archive = ( sf->value().toInt() == 1 ); + if ( ( sf = fields.findSingleField ( NM_A_SZ_STATUS ) ) ) + cd.status = sf->value().toInt(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_MESSAGE_BODY ) ) ) + cd.awayMessage = sf->value().toString(); + Field::MultiField * mf; + QMap< QString, QString > propMap; + if ( ( mf = fields.findMultiField ( NM_A_FA_INFO_DISPLAY_ARRAY ) ) ) + { + Field::FieldList fl = mf->fields(); + const Field::FieldListIterator end = fl.end(); + for ( Field::FieldListIterator it = fl.begin(); it != end; ++it ) + { + Field::SingleField * propField = dynamic_cast<Field::SingleField *>( *it ); + if ( propField ) + { + QString propName = propField->tag(); + QString propValue = propField->value().toString(); + propMap.insert( propName, propValue ); + } + else + { + Field::MultiField * propList = dynamic_cast<Field::MultiField*>( *it ); + if ( propList ) + { + // Hello A Nagappan. GW gave us a multiple field where we previously got a single field + QString parentName = propList->tag(); + Field::FieldList propFields = propList->fields(); + const Field::FieldListIterator end = propFields.end(); + for ( Field::FieldListIterator it = propFields.begin(); it != end; ++it ) + { + propField = dynamic_cast<Field::SingleField *>( *it ); + if ( propField /*&& propField->tag() == parentName */) + { + QString propValue = propField->value().toString(); + QString contents = propMap[ propField->tag() ]; + if ( !contents.isEmpty() ) + contents.append( ", " ); + contents.append( propField->value().toString()); + propMap.insert( propField->tag(), contents ); + } + } + } + } + } + } + if ( !propMap.empty() ) + { + cd.properties = propMap; + } + return cd; +} + +void LoginTask::extractPrivacy( Field::FieldList & fields ) +{ + bool privacyLocked = false; + bool defaultDeny = false; + QStringList allowList; + QStringList denyList; + // read blocking + // may be a single field or may be an array + Field::FieldListIterator it = fields.find( NM_A_LOCKED_ATTR_LIST ); + if ( it != fields.end() ) + { + if ( Field::SingleField * sf = dynamic_cast<Field::SingleField *>( *it ) ) + { + if ( sf->value().toString().find( NM_A_BLOCKING ) ) + privacyLocked = true; + } + else if ( Field::MultiField * mf = dynamic_cast<Field::MultiField *>( *it ) ) + { + Field::FieldList fl = mf->fields(); + for ( Field::FieldListIterator it = fl.begin(); it != fl.end(); ++it ) + { + if ( Field::SingleField * sf = dynamic_cast<Field::SingleField *>( *it ) ) + { + if ( sf->tag() == NM_A_BLOCKING ) + { + privacyLocked = true; + break; + } + } + } + } + } + + // read default privacy policy + Field::SingleField * sf = fields.findSingleField( NM_A_BLOCKING ); + if ( sf ) + defaultDeny = ( sf->value().toInt() != 0 ); + + + // read deny list + denyList = readPrivacyItems( NM_A_BLOCKING_DENY_LIST, fields ); + // read allow list + allowList = readPrivacyItems( NM_A_BLOCKING_ALLOW_LIST, fields ); + emit gotPrivacySettings( privacyLocked, defaultDeny, allowList, denyList ); + kdDebug( GROUPWISE_DEBUG_GLOBAL ) << "locked is " << privacyLocked << ", default is " << defaultDeny << "\nallow list is: " << allowList << "\ndeny list is: " << denyList << endl; +} + +QStringList LoginTask::readPrivacyItems( const QCString & tag, Field::FieldList & fields ) +{ + QStringList items; + + Field::FieldListIterator it = fields.find( tag ); + if ( it != fields.end() ) + { + if ( Field::SingleField * sf = dynamic_cast<Field::SingleField *>( *it ) ) + { + items.append( sf->value().toString().lower() ); + } + else if ( Field::MultiField * mf = dynamic_cast<Field::MultiField *>( *it ) ) + { + Field::FieldList fl = mf->fields(); + for ( Field::FieldListIterator it = fl.begin(); it != fl.end(); ++it ) + { + if ( Field::SingleField * sf = dynamic_cast<Field::SingleField *>( *it ) ) + { + items.append( sf->value().toString().lower() ); + } + } + } + } + return items; +} + +void LoginTask::extractCustomStatuses( Field::FieldList & fields ) +{ + Field::FieldListIterator it = fields.find( NM_A_FA_CUSTOM_STATUSES ); + if ( it != fields.end() ) + { + if ( Field::MultiField * mf = dynamic_cast<Field::MultiField *>( *it ) ) + { + Field::FieldList fl = mf->fields(); + for ( Field::FieldListIterator custStatIt = fl.begin(); custStatIt != fl.end(); ++custStatIt ) + { + Field::MultiField * mf2 = dynamic_cast<Field::MultiField *>( *custStatIt ); + if ( mf2 && ( mf2->tag() == NM_A_FA_STATUS ) ) + { + GroupWise::CustomStatus custom; + Field::FieldList fl2 = mf2->fields(); + for ( Field::FieldListIterator custContentIt = fl2.begin(); custContentIt != fl2.end(); ++custContentIt ) + { + if ( Field::SingleField * sf3 = dynamic_cast<Field::SingleField *>( *custContentIt ) ) + { + if ( sf3->tag() == NM_A_SZ_TYPE ) + custom.status = (GroupWise::Status)sf3->value().toInt(); + else if ( sf3->tag() == NM_A_SZ_DISPLAY_NAME ) + custom.name = sf3->value().toString(); + else if ( sf3->tag() == NM_A_SZ_MESSAGE_BODY ) + custom.autoReply = sf3->value().toString(); + } + } + emit gotCustomStatus( custom ); + } + } + } + } +} + +void LoginTask::extractKeepalivePeriod( Field::FieldList & fields ) +{ + Field::FieldListIterator it = fields.find( NM_A_UD_KEEPALIVE ); + if ( it != fields.end() ) + { + if ( Field::SingleField * sf = dynamic_cast<Field::SingleField *>( *it ) ) + { + bool ok; + int period = sf->value().toInt( &ok ); + if ( ok ) + { + emit gotKeepalivePeriod( period ); + } + } + } +} + +#include "logintask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/logintask.h b/kopete/protocols/groupwise/libgroupwise/tasks/logintask.h new file mode 100644 index 00000000..0b2acdfd --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/logintask.h @@ -0,0 +1,64 @@ +/* + Kopete Groupwise Protocol + logintask.h - Send our credentials to the server and process the contact list and privacy details that it returns. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef LOGINTASK_H +#define LOGINTASK_H + +#include "requesttask.h" + +using namespace GroupWise; + +/** +@author Kopete Developers +*/ +class LoginTask : public RequestTask +{ +Q_OBJECT +public: + LoginTask( Task * parent ); + ~LoginTask(); + /** + * Get the login fields ready to go + */ + void initialise(); + /** + * Only accepts the contactlist that comes back from the server, + * processes it and notifies the client of the contactlist + */ + bool take( Transfer * transfer ); +protected: + void extractFolder( Field::MultiField * folderContainer ); + void extractContact( Field::MultiField * contactContainer ); + ContactDetails extractUserDetails( Field::FieldList & fields ); + void extractPrivacy( Field::FieldList & fields ); + QStringList readPrivacyItems( const QCString & tag, Field::FieldList & fields ); + void extractCustomStatuses( Field::FieldList & fields ); + void extractKeepalivePeriod( Field::FieldList & fields ); +signals: + void gotMyself( const GroupWise::ContactDetails & ); + void gotFolder( const FolderItem & ); + void gotContact( const ContactItem & ); + void gotContactUserDetails( const GroupWise::ContactDetails & ); + void gotPrivacySettings( bool locked, bool defaultDeny, const QStringList & allowList, const QStringList & denyList ); + void gotCustomStatus( const GroupWise::CustomStatus & ); + void gotKeepalivePeriod( int ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/modifycontactlisttask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/modifycontactlisttask.cpp new file mode 100644 index 00000000..10233a18 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/modifycontactlisttask.cpp @@ -0,0 +1,139 @@ +/* + Kopete Groupwise Protocol + modifycontactlisttask.cpp - Ancestor of all tasks that change the server side contact list. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" +#include "response.h" +#include "gwerror.h" +#include "modifycontactlisttask.h" + +ModifyContactListTask::ModifyContactListTask(Task* parent): RequestTask(parent) +{ +} + +ModifyContactListTask::~ModifyContactListTask() +{ +} + +bool ModifyContactListTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + client()->debug( "ModifyContactListTask::take()" ); + + // scan the contact list received + // emit each add and delete as a signal + Field::FieldList fl = response->fields(); + fl.dump( true ); + Field::FieldListIterator it = fl.begin(); + Field::FieldListIterator end = fl.end(); + Field::MultiField * current = fl.findMultiField( NM_A_FA_RESULTS ); + if ( current ) + fl = current->fields(); + current = fl.findMultiField( NM_A_FA_CONTACT_LIST ); + if ( current ) + { + Field::FieldList contactList = current->fields(); + Field::FieldListIterator cursor = contactList.begin(); + const Field::FieldListIterator end = contactList.end(); + while ( cursor != end ) + { + Field::MultiField * mf = dynamic_cast< Field::MultiField * >( *cursor ); + if ( mf->tag() == NM_A_FA_CONTACT ) + { + // contact change + processContactChange( mf ); + } + else if ( mf->tag() == NM_A_FA_FOLDER ) + { + // folder change + processFolderChange( mf ); + } + ++cursor; + } + } + // TODO: call virtual here to read any fields after the contact list... + if ( response->resultCode() == GroupWise::None ) + setSuccess(); + else + setError( response->resultCode() ); + return true; +} + +void ModifyContactListTask::processContactChange( Field::MultiField * container ) +{ + if ( !( container->method() == NMFIELD_METHOD_ADD + || container->method() == NMFIELD_METHOD_DELETE ) ) + return; + + client()->debug( "ModifyContactListTask::processContactChange()" ); + Field::SingleField * current; + Field::FieldList fl = container->fields(); + ContactItem contact; + current = fl.findSingleField( NM_A_SZ_OBJECT_ID ); + contact.id = current->value().toInt(); + current = fl.findSingleField( NM_A_SZ_PARENT_ID ); + contact.parentId = current->value().toInt(); + current = fl.findSingleField( NM_A_SZ_SEQUENCE_NUMBER ); + contact.sequence = current->value().toInt(); + current = fl.findSingleField( NM_A_SZ_DISPLAY_NAME ); + contact.displayName = current->value().toString(); + current = fl.findSingleField( NM_A_SZ_DN ); + contact.dn = current->value().toString(); + + if ( container->method() == NMFIELD_METHOD_ADD ) + emit gotContactAdded( contact ); + else if ( container->method() == NMFIELD_METHOD_DELETE ) + emit gotContactDeleted( contact ); +} + +void ModifyContactListTask::processFolderChange( Field::MultiField * container ) +{ + if ( !( container->method() == NMFIELD_METHOD_ADD + || container->method() == NMFIELD_METHOD_DELETE ) ) + return; + + client()->debug( "ModifyContactListTask::processFolderChange()" ); + FolderItem folder; + Field::SingleField * current; + Field::FieldList fl = container->fields(); + // object id + current = fl.findSingleField( NM_A_SZ_OBJECT_ID ); + folder.id = current->value().toInt(); + // sequence number + current = fl.findSingleField( NM_A_SZ_SEQUENCE_NUMBER ); + folder.sequence = current->value().toInt(); + // name + current = fl.findSingleField( NM_A_SZ_DISPLAY_NAME ); + folder.name = current->value().toString(); + // parent + current = fl.findSingleField( NM_A_SZ_PARENT_ID ); + folder.parentId = current->value().toInt(); + if ( container->method() == NMFIELD_METHOD_ADD ) + emit gotFolderAdded( folder ); + else if ( container->method() == NMFIELD_METHOD_DELETE ) + emit gotFolderDeleted( folder ); + +} + + +#include "modifycontactlisttask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/modifycontactlisttask.h b/kopete/protocols/groupwise/libgroupwise/tasks/modifycontactlisttask.h new file mode 100644 index 00000000..2f5a4939 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/modifycontactlisttask.h @@ -0,0 +1,51 @@ +/* + Kopete Groupwise Protocol + modifycontactlisttask.h - Ancestor of all tasks that change the server side contact list. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef MODIFYCONTACTLISTTASK_H +#define MODIFYCONTACTLISTTASK_H + +#include "requesttask.h" + +/** +This is the parent of all tasks that manipulate the contact list. The server responds to each one in the same way, and this task contains a take() to process this response. + +@author SUSE AG +*/ + +using namespace GroupWise; + +class ModifyContactListTask : public RequestTask +{ +Q_OBJECT +public: + ModifyContactListTask(Task* parent); + ~ModifyContactListTask(); + bool take( Transfer * transfer ); +signals: + void gotFolderAdded( const FolderItem &); + void gotFolderDeleted( const FolderItem & ); + void gotContactAdded( const ContactItem & ); + void gotContactDeleted( const ContactItem & ); +private: + void processFolderChange( Field::MultiField * container ); + void processContactChange( Field::MultiField * container ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/movecontacttask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/movecontacttask.cpp new file mode 100644 index 00000000..713315ee --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/movecontacttask.cpp @@ -0,0 +1,83 @@ +/* + Kopete Groupwise Protocol + movecontacttask.cpp - Move a contact between folders on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" + +#include "movecontacttask.h" + +MoveContactTask::MoveContactTask(Task* parent): NeedFolderTask(parent) +{ + // make the client tell the client app (Kopete) when we receive a contact + connect( this, SIGNAL( gotContactAdded( const ContactItem & ) ), client(), SIGNAL( contactReceived( const ContactItem & ) ) ); +} + + +MoveContactTask::~MoveContactTask() +{ +} + +void MoveContactTask::moveContact( const ContactItem & contact, const int newParent ) +{ + Field::FieldList lst; + // TODO: - write a contact_item_to_fields method and factor duplicate code like this out + Field::FieldList contactFields; + contactFields.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, contact.id ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, contact.parentId ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_SEQUENCE_NUMBER, 0, NMFIELD_TYPE_UTF8, contact.sequence ) ); + if ( !contact.dn.isNull() ) + contactFields.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, contact.dn ) ); + if ( !contact.displayName.isNull() ) + contactFields.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, contact.displayName ) ); + Field::FieldList contactList; + contactList.append( + new Field::MultiField( NM_A_FA_CONTACT, NMFIELD_METHOD_DELETE, 0, NMFIELD_TYPE_ARRAY, contactFields ) ); + + lst.append( new Field::MultiField( NM_A_FA_CONTACT_LIST, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, contactList ) ); + + lst.append( new Field::SingleField( NM_A_SZ_SEQUENCE_NUMBER, 0, NMFIELD_TYPE_UTF8, "-1" ) ); + lst.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, QString::number( newParent ) ) ); + createTransfer( "movecontact", lst ); +} + +void MoveContactTask::moveContactToNewFolder( const ContactItem & contact, const int newSequenceNumber, const QString & folderDisplayName ) +{ + client()->debug("MoveContactTask::moveContactToNewFolder()" ); + m_folderSequence = newSequenceNumber; + m_folderDisplayName = folderDisplayName; + m_contactToMove = contact; + +} + +void MoveContactTask::onGo() +{ + // are we creating a folder first or can we just proceed as normal? + if ( m_folderDisplayName.isEmpty() ) + RequestTask::onGo(); + else // create the folder, when the folder has been created, onFolderCreated gets called and creates the contact + createFolder(); +} + +void MoveContactTask::onFolderCreated() +{ + client()->debug("MoveContactTask::onFolderCreated()" ); + moveContact( m_contactToMove, m_folderId ); + RequestTask::onGo(); +} +#include "movecontacttask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/movecontacttask.h b/kopete/protocols/groupwise/libgroupwise/tasks/movecontacttask.h new file mode 100644 index 00000000..f423981a --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/movecontacttask.h @@ -0,0 +1,49 @@ +/* + Kopete Groupwise Protocol + movecontacttask.h - Move a contact between folders on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef MOVECONTACTTASK_H +#define MOVECONTACTTASK_H + +#include "needfoldertask.h" + +/** +Moves a contact between folders on the server + +@author SUSE AG +*/ +class MoveContactTask : public NeedFolderTask +{ +Q_OBJECT +public: + MoveContactTask(Task* parent); + ~MoveContactTask(); + void moveContact( const ContactItem & contact, const int newParent ); + void moveContactToNewFolder( const ContactItem & contact, const int newSequenceNumber, const QString & folderDisplayName ); + void onGo(); +protected: + void onFolderCreated(); +private: + int m_targetFolder; + QString m_dn; + QString m_displayName; + ContactItem m_contactToMove; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/needfoldertask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/needfoldertask.cpp new file mode 100644 index 00000000..810326ee --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/needfoldertask.cpp @@ -0,0 +1,58 @@ +// +// C++ Implementation: %{MODULE} +// +// Description: +// +// +// Author: %{AUTHOR} <%{EMAIL}>, (C) %{YEAR} +// +// Copyright: See COPYING file that comes with this distribution +// +// +#include "client.h" +#include "tasks/createcontactinstancetask.h" +#include "tasks/createfoldertask.h" + +#include "needfoldertask.h" + +NeedFolderTask::NeedFolderTask(Task* parent): ModifyContactListTask(parent) +{ +} + +NeedFolderTask::~NeedFolderTask() +{ +} + +void NeedFolderTask::createFolder() +{ + CreateFolderTask * cct = new CreateFolderTask( client()->rootTask() ); + cct->folder( 0, m_folderSequence, m_folderDisplayName ); + connect( cct, SIGNAL( gotFolderAdded( const FolderItem & ) ), client(), SIGNAL( folderReceived( const FolderItem & ) ) ); + connect( cct, SIGNAL( gotFolderAdded( const FolderItem & ) ), SLOT( slotFolderAdded( const FolderItem & ) ) ); + connect( cct, SIGNAL( finished() ), SLOT( slotFolderTaskFinished() ) ); + cct->go( true ); +} + +void NeedFolderTask::slotFolderAdded( const FolderItem & addedFolder ) +{ + // if this is the folder we were trying to create + if ( m_folderDisplayName == addedFolder.name ) + { + client()->debug( QString( "NeedFolderTask::slotFolderAdded() - Folder %1 was created on the server, now has objectId %2" ).arg( addedFolder.name ).arg( addedFolder.id ) ); + m_folderId = addedFolder.id; + } +} + +void NeedFolderTask::slotFolderTaskFinished() +{ + CreateFolderTask *cct = ( CreateFolderTask* )sender(); + if ( cct->success() ) + { + // call our child class's action to be performed + onFolderCreated(); + } + else + setError( 1, "Folder creation failed" ); +} + +#include "needfoldertask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/needfoldertask.h b/kopete/protocols/groupwise/libgroupwise/tasks/needfoldertask.h new file mode 100644 index 00000000..8d6278df --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/needfoldertask.h @@ -0,0 +1,39 @@ +// +// C++ Interface: %{MODULE} +// +// Description: +// +// +// Author: %{AUTHOR} <%{EMAIL}>, (C) %{YEAR} +// +// Copyright: See COPYING file that comes with this distribution +// +// +#ifndef NEEDFOLDERTASK_H +#define NEEDFOLDERTASK_H + +#include "modifycontactlisttask.h" + +/** +This Task is the ancestor of Tasks that may need to create a folder on the server before they can carry out their own operation. + +@author Kopete Developers +*/ +class NeedFolderTask : public ModifyContactListTask +{ +Q_OBJECT +public: + NeedFolderTask(Task* parent); + ~NeedFolderTask(); + void createFolder(); + virtual void onFolderCreated() = 0; +protected slots: + void slotFolderAdded( const FolderItem & ); + void slotFolderTaskFinished(); +protected: + int m_folderSequence; + int m_folderId; + QString m_folderDisplayName; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/pollsearchresultstask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/pollsearchresultstask.cpp new file mode 100644 index 00000000..772a0888 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/pollsearchresultstask.cpp @@ -0,0 +1,185 @@ +/* + Kopete Groupwise Protocol + pollsearchresultstask.cpp - Poll the server to see if it has processed our search yet. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "gwfield.h" +#include "response.h" + +#include "logintask.h" + +#include "pollsearchresultstask.h" + +using namespace GroupWise; + +PollSearchResultsTask::PollSearchResultsTask(Task* parent): RequestTask(parent) +{ +} + + +PollSearchResultsTask::~PollSearchResultsTask() +{ +} + +void PollSearchResultsTask::poll( const QString & queryHandle ) +{ + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, queryHandle ) ); + createTransfer( "getresults", lst ); +} + +bool PollSearchResultsTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + setError( response->resultCode() ); + return true; + } + + // look for the status code + Field::FieldList responseFields = response->fields(); + Field::SingleField * sf = responseFields.findSingleField( NM_A_SZ_STATUS ); + m_queryStatus = sf->value().toInt(); + + Field::MultiField * resultsArray = responseFields.findMultiField( NM_A_FA_RESULTS ); + if ( !resultsArray ) + { + setError( Protocol ); + return true; + } + Field::FieldList matches = resultsArray->fields(); + const Field::FieldListIterator end = matches.end(); + for ( Field::FieldListIterator it = matches.find( NM_A_FA_CONTACT ); + it != end; + it = matches.find( ++it, NM_A_FA_CONTACT ) ) + { + Field::MultiField * mf = static_cast<Field::MultiField *>( *it ); + Field::FieldList contact = mf->fields(); + GroupWise::ContactDetails cd = extractUserDetails( contact ); + m_results.append( cd ); + } + + // first field: NM_A_SZ_STATUS contains + #define SEARCH_PENDING 0 + #define SEARCH_INPROGRESS 1 + #define SEARCH_COMPLETED 2 + #define SEARCH_TIMEOUT 3 + #define SEARCH_CANCELLED 4 + #define SEARCH_ERROR 5 + // set a status code if needed + // followed by NM_A_FA_RESULTS, looks like a getdetails + // add an accessor to get at the results list of ContactItems, probably + + if ( m_queryStatus != 2 ) + setError( m_queryStatus ); + else + setSuccess( m_queryStatus ); + return true; +} + +QValueList< GroupWise::ContactDetails > PollSearchResultsTask::results() +{ + return m_results; +} + +int PollSearchResultsTask::queryStatus() +{ + return m_queryStatus; +} + +GroupWise::ContactDetails PollSearchResultsTask::extractUserDetails( Field::FieldList & fields ) +{ + ContactDetails cd; + cd.status = GroupWise::Invalid; + cd.archive = false; + // read the supplied fields, set metadata and status. + Field::SingleField * sf; + if ( ( sf = fields.findSingleField ( NM_A_SZ_AUTH_ATTRIBUTE ) ) ) + cd.authAttribute = sf->value().toString(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_DN ) ) ) + cd.dn =sf->value().toString().lower(); // HACK: lowercased DN + if ( ( sf = fields.findSingleField ( "CN" ) ) ) + cd.cn = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Given Name" ) ) ) + cd.givenName = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Surname" ) ) ) + cd.surname = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "Full Name" ) ) ) + cd.fullName = sf->value().toString(); + if ( ( sf = fields.findSingleField ( "nnmArchive" ) ) ) + cd.archive = ( sf->value().toInt() == 1 ); + if ( ( sf = fields.findSingleField ( NM_A_SZ_STATUS ) ) ) + cd.status = sf->value().toInt(); + if ( ( sf = fields.findSingleField ( NM_A_SZ_MESSAGE_BODY ) ) ) + cd.awayMessage = sf->value().toString(); + Field::MultiField * mf; + QMap< QString, QString > propMap; + if ( ( mf = fields.findMultiField ( NM_A_FA_INFO_DISPLAY_ARRAY ) ) ) + { + Field::FieldList fl = mf->fields(); + const Field::FieldListIterator end = fl.end(); + for ( Field::FieldListIterator it = fl.begin(); it != end; ++it ) + { + // assumes each property only present once + // check in logintask.cpp and if it's a multi field, + // get the value of this instance, check if it's already in the property map and append if found. + Field::SingleField * propField = dynamic_cast<Field::SingleField *>( *it ); + if ( propField ) + { + QString propName = propField->tag(); + QString propValue = propField->value().toString(); + propMap.insert( propName, propValue ); + } + else + { + Field::MultiField * propList = dynamic_cast<Field::MultiField*>( *it ); + if ( propList ) + { + QString parentName = propList->tag(); + Field::FieldList propFields = propList->fields(); + const Field::FieldListIterator end = propFields.end(); + for ( Field::FieldListIterator it = propFields.begin(); it != end; ++it ) + { + propField = dynamic_cast<Field::SingleField *>( *it ); + if ( propField ) + { + QString propValue = propField->value().toString(); + QString contents = propMap[ propField->tag() ]; + if ( !contents.isEmpty() ) + contents.append( ", " ); + contents.append( propField->value().toString()); + propMap.insert( propField->tag(), contents ); + } + } + } + } + } + } + if ( !propMap.empty() ) + { + cd.properties = propMap; + } + return cd; +} + +#include "pollsearchresultstask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/pollsearchresultstask.h b/kopete/protocols/groupwise/libgroupwise/tasks/pollsearchresultstask.h new file mode 100644 index 00000000..11f810c0 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/pollsearchresultstask.h @@ -0,0 +1,52 @@ +/* + Kopete Groupwise Protocol + pollsearchresultstask.h - Poll the server once to see if it has processed our search yet. + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef POLLSEARCHRESULTSTASK_H +#define POLLSEARCHRESULTSTASK_H + +#include <qvaluelist.h> + +#include "gwerror.h" + +#include "requesttask.h" + +/** +Search results are polled on the server, using the search handle supplied by the client with the original query. This is a single poll request, which if successful, will retrieve the results. Otherwise, it will set a status code, so the ContactSearchTask can decide whether to poll again. + +@author SUSE AG +*/ +class PollSearchResultsTask : public RequestTask +{ +Q_OBJECT +public: + enum SearchResultCode { Pending=0, InProgess=1, Completed=2, TimeOut=3, Cancelled=4, Error=5 }; + PollSearchResultsTask(Task* parent); + ~PollSearchResultsTask(); + void poll( const QString & queryHandle); + bool take( Transfer * transfer ); + int queryStatus(); + QValueList< GroupWise::ContactDetails > results(); +GroupWise::ContactDetails extractUserDetails( Field::FieldList & fields ); +private: + int m_queryStatus; + QValueList< GroupWise::ContactDetails > m_results; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/privacyitemtask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/privacyitemtask.cpp new file mode 100644 index 00000000..003a6d60 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/privacyitemtask.cpp @@ -0,0 +1,82 @@ +/* + Kopete Groupwise Protocol + privacyitemtask.cpp - Add an entry to the server side deny or allow lists + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "privacyitemtask.h" + +PrivacyItemTask::PrivacyItemTask( Task* parent) : RequestTask( parent ) +{ +} + +PrivacyItemTask::~PrivacyItemTask() +{ +} + +QString PrivacyItemTask::dn() const +{ + return m_dn; +} + +bool PrivacyItemTask::defaultDeny() const +{ + return m_default; +} + +void PrivacyItemTask::allow( const QString & dn ) +{ + m_dn = dn; + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_BLOCKING_ALLOW_ITEM, NMFIELD_METHOD_ADD, 0, NMFIELD_TYPE_UTF8, dn ) ); + createTransfer( "createblock", lst ); +} + +void PrivacyItemTask::deny( const QString & dn ) +{ + m_dn = dn; + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_BLOCKING_DENY_ITEM, NMFIELD_METHOD_ADD, 0, NMFIELD_TYPE_UTF8, dn ) ); + createTransfer( "createblock", lst ); +} + +void PrivacyItemTask::removeAllow( const QString & dn ) +{ + m_dn = dn; + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_BLOCKING_ALLOW_LIST, NMFIELD_METHOD_DELETE, 0, NMFIELD_TYPE_UTF8, dn ) ); + createTransfer( "updateblocks", lst ); + +} + +void PrivacyItemTask::removeDeny( const QString & dn ) +{ + m_dn = dn; + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_BLOCKING_DENY_LIST, NMFIELD_METHOD_DELETE, 0, NMFIELD_TYPE_UTF8, dn ) ); + createTransfer( "updateblocks", lst ); +} + +void PrivacyItemTask::defaultPolicy( bool defaultDeny ) +{ + m_default = defaultDeny; + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_BLOCKING, NMFIELD_METHOD_UPDATE, 0, NMFIELD_TYPE_UTF8, ( defaultDeny ? "1" :"0" ) ) ); + createTransfer( "updateblocks", lst ); +} + +#include "privacyitemtask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/privacyitemtask.h b/kopete/protocols/groupwise/libgroupwise/tasks/privacyitemtask.h new file mode 100644 index 00000000..809cb7a4 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/privacyitemtask.h @@ -0,0 +1,50 @@ +/* + Kopete Groupwise Protocol + privacyitemtask.h - Add an entry to the server side deny or allow lists + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef PRIVACYITEMTASK_H +#define PRIVACYITEMTASK_H + +#include "requesttask.h" + +/** +Adds a contact to the server side allow or deny lists + +@author SUSE AG +*/ +class PrivacyItemTask : public RequestTask +{ +Q_OBJECT +public: + PrivacyItemTask( Task* parent); + ~PrivacyItemTask(); + void allow( const QString & dn ); + void deny( const QString & dn ); + void removeAllow( const QString & dn ); + void removeDeny( const QString & dn ); + void defaultPolicy( bool defaultDeny ); + QString dn() const; + bool defaultDeny() const; + // void contacts( const QStringList & contacts ); +private: + bool m_default; + QString m_dn; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/rejectinvitetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/rejectinvitetask.cpp new file mode 100644 index 00000000..2b252ff5 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/rejectinvitetask.cpp @@ -0,0 +1,39 @@ +/* + Kopete Groupwise Protocol + rejectinvitetask.cpp - Decline an invitation to chat + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "rejectinvitetask.h" + +RejectInviteTask::RejectInviteTask(Task* parent): RequestTask(parent) +{ +} + +RejectInviteTask::~RejectInviteTask() +{ +} + +void RejectInviteTask::reject( const GroupWise::ConferenceGuid & guid ) +{ + Field::FieldList lst, tmp; + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, guid ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + createTransfer( "rejectconf", lst ); +} + +#include "rejectinvitetask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/rejectinvitetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/rejectinvitetask.h new file mode 100644 index 00000000..b82f4e77 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/rejectinvitetask.h @@ -0,0 +1,41 @@ +/* + Kopete Groupwise Protocol + rejectinvitetask.h - Decline an invitation to chat + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef REJECTINVITETASK_H +#define REJECTINVITETASK_H + +#include "requesttask.h" + +/** +Used to reject an invitation to join a conference + +@author SUSE AG +*/ +class RejectInviteTask : public RequestTask +{ +Q_OBJECT +public: + RejectInviteTask(Task* parent); + ~RejectInviteTask(); + void reject( const GroupWise::ConferenceGuid & guid ); + +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/requesttask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/requesttask.cpp new file mode 100644 index 00000000..3788bb6e --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/requesttask.cpp @@ -0,0 +1,76 @@ +/* + Kopete Groupwise Protocol + requesttask.cpp - Ancestor of all tasks that carry out a user request + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "gwfield.h" +#include "client.h" +#include "request.h" +#include "response.h" +#include "requestfactory.h" + +#include "requesttask.h" + +RequestTask::RequestTask( Task * parent ) +: Task( parent ) +{ +} + +bool RequestTask::forMe( Transfer * transfer ) const +{ + // see if we can down-cast transfer to a Response + Response * theResponse = dynamic_cast<Response *>(transfer); + return (theResponse && theResponse->transactionId() == m_transactionId ); +} + +void RequestTask::createTransfer( const QString & command, const Field::FieldList & fields ) +{ + Request * request = client()->requestFactory()->request( command ); + m_transactionId = request->transactionId(); + request->setFields( fields ); + Task::setTransfer( request ); +} + +void RequestTask::onGo() +{ + if ( transfer() ) + { + client()->debug( QString( "%1::onGo() - sending %2 fields" ).arg( className() ).arg( static_cast<Request *>( transfer() )->command() ) ); + send( static_cast<Request *>( transfer() ) ); + } + else + client()->debug( "RequestTask::onGo() - called prematurely, no transfer set." ); +} + +bool RequestTask::take( Transfer * transfer ) +{ + if ( forMe( transfer ) ) + { + client()->debug( "RequestTask::take() - Default take() Accepting transaction ack, taking no further action" ); + Response * response = dynamic_cast<Response *>( transfer ); + if ( response->resultCode() == GroupWise::None ) + setSuccess(); + else + setError( response->resultCode() ); + return true; + } + else + return false; +} + +#include "requesttask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/requesttask.h b/kopete/protocols/groupwise/libgroupwise/tasks/requesttask.h new file mode 100644 index 00000000..30ee57ed --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/requesttask.h @@ -0,0 +1,42 @@ +/* + Kopete Groupwise Protocol + requesttask.h - Ancestor of all tasks that carry out a user request + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef GW_REQUESTTASK_H +#define GW_REQUESTTASK_H + +#include "task.h" + +class Transfer; + +class RequestTask : public Task +{ +Q_OBJECT + public: + RequestTask( Task *parent ); + bool take( Transfer * transfer ); + virtual void onGo(); + protected: + bool forMe( Transfer * transfer ) const; + void createTransfer( const QString & command, const Field::FieldList & fields ); + private: + int m_transactionId; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/searchchattask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/searchchattask.cpp new file mode 100644 index 00000000..4ee35549 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/searchchattask.cpp @@ -0,0 +1,127 @@ +/* + Kopete Groupwise Protocol + searchchattask.cpp - high level search for users on the server - spawns PollSearchResultsTasks + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include <qdatetime.h> +#include <qtimer.h> + +#include "client.h" +#include "gwerror.h" +#include "gwfield.h" +#include "response.h" + +#include "getchatsearchresultstask.h" + +#include "searchchattask.h" + + +// the delay we allow the server to initially do the search +#define GW_POLL_INITIAL_DELAY 1000 +// the maximum number of times to poll the server +#define GW_POLL_MAXIMUM 5 +// the frequency between subsequent polls +#define GW_POLL_FREQUENCY_MS 8000 + +using namespace GroupWise; + +SearchChatTask::SearchChatTask(Task* parent): RequestTask(parent), m_polls( 0 ) +{ +} + + +SearchChatTask::~SearchChatTask() +{ +} + +void SearchChatTask::search( SearchType type ) +{ + Field::FieldList lst; + // object Id identifies the search for later reference + lst.append( new Field::SingleField( NM_A_B_ONLY_MODIFIED, 0, NMFIELD_TYPE_BOOL, ( type == FetchAll ? 0 : 1 ) ) ); + createTransfer( "chatsearch", lst ); +} + +bool SearchChatTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + kdDebug( GROUPWISE_DEBUG_GLOBAL ) << k_funcinfo << "got return code in response << " << response->resultCode() << endl; + setError( response->resultCode() ); + return true; + } + Field::FieldList responseFields = response->fields(); + Field::SingleField * sf = responseFields.findSingleField( NM_A_UD_OBJECT_ID ); + m_objectId = sf->value().toInt(); + + // now start the results poll timer + QTimer::singleShot( GW_POLL_INITIAL_DELAY, this, SLOT( slotPollForResults() ) ); + return true; +} + +void SearchChatTask::slotPollForResults() +{ + //create a PollSearchResultsTask + GetChatSearchResultsTask * gcsrt = new GetChatSearchResultsTask( client()->rootTask() ); + gcsrt->poll( m_objectId ); + connect( gcsrt, SIGNAL( finished() ), SLOT( slotGotPollResults() ) ); + gcsrt->go( true ); +} + +void SearchChatTask::slotGotPollResults() +{ + GetChatSearchResultsTask * gcsrt = (GetChatSearchResultsTask *)sender(); + kdDebug( GROUPWISE_DEBUG_GLOBAL ) << k_funcinfo << "status code is " << gcsrt->queryStatus() << endl; + m_polls++; + switch ( gcsrt->queryStatus() ) + { + case GetChatSearchResultsTask::GettingData: + if ( m_polls < GW_POLL_MAXIMUM ) // restart timer + QTimer::singleShot( GW_POLL_FREQUENCY_MS, this, SLOT( slotPollForResults() ) ); + else + setSuccess( gcsrt->statusCode() ); + break; + case GetChatSearchResultsTask::DataRetrieved: + // got some results, there may be more. + m_results += gcsrt->results(); + QTimer::singleShot( 0, this, SLOT( slotPollForResults() ) ); + break; + case GetChatSearchResultsTask::Completed: + m_results += gcsrt->results(); + setSuccess(); + break; + case GetChatSearchResultsTask::Cancelled: + setError(gcsrt->statusCode() ); + break; + case GetChatSearchResultsTask::Error: + setError( gcsrt->statusCode() ); + break; + } +} + +QValueList< GroupWise::ChatroomSearchResult > SearchChatTask::results() +{ + return m_results; +} + +#include "searchchattask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/searchchattask.h b/kopete/protocols/groupwise/libgroupwise/tasks/searchchattask.h new file mode 100644 index 00000000..2f24e075 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/searchchattask.h @@ -0,0 +1,66 @@ +/* + Kopete Groupwise Protocol + searchchattask.h - search for chatrooms on the server - spawns PollSearchResultsTasks + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef SEARCHCHATTASK_H +#define SEARCHCHATTASK_H + +#include "gwerror.h" + +#include "requesttask.h" + +class QTimer; + +/** +This Task searches for chatrooms on the server + +@author SUSE Linux Products GmbH + */ +class SearchChatTask : public RequestTask +{ + Q_OBJECT + public: + enum SearchType { FetchAll=0, SinceLastSearch }; + + SearchChatTask(Task* parent); + + ~SearchChatTask(); + /** + * Create the search query + */ + void search( SearchType type ); + /** + * If the query was accepted, start a timer to poll for results using PollSearchResultsTask + */ + virtual bool take( Transfer * transfer ); + /** + * Access the results of the search + */ + QValueList< GroupWise::ChatroomSearchResult > results(); + protected slots: + void slotPollForResults(); + void slotGotPollResults(); + private: + QTimer * m_resultsPollTimer; + QValueList< GroupWise::ChatroomSearchResult > m_results; + int m_polls; + int m_objectId; // used to identify our query to the server, so we can poll for its results +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/searchusertask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/searchusertask.cpp new file mode 100644 index 00000000..cd199ad8 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/searchusertask.cpp @@ -0,0 +1,137 @@ +/* + Kopete Groupwise Protocol + searchusertask.cpp - high level search for users on the server - spawns PollSearchResultsTasks + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include <qdatetime.h> +#include <qtimer.h> + +#include "client.h" +#include "gwerror.h" +#include "gwfield.h" +#include "response.h" + +#include "pollsearchresultstask.h" + +#include "searchusertask.h" + +// the delay we allow the server to initially do the search +#define GW_POLL_INITIAL_DELAY 1000 +// the maximum number of times to poll the server +#define GW_POLL_MAXIMUM 5 +// the frequency between subsequent polls +#define GW_POLL_FREQUENCY_MS 8000 + +using namespace GroupWise; + +SearchUserTask::SearchUserTask(Task* parent): RequestTask(parent), m_polls( 0 ) +{ +} + + +SearchUserTask::~SearchUserTask() +{ +} + +void SearchUserTask::search( const QValueList<UserSearchQueryTerm> & query ) +{ + m_queryHandle = QString::number( QDateTime::currentDateTime().toTime_t () ); + Field::FieldList lst; + if ( query.isEmpty() ) + { + setError( 1, "no query terms" ); + return; + } + // object Id identifies the search for later reference + lst.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, m_queryHandle ) ); + QValueList<UserSearchQueryTerm>::ConstIterator it = query.begin(); + const QValueList<UserSearchQueryTerm>::ConstIterator end = query.end(); + for ( ; it != end; ++it ) + { + Field::SingleField * fld = new Field::SingleField( (*it).field.ascii(), (*it).operation, 0, NMFIELD_TYPE_UTF8, (*it).argument ); + lst.append( fld ); + } + //lst.append( new Field::SingleField( "Given Name", 0, NMFIELD_TYPE_UTF8, [ NMFIELD_METHOD_EQUAL | NMFIELD_METHOD_MATCHBEGIN | NMFIELD_METHOD_MATCHEND | NMFIELD_METHOD_SEARCH ], searchTerm ); + // Or "Surname", NM_A_SZ_USERID, NM_A_SZ_TITLE, NM_A_SZ_DEPARTMENT in other fields + + createTransfer( "createsearch", lst ); +} + +bool SearchUserTask::take( Transfer * transfer ) +{ + if ( !forMe( transfer ) ) + return false; + Response * response = dynamic_cast<Response *>( transfer ); + if ( !response ) + return false; + if ( response->resultCode() ) + { + kdDebug( GROUPWISE_DEBUG_GLOBAL ) << k_funcinfo << "got return code in response << " << response->resultCode() << endl; + setError( response->resultCode() ); + return true; + } + // now start the results poll timer + QTimer::singleShot( GW_POLL_INITIAL_DELAY, this, SLOT( slotPollForResults() ) ); + return true; +} + +void SearchUserTask::slotPollForResults() +{ + //create a PollSearchResultsTask + PollSearchResultsTask * psrt = new PollSearchResultsTask( client()->rootTask() ); + psrt->poll( m_queryHandle ); + connect( psrt, SIGNAL( finished() ), SLOT( slotGotPollResults() ) ); + psrt->go( true ); +} + +void SearchUserTask::slotGotPollResults() +{ + PollSearchResultsTask * psrt = (PollSearchResultsTask *)sender(); + kdDebug( GROUPWISE_DEBUG_GLOBAL ) << k_funcinfo << "status code is " << psrt->queryStatus() << endl; + m_polls++; + switch ( psrt->queryStatus() ) + { + case PollSearchResultsTask::Pending: + case PollSearchResultsTask::InProgess: + if ( m_polls < GW_POLL_MAXIMUM ) // restart timer + QTimer::singleShot( GW_POLL_FREQUENCY_MS, this, SLOT( slotPollForResults() ) ); + else + setSuccess( psrt->statusCode() ); + break; + case PollSearchResultsTask::Completed: + m_results = psrt->results(); + setSuccess(); + break; + case PollSearchResultsTask::Cancelled: + setError(psrt->statusCode() ); + break; + case PollSearchResultsTask::Error: + setError( psrt->statusCode() ); + break; + case PollSearchResultsTask::TimeOut: + setError( psrt->statusCode() ); + break; + } +} + +QValueList< GroupWise::ContactDetails > SearchUserTask::results() +{ + return m_results; +} + +#include "searchusertask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/searchusertask.h b/kopete/protocols/groupwise/libgroupwise/tasks/searchusertask.h new file mode 100644 index 00000000..28c09b02 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/searchusertask.h @@ -0,0 +1,63 @@ +/* + Kopete Groupwise Protocol + searchusertask.h - high level search for users on the server - spawns PollSearchResultsTasks + + Copyright (c) 2005 SUSE Linux Products GmbH http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2005 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef SEARCHUSERTASK_H +#define SEARCHUSERTASK_H + +#include "requesttask.h" + +class QTimer; + +/** +This Task performs user searching on the server + +@author SUSE AG +*/ +class SearchUserTask : public RequestTask +{ +Q_OBJECT +public: + SearchUserTask(Task* parent); + + ~SearchUserTask(); + /** + * Create the search query + * @param query a list of search terms + */ + void search( const QValueList<GroupWise::UserSearchQueryTerm> & query); + /** + * If the query was accepted, start a timer to poll for results using PollSearchResultsTask + */ + virtual bool take( Transfer * transfer ); + /** + * Access the results of the search + */ + QValueList< GroupWise::ContactDetails > results(); +protected slots: + void slotPollForResults(); + void slotGotPollResults(); +private: + QString m_queryHandle; // used to identify our query to the server, so we can poll for its results + QTimer * m_resultsPollTimer; + QValueList< GroupWise::ContactDetails > m_results; + int m_polls; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/sendinvitetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/sendinvitetask.cpp new file mode 100644 index 00000000..b3a9614f --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/sendinvitetask.cpp @@ -0,0 +1,42 @@ +/* + Kopete Groupwise Protocol + sendinvitetask.cpp - invites someone to join a conference + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "sendinvitetask.h" + +SendInviteTask::SendInviteTask(Task* parent): RequestTask(parent) +{ +} + +SendInviteTask::~SendInviteTask() +{ +} + +void SendInviteTask::invite( const GroupWise::ConferenceGuid & guid, const QStringList & invitees, const GroupWise::OutgoingMessage & msg) +{ + Field::FieldList lst, tmp; + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, guid ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + QValueListConstIterator<QString> end = invitees.end(); + for ( QValueListConstIterator<QString> it = invitees.begin(); it != end; ++it ) + lst.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_DN, *it ) ); + if ( !msg.message.isEmpty() ) + lst.append( new Field::SingleField( NM_A_SZ_MESSAGE_BODY, 0, NMFIELD_TYPE_UTF8, msg.message ) ); + createTransfer( "sendinvite", lst ); +} diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/sendinvitetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/sendinvitetask.h new file mode 100644 index 00000000..c8cf1d9b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/sendinvitetask.h @@ -0,0 +1,43 @@ +/* + Kopete Groupwise Protocol + sendinvitetask.h - invites someone to join a conference + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef SENDINVITETASK_H +#define SENDINVITETASK_H + +#include "gwerror.h" + +#include "requesttask.h" + +/** +This sends an invitation to a conference + +@author SUSE AG +*/ +class SendInviteTask : public RequestTask +{ +public: + SendInviteTask(Task* parent); + ~SendInviteTask(); + void invite( const GroupWise::ConferenceGuid & guid, const QStringList & invitees, const GroupWise::OutgoingMessage & msg ); +private: + QString m_confId; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/sendmessagetask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/sendmessagetask.cpp new file mode 100644 index 00000000..290b9d9b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/sendmessagetask.cpp @@ -0,0 +1,51 @@ +/* + Kopete Groupwise Protocol + sendmessagetask.cpp - sends a message to a conference + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "sendmessagetask.h" + +SendMessageTask::SendMessageTask(Task* parent): RequestTask(parent) +{ +} + + +SendMessageTask::~SendMessageTask() +{ +} + +void SendMessageTask::message( const QStringList & recipientDNList, const OutgoingMessage & msg ) +{ + // Assumes the conference is instantiated, unlike Gaim's nm_send_message + Field::FieldList lst, tmp, msgBodies; + // list containing GUID + tmp.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, msg.guid ) ); + lst.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, tmp ) ); + msgBodies.append( new Field::SingleField( NM_A_SZ_MESSAGE_BODY, 0, NMFIELD_TYPE_UTF8, msg.rtfMessage ) ); + // message body type indicator / separator? + msgBodies.append( new Field::SingleField( NM_A_UD_MESSAGE_TYPE, 0, NMFIELD_TYPE_UDWORD, 0 ) ); + // message body plaintext + msgBodies.append( new Field::SingleField( NM_A_SZ_MESSAGE_TEXT, 0, NMFIELD_TYPE_UTF8, msg.message ) ); + // list containing message bodies + lst.append( new Field::MultiField( NM_A_FA_MESSAGE, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, msgBodies ) ); + // series of participants (may be empty ) + QValueListConstIterator<QString> end = recipientDNList.end(); + for ( QValueListConstIterator<QString> it = recipientDNList.begin(); it != end; ++it ) + lst.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_DN, *it ) ); + createTransfer( "sendmessage", lst ); +} diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/sendmessagetask.h b/kopete/protocols/groupwise/libgroupwise/tasks/sendmessagetask.h new file mode 100644 index 00000000..f45e491f --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/sendmessagetask.h @@ -0,0 +1,41 @@ +/* + Kopete Groupwise Protocol + sendmessagetask.h - sends a message to a conference + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef SENDMESSAGETASK_H +#define SENDMESSAGETASK_H + +#include "client.h" +#include "requesttask.h" + +/** +Sends messages to a particular conference on the server + +@author SUSE AG +*/ +class SendMessageTask : public RequestTask +{ +public: + SendMessageTask(Task* parent); + ~SendMessageTask(); + + void message( const QStringList & recipientDNList, const OutgoingMessage & msg ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/setstatustask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/setstatustask.cpp new file mode 100644 index 00000000..0744ff8a --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/setstatustask.cpp @@ -0,0 +1,69 @@ +/* + Kopete Groupwise Protocol + setstatustask.cpp - Sets our status on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "setstatustask.h" + +using namespace GroupWise; + +SetStatusTask::SetStatusTask(Task* parent): RequestTask(parent) +{ +} + +SetStatusTask::~SetStatusTask() +{ +} + +void SetStatusTask::status( Status newStatus, const QString &awayMessage, const QString &autoReply ) +{ + if ( newStatus > GroupWise::Invalid ) + { + setError( 1, "Invalid Status" ); + return; + } + + m_status = newStatus; + m_awayMessage = awayMessage; + m_autoReply = autoReply; + + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_STATUS, 0, NMFIELD_TYPE_UTF8, QString::number( newStatus ) ) ); + if ( !awayMessage.isNull() ) + lst.append( new Field::SingleField( NM_A_SZ_STATUS_TEXT, 0, NMFIELD_TYPE_UTF8, awayMessage ) ); + if ( !autoReply.isNull() ) + lst.append( new Field::SingleField( NM_A_SZ_MESSAGE_BODY, 0, NMFIELD_TYPE_UTF8, autoReply ) ); + createTransfer( "setstatus", lst ); +} + +Status SetStatusTask::requestedStatus() const +{ + return m_status; +} + +QString SetStatusTask::awayMessage() const +{ + return m_awayMessage; +} + +QString SetStatusTask::autoReply() const +{ + return m_autoReply; +} + +#include "setstatustask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/setstatustask.h b/kopete/protocols/groupwise/libgroupwise/tasks/setstatustask.h new file mode 100644 index 00000000..2d3c53d7 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/setstatustask.h @@ -0,0 +1,46 @@ +/* + Kopete Groupwise Protocol + setstatustask.h - Sets our status on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef SETSTATUSTASK_H +#define SETSTATUSTASK_H + +#include "gwerror.h" +#include "requesttask.h" + +/** +@author Kopete Developers +*/ +class SetStatusTask : public RequestTask +{ +Q_OBJECT +public: + SetStatusTask(Task* parent); + ~SetStatusTask(); + void status( GroupWise::Status newStatus, const QString &awayMessage, const QString &autoReply ); + GroupWise::Status requestedStatus() const; + QString awayMessage() const; + QString autoReply() const; +private: + GroupWise::Status m_status; + QString m_awayMessage; + QString m_autoReply; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/statustask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/statustask.cpp new file mode 100644 index 00000000..8f8eccd4 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/statustask.cpp @@ -0,0 +1,47 @@ +/* + Kopete Groupwise Protocol + statustask.cpp - Event handling task responsible for status change events + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "client.h" + +#include "statustask.h" + +StatusTask::StatusTask(Task* parent): EventTask(parent) +{ + registerEvent( GroupWise::StatusChange ); +} + +StatusTask::~StatusTask() +{ +} + +bool StatusTask::take( Transfer * transfer ) +{ + EventTransfer * event; + if ( forMe( transfer, event ) ) + { + client()->debug( "Got a status change!" ); + client()->debug( QString( "%1 changed status to %2, message: %3" ).arg( event->source() ).arg( event->status() ).arg( event->statusText() ) ); + emit gotStatus( event->source().lower(), event->status(), event->statusText() ); + return true; + } + else + return false; +} +#include "statustask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/statustask.h b/kopete/protocols/groupwise/libgroupwise/tasks/statustask.h new file mode 100644 index 00000000..8e4994ff --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/statustask.h @@ -0,0 +1,40 @@ +/* + Kopete Groupwise Protocol + statustask.h - Event handling task responsible for status change events + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef STATUSTASK_H +#define STATUSTASK_H + +#include "eventtask.h" + +/** +@author Kopete Developers +*/ +class StatusTask : public EventTask +{ +Q_OBJECT +public: + StatusTask(Task* parent); + ~StatusTask(); + bool take( Transfer * transfer ); +signals: + void gotStatus( const QString & contactId, Q_UINT16 status, const QString & statusText ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/tests/Makefile.am b/kopete/protocols/groupwise/libgroupwise/tasks/tests/Makefile.am new file mode 100644 index 00000000..6a10925b --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/tests/Makefile.am @@ -0,0 +1,7 @@ +INCLUDES = -I$(top_srcdir)/protocols/groupwise/libgroupwise/qca/src -I$(srcdir)/../../libgroupwise/ -I$(top_srcdir)/kopete/protocols/groupwise/libgroupwise/qca/src $(all_includes) +METASOURCES = AUTO +noinst_PROGRAMS = task_take_test + +task_take_test_LDADD = -lqt-mt ../../libgwtest.la + +task_take_test_SOURCES = task_take_test.cpp diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/tests/task_take_test.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/tests/task_take_test.cpp new file mode 100644 index 00000000..140e851f --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/tests/task_take_test.cpp @@ -0,0 +1,18 @@ +// +// C++ Implementation: task_take_test +// +// Description: +// +// +// Author: Kopete Developers <[email protected]>, (C) 2004 +// +// Copyright: See COPYING file that comes with this distribution +// +// + +//#include "requesttask.h" + +int main() +{ + // balls, root task requires client, will test in situ instead +} diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/typingtask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/typingtask.cpp new file mode 100644 index 00000000..b835c525 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/typingtask.cpp @@ -0,0 +1,44 @@ +/* + Kopete Groupwise Protocol + typingtask.cpp - sends typing notifications to the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +//#include "eventtransfer.h" + +#include "typingtask.h" + +TypingTask::TypingTask(Task* parent): RequestTask(parent) +{ +} + + +TypingTask::~TypingTask() +{ +} + +void TypingTask::typing( const GroupWise::ConferenceGuid & conferenceGuid, const bool typing ) +{ + Field::FieldList typingNotification, outgoingList; + typingNotification.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, conferenceGuid ) ); + typingNotification.append( new Field::SingleField( NM_A_SZ_TYPE, 0, NMFIELD_TYPE_UTF8, + QString::number( typing ? GroupWise::UserTyping : GroupWise::UserNotTyping ) ) ); + outgoingList.append( new Field::MultiField( NM_A_FA_CONVERSATION, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, typingNotification ) ); + createTransfer( "sendtyping", outgoingList ); +} + +#include "typingtask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/typingtask.h b/kopete/protocols/groupwise/libgroupwise/tasks/typingtask.h new file mode 100644 index 00000000..4f4da1cd --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/typingtask.h @@ -0,0 +1,41 @@ +/* + Kopete Groupwise Protocol + typingtask.h - sends typing notifications to the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef TYPINGTASK_H +#define TYPINGTASK_H + +#include "requesttask.h" + +/** + Notifies the server that we are typing or are no longer typing in a particular conversation + +@author Kopete Developers +*/ +class TypingTask : public RequestTask +{ +Q_OBJECT + +public: + TypingTask(Task* parent); + ~TypingTask(); + void typing( const GroupWise::ConferenceGuid & guid, const bool typing ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/updatecontacttask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/updatecontacttask.cpp new file mode 100644 index 00000000..d8c1a68a --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/updatecontacttask.cpp @@ -0,0 +1,76 @@ +/* + Kopete Groupwise Protocol + updatecontacttask.cpp - rename a contact on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "gwfield.h" + +#include "updatecontacttask.h" + +using namespace GroupWise; + +UpdateContactTask::UpdateContactTask(Task* parent): UpdateItemTask(parent) +{ +} + + +UpdateContactTask::~UpdateContactTask() +{ +} + +QString UpdateContactTask::displayName() +{ + return m_name; +} + +void UpdateContactTask::renameContact( const QString & newName, const QValueList<ContactItem> & contactInstances ) +{ + m_name = newName; + // build a list of delete, add fields that removes each instance on the server and then readds it with the new name + Field::FieldList lst; + const QValueList<ContactItem>::ConstIterator end = contactInstances.end(); + for( QValueList<ContactItem>::ConstIterator it = contactInstances.begin(); it != end; ++it ) + { + Field::FieldList contactFields; + contactFields.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, (*it).id ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, (*it).parentId ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_SEQUENCE_NUMBER, 0, NMFIELD_TYPE_UTF8, (*it).sequence ) ); + if ( !(*it).dn.isNull() ) + contactFields.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, (*it).dn ) ); + if ( !(*it).displayName.isNull() ) + contactFields.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, (*it).displayName ) ); + lst.append( + new Field::MultiField( NM_A_FA_CONTACT, NMFIELD_METHOD_DELETE, 0, NMFIELD_TYPE_ARRAY, contactFields ) ); + } + for( QValueList<ContactItem>::ConstIterator it = contactInstances.begin(); it != end; ++it ) + { + Field::FieldList contactFields; + contactFields.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, (*it).id ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, (*it).parentId ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_SEQUENCE_NUMBER, 0, NMFIELD_TYPE_UTF8, (*it).sequence ) ); + if ( !(*it).dn.isNull() ) + contactFields.append( new Field::SingleField( NM_A_SZ_DN, 0, NMFIELD_TYPE_UTF8, (*it).dn ) ); + contactFields.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, newName ) ); + lst.append( + new Field::MultiField( NM_A_FA_CONTACT, NMFIELD_METHOD_ADD, 0, NMFIELD_TYPE_ARRAY, contactFields ) ); + } + //lst.dump( true ); + UpdateItemTask::item( lst ); +} + +#include "updatecontacttask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/updatecontacttask.h b/kopete/protocols/groupwise/libgroupwise/tasks/updatecontacttask.h new file mode 100644 index 00000000..7e6ac899 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/updatecontacttask.h @@ -0,0 +1,44 @@ +/* + Kopete Groupwise Protocol + updatecontacttask.h - rename a contact on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef UPDATECONTACTTASK_H +#define UPDATECONTACTTASK_H + +#include "gwerror.h" + +#include "updateitemtask.h" + +/** + * Renames a contact on the server + * @author Kopete Developers + */ +class UpdateContactTask : public UpdateItemTask +{ +Q_OBJECT +public: + UpdateContactTask(Task* parent); + ~UpdateContactTask(); + void renameContact( const QString& newName, const QValueList<GroupWise::ContactItem> & contactInstances ); + QString displayName(); +private: + QString m_name; +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/updatefoldertask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/updatefoldertask.cpp new file mode 100644 index 00000000..fef5d2fe --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/updatefoldertask.cpp @@ -0,0 +1,59 @@ +/* + Kopete Groupwise Protocol + updatefoldertask.cpp - rename a folder on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ +#include "gwfield.h" + +#include "updatefoldertask.h" + +UpdateFolderTask::UpdateFolderTask(Task* parent): UpdateItemTask(parent) +{ +} + +UpdateFolderTask::~UpdateFolderTask() +{ +} + +void UpdateFolderTask::renameFolder( const QString & newName, const GroupWise::FolderItem & existing ) +{ + Field::FieldList lst; + // add the old version of the folder, marked delete + lst.append( new Field::MultiField( NM_A_FA_FOLDER, NMFIELD_METHOD_DELETE, 0, NMFIELD_TYPE_ARRAY, folderToFields( existing) ) ); + + GroupWise::FolderItem renamed = existing; + renamed.name = newName; + // add the new version of the folder, marked add + lst.append( new Field::MultiField( NM_A_FA_FOLDER, NMFIELD_METHOD_ADD, 0, NMFIELD_TYPE_ARRAY, folderToFields( renamed ) ) ); + // let our parent class package it up as a contactlist in a transfer + UpdateItemTask::item( lst ); +} + +Field::FieldList UpdateFolderTask::folderToFields( const GroupWise::FolderItem & folder ) +{ + Field::FieldList lst; + lst.append( new Field::SingleField( NM_A_SZ_OBJECT_ID, 0, NMFIELD_TYPE_UTF8, folder.id ) ); + lst.append( new Field::SingleField( NM_A_SZ_PARENT_ID, 0, NMFIELD_TYPE_UTF8, 0 ) ); + lst.append( new Field::SingleField( NM_A_SZ_TYPE, 0, NMFIELD_TYPE_UTF8, 1 ) ); + lst.append( new Field::SingleField( NM_A_SZ_SEQUENCE_NUMBER, 0, NMFIELD_TYPE_UTF8, folder.sequence ) ); + if ( !folder.name.isEmpty() ) + lst.append( new Field::SingleField( NM_A_SZ_DISPLAY_NAME, 0, NMFIELD_TYPE_UTF8, folder.name ) ); + return lst; +} + +#include "updatefoldertask.moc" + diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/updatefoldertask.h b/kopete/protocols/groupwise/libgroupwise/tasks/updatefoldertask.h new file mode 100644 index 00000000..230bd563 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/updatefoldertask.h @@ -0,0 +1,42 @@ +/* + Kopete Groupwise Protocol + updatefoldertask.h - rename a folder on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef UPDATEFOLDERTASK_H +#define UPDATEFOLDERTASK_H + +#include <updateitemtask.h> + +/** +Renames a folder on the server + +@author Kopete Developers +*/ +class UpdateFolderTask : public UpdateItemTask +{ +Q_OBJECT +public: + UpdateFolderTask(Task* parent); + ~UpdateFolderTask(); + void renameFolder( const QString & newName, const GroupWise::FolderItem & existing ); +protected: + Field::FieldList folderToFields( const GroupWise::FolderItem & folder ); +}; + +#endif diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/updateitemtask.cpp b/kopete/protocols/groupwise/libgroupwise/tasks/updateitemtask.cpp new file mode 100644 index 00000000..1af4ef12 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/updateitemtask.cpp @@ -0,0 +1,39 @@ +/* + Kopete Groupwise Protocol + updateitemtask.cpp - ancestor for tasks that rename objects on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#include "updateitemtask.h" + +UpdateItemTask::UpdateItemTask( Task* parent) : RequestTask( parent ) +{ +} + + +UpdateItemTask::~UpdateItemTask() +{ +} + +void UpdateItemTask::item( Field::FieldList updateItemFields ) +{ + Field::FieldList lst; + lst.append( new Field::MultiField( NM_A_FA_CONTACT_LIST, NMFIELD_METHOD_VALID, 0, NMFIELD_TYPE_ARRAY, updateItemFields ) ); + createTransfer( "updateitem", lst ); +} + +#include "updateitemtask.moc" diff --git a/kopete/protocols/groupwise/libgroupwise/tasks/updateitemtask.h b/kopete/protocols/groupwise/libgroupwise/tasks/updateitemtask.h new file mode 100644 index 00000000..a087d276 --- /dev/null +++ b/kopete/protocols/groupwise/libgroupwise/tasks/updateitemtask.h @@ -0,0 +1,40 @@ +/* + Kopete Groupwise Protocol + updateitemtask.h - ancestor for tasks that rename objects on the server + + Copyright (c) 2004 SUSE Linux AG http://www.suse.com + + Based on Iris, Copyright (C) 2003 Justin Karneges + + Kopete (c) 2002-2004 by the Kopete developers <[email protected]> + + ************************************************************************* + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Lesser General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + ************************************************************************* +*/ + +#ifndef UPDATEITEMTASK_H +#define UPDATEITEMTASK_H + +#include "requesttask.h" + +/** +Rename a folder or contact on the server. In future may be used for changing the order of folders or contacts relative to one another, but this is not supported by Kopete yet. + +@author SUSE AG +*/ +class UpdateItemTask : public RequestTask +{ +Q_OBJECT +public: + UpdateItemTask( Task* parent ); + ~UpdateItemTask(); + void item( Field::FieldList updateItemFields ); +}; + +#endif |