Imported Upstream version 1.3.99.3~20130529~SE~b989f69~SYSYNC~3366831
[platform/upstream/syncevolution.git] / src / dbus / server / presence-status.cpp
1 /*
2  * Copyright (C) 2011 Intel Corporation
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) version 3.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17  * 02110-1301  USA
18  */
19
20 #include "presence-status.h"
21 #include "server.h"
22
23 SE_BEGIN_CXX
24
25 void PresenceStatus::init(){
26     //initialize the configured peer list
27     if (!m_initiated) {
28         SyncConfig::ConfigList list = SyncConfig::getConfigs();
29         BOOST_FOREACH(const SyncConfig::ConfigList::value_type &server, list) {
30             SyncConfig config (server.first);
31             vector<string> urls = config.getSyncURL();
32             m_peers[server.first].clear();
33             BOOST_FOREACH (const string &url, urls) {
34                 // take current status into account,
35                 // PresenceStatus::checkPresence() calls init() and
36                 // expects up-to-date information
37                 PeerStatus status;
38                 if ((boost::starts_with(url, "obex-bt") && m_btPresence) ||
39                     (boost::starts_with (url, "http") && m_httpPresence) ||
40                     boost::starts_with (url, "local")) {
41                     status = MIGHTWORK;
42                 } else {
43                     status = NOTRANSPORT;
44                 }
45                 m_peers[server.first].push_back(make_pair(url, status));
46             }
47         }
48         m_initiated = true;
49     }
50 }
51
52 /* Implement PresenceStatus::checkPresence*/
53 void PresenceStatus::checkPresence (const string &peer, string& status, std::vector<std::string> &transport) {
54
55     if (!m_initiated) {
56         //might triggered by updateConfigPeers
57         init();
58     }
59
60     string peerName = SyncConfig::normalizeConfigString (peer);
61     vector< pair<string, PeerStatus> > mytransports = m_peers[peerName];
62     if (mytransports.empty()) {
63         //wrong config name?
64         status = status2string(NOTRANSPORT);
65         transport.clear();
66         return;
67     }
68     PeerStatus mystatus = MIGHTWORK;
69     transport.clear();
70     //only if all transports are unavailable can we declare the peer
71     //status as unavailable
72     BOOST_FOREACH (PeerStatusPair &mytransport, mytransports) {
73         if (mytransport.second == MIGHTWORK) {
74             transport.push_back (mytransport.first);
75         }
76     }
77     if (transport.empty()) {
78         mystatus = NOTRANSPORT;
79     }
80     status = status2string(mystatus);
81 }
82
83 void PresenceStatus::updateConfigPeers (const std::string &peer, const ReadOperations::Config_t &config) {
84     ReadOperations::Config_t::const_iterator iter = config.find ("");
85     if (iter != config.end()) {
86         //As a simple approach, just reinitialize the whole STATUSMAP
87         //it will cause later updatePresenceStatus resend all signals
88         //and a reload in checkPresence
89         m_initiated = false;
90     }
91 }
92
93 void PresenceStatus::updatePresenceStatus (bool newStatus, PresenceStatus::TransportType type) {
94     if (type == PresenceStatus::HTTP_TRANSPORT) {
95         updatePresenceStatus (newStatus, m_btPresence);
96     } else if (type == PresenceStatus::BT_TRANSPORT) {
97         updatePresenceStatus (m_httpPresence, newStatus);
98     }else {
99     }
100 }
101
102 void PresenceStatus::updatePresenceStatus (bool httpPresence, bool btPresence) {
103     bool httpChanged = (m_httpPresence != httpPresence);
104     bool btChanged = (m_btPresence != btPresence);
105     if (m_initiated && !httpChanged && !btChanged) {
106         //nothing changed
107         return;
108     }
109
110     //initialize the configured peer list using old presence status
111     bool initiated = m_initiated;
112     if (!m_initiated) {
113         init();
114     }
115
116     // switch to new status
117     m_httpPresence = httpPresence;
118     m_btPresence = btPresence;
119     if (httpChanged) {
120         m_httpPresenceSignal(httpPresence);
121     }
122     if (btChanged) {
123         m_btPresenceSignal(btPresence);
124     }
125
126
127     //iterate all configured peers and fire singals
128     BOOST_FOREACH (StatusPair &peer, m_peers) {
129         //iterate all possible transports
130         //TODO One peer might got more than one signals, avoid this
131         std::vector<pair<string, PeerStatus> > &transports = peer.second;
132         BOOST_FOREACH (PeerStatusPair &entry, transports) {
133             string url = entry.first;
134             if (boost::starts_with (url, "http") && (httpChanged || !initiated)) {
135                 entry.second = m_httpPresence ? MIGHTWORK: NOTRANSPORT;
136                 m_server.emitPresence (peer.first, status2string (entry.second), entry.first);
137                 SE_LOG_DEBUG(NULL,
138                         "http presence signal %s,%s,%s",
139                         peer.first.c_str(),
140                         status2string (entry.second).c_str(), entry.first.c_str());
141             } else if (boost::starts_with (url, "obex-bt") && (btChanged || !initiated)) {
142                 entry.second = m_btPresence ? MIGHTWORK: NOTRANSPORT;
143                 m_server.emitPresence (peer.first, status2string (entry.second), entry.first);
144                 SE_LOG_DEBUG(NULL,
145                         "bluetooth presence signal %s,%s,%s",
146                         peer.first.c_str(),
147                         status2string (entry.second).c_str(), entry.first.c_str());
148             } else if (boost::starts_with (url, "local") && !initiated) {
149                 m_server.emitPresence (peer.first, status2string (MIGHTWORK), entry.first);
150                 SE_LOG_DEBUG(NULL,
151                         "local presence signal %s,%s,%s",
152                         peer.first.c_str(),
153                         status2string (MIGHTWORK).c_str(), entry.first.c_str());
154             }
155         }
156     }
157 }
158
159 SE_END_CXX