2 * This file is part of TpSession
4 * Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
5 * Contact Kate Alhola kate.alholanokia.com
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21 #include "tpsessionaccount.h"
22 #include <TelepathyQt4/Message>
24 TpSessionAccount::TpSessionAccount(Tp::AccountManagerPtr am,const QString &objectPath):
25 mAcc(Tp::Account::create(am->dbusConnection(),am->busName(), objectPath))
28 connect(mAcc->becomeReady(),SIGNAL(finished(Tp::PendingOperation *)),SLOT(onReady(Tp::PendingOperation *)));
30 qDebug() << "TpSessionAccount::TpSessionAccount objectPath=" << objectPath;
34 void TpSessionAccount::onReady(Tp::PendingOperation *op)
38 qDebug() << "TpSessionAccount::onReady cmName=" << acc->cmName() << "haveConnection=" <<
39 (acc->haveConnection()? ( acc->connection()->isReady() ? "Ready":"notReady"):"no");
41 if(acc->haveConnection()) {
43 connect(acc->connection()->becomeReady(Tp::Connection::FeatureRoster | Tp::Connection::FeatureSelfContact ),
44 SIGNAL(finished(Tp::PendingOperation *)),
45 SLOT(onContactsConnectionReady(Tp::PendingOperation *)));
46 if (acc->connection()->isReady() && acc->connection()->interfaces().contains(TELEPATHY_INTERFACE_CONNECTION_INTERFACE_REQUESTS)) {
47 qDebug() << "TpSessionAccount::onReady: connecting to Connection.Interface.NewChannels";
48 connect(acc->connection()->requestsInterface(),
49 SIGNAL(NewChannels(const Tp::ChannelDetailsList&)),
50 SLOT(onNewChannels(const Tp::ChannelDetailsList&)));
53 else { // If there is no connection, we are ready now, else we are ready when contacts connection is ready
55 emit accountReady(this);
59 void TpSessionAccount::onContactsConnectionReady(Tp::PendingOperation *op)
62 qWarning() << "Connection cannot become ready" << acc->cmName();
66 if (acc->connection()->interfaces().contains(TELEPATHY_INTERFACE_CONNECTION_INTERFACE_REQUESTS)) {
67 qDebug() << "TpSessionAccount::onContactsConectionReady: connecting to Connection.Interface.NewChannels";
68 connect(acc->connection()->requestsInterface(),
69 SIGNAL(NewChannels(const Tp::ChannelDetailsList&)),
70 SLOT(onNewChannels(const Tp::ChannelDetailsList&)));
71 } else qDebug() << "TpSessionAccount::onContactsConnectionReady: does NO have CONNECTION_INTERFACE_REQUESTS";
72 Tp::PendingReady *pr = qobject_cast<Tp::PendingReady *>(op);
73 contactsConn = Tp::ConnectionPtr(qobject_cast<Tp::Connection *>(pr->object()));
75 connect(contactsConn->contactManager(),
76 SIGNAL(presencePublicationRequested(const Tp::Contacts &)),
77 SLOT(onPresencePublicationRequested(const Tp::Contacts &)));
79 qDebug() << "TpSessionAccount::onContactsConnectionReady "<< acc->cmName() ;
82 myContacts=contactsConn->contactManager()->allKnownContacts();
83 foreach (const Tp::ContactPtr &contact, myContacts) {
84 qDebug() << "id=" <<contact->id() << " alias=" << contact->alias() << " presence=" << contact->presenceStatus() ;
85 if(contact->id()==reqContact) {
86 addOutgoingChannel(contact);
90 if(!reqContact.isEmpty() ) makeContactFromAddress(reqContact);
92 emit accountReady(this);
95 Tp::ContactPtr TpSessionAccount::getContactFromAddress(QString id)
98 foreach (const Tp::ContactPtr &contact, myContacts) {
99 if(contact->id()==reqContact) return p=contact;
104 TpSessionChannel* TpSessionAccount::getChannelFromPeerAddress(QString id)
106 TpSessionChannel* p=NULL;
107 foreach (TpSessionChannel* channel, myChannels) {
108 if(channel->peerId()==id) return p=channel;
113 void TpSessionAccount::makeContactFromAddress(QString address)
115 reqContact=address; // When we get retrieved signal, we check if it is this one
116 Tp::PendingContacts *pc=contactsConn->contactManager()->contactsForIdentifiers(QStringList(address));
117 connect(pc,SIGNAL(finished(Tp::PendingOperation *)),SLOT(onNewContactRetrieved(Tp::PendingOperation *)));
120 void TpSessionAccount::onNewContactRetrieved(Tp::PendingOperation *op)
122 Tp::PendingContacts *pcontacts = qobject_cast<Tp::PendingContacts *>(op);
123 QList<Tp::ContactPtr> contacts = pcontacts->contacts();
124 QString username = pcontacts->identifiers().first();
125 if (contacts.size() != 1 || !contacts.first()) {
126 qDebug() << "Unable to add contact " <<reqContact;
130 Tp::ContactPtr contact = contacts.first();
131 qDebug() << "TpSessionAccount::onContactRetrieved" << reqContact;
132 if(!reqContact.isEmpty()) addOutgoingChannel(contacts.first());
135 void TpSessionAccount::sendMessageToAddress(QString address,QString message)
138 TpSessionChannel* channel=getChannelFromPeerAddress(address);
140 channel->sendMessage(message); // We have already channel
143 p=getContactFromAddress(address); // Do we have contact ready ?
144 if(p.isNull()) // If not, create it
145 makeContactFromAddress(address); // Create and after created, send
147 addOutgoingChannel(p); // Create channel and when ready, send
151 void TpSessionAccount::addOutgoingChannel(const Tp::ContactPtr &contact)
155 qDebug() << "TpSessionAccount::addOutgoingChannel";
157 TpSessionChannel* newChannel=new TpSessionChannel(contact->manager()->connection(),contact);
158 connect(newChannel,SIGNAL(messageReceived(const Tp::ReceivedMessage &,TpSessionChannel *)),
159 SLOT(onMessageReceived(const Tp::ReceivedMessage &,TpSessionChannel *)));
160 connect(newChannel,SIGNAL(channelReady(TpSessionChannel *)),
161 SLOT(onOutgoingChannelReady(TpSessionChannel*)));
162 myChannels+=newChannel;
166 void TpSessionAccount::onOutgoingChannelReady(TpSessionChannel *ch)
168 qDebug() << "TpSessionAccoiunt::onOutgoingChannelReady";
169 emit channelReady(this);
170 if(!reqMessage.isEmpty()) ch->sendMessage(reqMessage);
175 void TpSessionAccount::onMessageSent(const Tp::Message &msg,Tp::MessageSendingFlags, const QString &flags)
177 qDebug() << "TpSessionAccount::onMessageSent";
180 void TpSessionAccount::onMessageReceived(const Tp::ReceivedMessage &msg,TpSessionChannel *ch)
182 qDebug() << "TpSessionAccount::onMessageReceived " << msg.text();
183 emit messageReceived(msg,this);
186 void TpSessionAccount::onNewChannels(const Tp::ChannelDetailsList &channels)
189 Tp::TextChannelPtr myIngoingTextChannel;
190 qDebug() << "TpSessionAccount::onNewChannels";
191 foreach (const Tp::ChannelDetails &details, channels) {
192 QString channelType = details.properties.value(QLatin1String(TELEPATHY_INTERFACE_CHANNEL ".ChannelType")).toString();
193 bool requested = details.properties.value(QLatin1String(TELEPATHY_INTERFACE_CHANNEL ".Requested")).toBool();
194 qDebug() << " channelType:" << channelType;
195 qDebug() << " requested :" << requested;
197 if (channelType == TELEPATHY_INTERFACE_CHANNEL_TYPE_TEXT && !requested) {
199 myIngoingTextChannel = Tp::TextChannel::create(acc->connection(),details.channel.path(),details.properties);
200 qDebug() << "TpSessionAccount::onNewChannels path=" <<"path " << myIngoingTextChannel->objectPath();
202 TpSessionChannel* newChannel=new TpSessionChannel( myIngoingTextChannel);
203 connect(newChannel,SIGNAL(messageReceived(const Tp::ReceivedMessage &,TpSessionChannel *)),
204 SLOT(onMessageReceived(const Tp::ReceivedMessage &,TpSessionChannel *)));
205 myChannels+=newChannel;