d90fc39513b21e4e2c41dd430c273aca8ccbf610
[situare] / src / situareservice / situareservice.h
1 /*
2    Situare - A location system for Facebook
3    Copyright (C) 2010  Ixonos Plc. Authors:
4
5       Henri Lampela - henri.lampela@ixonos.com
6       Jussi Laitinen - jussi.laitinen@ixonos.com
7       Sami Rämö - sami.ramo@ixonos.com
8
9    Situare is free software; you can redistribute it and/or
10    modify it under the terms of the GNU General Public License
11    version 2 as published by the Free Software Foundation.
12
13    Situare is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with Situare; if not, write to the Free Software
20    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301,
21    USA.
22 */
23
24
25 #ifndef SITUARESERVICE_H
26 #define SITUARESERVICE_H
27
28 #include <QObject>
29
30 #include "../user/user.h"
31 #include "imagefetcher.h"
32 #include "message.h"
33
34 class Database;
35 class NetworkAccessManager;
36 class QNetworkReply;
37 class QNetworkRequest;
38 class GeoCoordinate;
39 class QUrl;
40
41 /**
42 * @brief SituareService class for communicating with Situare server
43 *
44 * @author Henri Lampela
45 * @author Jussi Laitinen - jussi.laitinen (at) ixonos.com
46 * @author Sami Rämö - sami.ramo (at) ixonos.com
47 */
48 class SituareService : public QObject
49 {
50     Q_OBJECT
51
52 private:
53     /**
54     * @brief Request name enum
55     */
56     enum RequestName { RequestUnknown,
57                        RequestGetLocations,
58                        RequestUpdateLocation,
59                        RequestReverseGeo,
60                        RequestGetMessages,
61                        RequestRemoveMessage,
62                        RequestSendMessage,
63                        RequestGetPeopleWithSimilarInterest,
64                        RequestGetPopularTags,
65                        RequestAddTags,
66                        RequestGetTags,
67                        RequestRemoveTags,
68                        RequestGetPeopleWithTag };
69
70 public:
71
72     /**
73     * Unit test class
74     */
75     friend class TestSituareService;
76
77     enum SuccessfulMethod {SuccessfulUpdateLocation, SuccessfulAddTags, SuccessfulRemoveTags,
78                            SuccessfulSendMessage, SuccessfulRemoveMessage};
79
80     /**
81     * @brief Default constructor
82     *
83     * @param parent instance of parent
84     */
85     SituareService(NetworkAccessManager *networkManager, ImageFetcher *imageFetcher,
86                    QObject *parent = 0);
87
88     /**
89     * @brief Destructor
90     *
91     */
92     ~SituareService();
93
94 /*******************************************************************************
95  * MEMBER FUNCTIONS AND SLOTS
96  ******************************************************************************/
97     /**
98     * @brief Retriesves user tags.
99     *
100     * @return QStringList list of tags
101     */
102     void getTags();
103
104     /**
105     * @brief Retrieves people with similart interest (same tags).
106     *
107     * People is searched from area defined by maximum distance
108     * @param maximumDistance maximum distance to people
109     */
110     void fetchPeopleWithSimilarInterest(const qreal distance);
111
112     /**
113     * @brief Retrieves location user and friends information from Situare server
114     *
115     */
116     void fetchLocations();
117
118     /**
119     * @brief Translates coordinates to street address via Situare server
120     *
121     * @param coordinates coordinates to be translated
122     */
123     void reverseGeo(const GeoCoordinate &coordinates);
124
125     /**
126     * @brief Updates location to the Situare server
127     *
128     * @param coordinates current cordinates
129     * @param status message
130     * @param publish publish location on Facebook wall
131     */
132     void updateLocation(const GeoCoordinate &coordinates, const QString &status, const bool &publish);
133
134 public slots:
135     /**
136     * @brief Adds tags to the Situare server
137     *
138     * CURRENTLY TAGS ARE UPDATED TO THE LOCAL DATABASE, NOT SITUARE SERVER
139     * @param tags list of user's tags
140     */
141     void addTags(const QStringList &tags);
142
143     /**
144     * @brief Public slot, to clear user data
145     *
146     */
147     void clearUserData();
148
149     /**
150     * @brief Retrieves messages sent to user.
151     */
152     void fetchMessages();
153
154     /**
155     * @brief Retrieves popular tags.
156     *
157     * Tags are fetch from local database instead of Situare server.
158     */
159     void fetchPopularTags();
160
161     /**
162     * @brief Removes message.
163     *
164     * @param id message ID
165     */
166     void removeMessage(const QString &id);
167
168     /**
169     * @brief Removes tags.
170     *
171     * @param tags list of tags to remove
172     */
173     void removeTags(const QStringList &tags);
174
175     /**
176     * @brief Public slot, which indicates when http request has been completed
177     *
178     * @param reply storage for http reply
179     */
180     void requestFinished(QNetworkReply *reply);
181
182     /**
183     * @brief Searches people by tag name.
184     *
185     * @param tag tag name
186     */
187     void searchPeopleByTag(const QString &tag);
188
189     /**
190     * @brief Sends a message to a person.
191     *
192     * @param receiverId Facebook user ID
193     * @param message message text
194     * @param message coordinates
195     */
196     void sendMessage(const QString &receiverId, const QString &message,
197                      const GeoCoordinate &coordinates = GeoCoordinate());
198
199     /**
200       * @brief Update session data
201       *
202       * @param session New session data
203       */
204     void updateSession(const QString &session);
205
206 private:
207     /**
208     * @brief Requests ImageFetcher if user/friend has a profile image
209     *        uses members: m_user and m_friendsList
210     *
211     * @param imageUrlList list of image urls
212     */
213     void addProfileImages(const QHash<QString, QUrl> &imageUrlList);
214
215     /**
216       * @brief Append access_token and other session data to the reques url
217       *
218       * @param[in,out] requestUrl Request URL with other request parameters and ending to &
219       */
220     void appendAccessToken(QString &requestUrl);
221
222     /**
223       * @brief Build and send request
224       *
225       * Appends script pathname and parameters to the server base URL. Access token is appended and
226       * the request sent if the access token is available, otherwise the request is queued.
227       *
228       * @param script Requested script pathname
229       * @param parameters Hash containing parameter key/value pairs.
230       */
231     void buildRequest(const QString &script, const QHash<QString,QString> &parameters);
232
233     /**
234       * @brief Convert coordinate value in degrees (double) to string with enough precision
235       *
236       * @param degrees Coordinate value in degrees
237       * @returns Coordinate value as string
238       */
239     QString degreesToString(double degrees);
240     
241     /**
242     * @brief Returns reuquest script's name.
243     *
244     * @param url url to check
245     * @return RequestName
246     */
247     SituareService::RequestName getRequestName(const QUrl &url) const;
248
249     /**
250     * @brief Parses interesting people data from JSON string
251     *
252     * @param interestingPeopleData interesting people data QVariant tree
253     */
254     void parseInterestingPeopleData(const QVariant &interestingPeopleData);
255
256     /**
257     * @brief Parses messages data from JSON string
258     *
259     * @param messagesData messages data QVariant tree
260     */
261     void parseMessagesData(const QVariant &messagesData);
262
263     /**
264     * @brief Parses popular tags data from JSON string
265     *
266     * @param popularTagsData popular tags data QVariant tree
267     */
268     void parsePopularTagsData(const QVariant &popularTagsData);
269
270     /**
271     * @brief Parses reply from JSON string
272     *
273     * Calls different parse methods or emits error signal if response contains error status.
274     */
275     void parseReply(const QByteArray &jsonReply, RequestName requestName);
276
277     /**
278     * @brief Parses reverse geo data
279     *
280     * @param reverseGeoData reverse geo data QVariant tree
281     */
282     void parseReverseGeoData(const QVariant &reverseGeoData);
283
284     /**
285     * @brief Parses user tags data from JSON string
286     *
287     * @param userTagsData user tags data QVariant tree
288     */
289     void parseUserTagsData(const QVariant &userTagsData);
290
291     /**
292     * @brief Parses user and friend data from JSON string
293     *
294     * @param userData user data QVariant tree
295     */
296     void parseUserData(const QVariant &userData);
297
298     /**
299       * @brief Send request
300       *
301       * @param requestUrl Request URL containing also all parameters
302       */
303     void sendRequest(const QString &requestUrl);
304
305 private slots:
306     /**
307     * @brief Slot for received images
308     *
309     * @param id image ID
310     * @param image image pixmap
311     */
312     void imageReceived(const QString &id, const QPixmap &image);
313
314 /*******************************************************************************
315  * SIGNALS
316  ******************************************************************************/
317 signals:
318     /**
319     * @brief Signals error
320     *
321     * @param context error context
322     * @param error error code
323     */
324     void error(const int context, const int error);
325
326     /**
327     * @brief Signal for image fetching
328     *
329     * @param id Image id
330     * @param url Image url
331     */
332     void fetchImage(const QString &id, const QUrl &url);
333
334     /**
335     * @brief Signals when image is downloaded
336     *
337     * @param id image ID
338     * @param image image pixmap
339     */
340     void imageReady(const QString &id, const QPixmap &image);
341
342     /**
343     * @brief Signal when fetchPeopleWithSimilarInterest request is finished
344     *
345     * @param friends list of friends
346     * @param others list of other people
347     */
348     void interestingPeopleReceived(QList<User> &friends, QList<User> &others);
349
350     /**
351     * @brief Signal when fetchMessages request is finished
352     *
353     * @param messages list of messages sent to user
354     */
355     void messagesReceived(QList<Message> &received, QList<Message> &sent);
356
357     /**
358     * @brief Signals when fetchPopularTags request is finished
359     *
360     * @param popularTags list of popular tags
361     */
362     void popularTagsReceived(QHash<QString, QString> &popularTags);
363
364     /**
365     * @brief Signals when address data is retrieved
366     *
367     * @param address Street address
368     */
369     void reverseGeoReady(const QString &address);
370
371     /**
372     * @brief Signals when updateLocation request finished successfully
373     */
374     void updateWasSuccessful(SituareService::SuccessfulMethod successfulMethod);
375
376     /**
377     * @brief Signals when user data is retrieved
378     *
379     * @param user instance of user
380     * @param friendList list of friends
381     */
382     void userDataChanged(User *user, QList<User *> &friendList);
383
384     /**
385     * @brief Signals when getTags request is finished
386     *
387     * @param userTags list of user tags
388     */
389     void userTagsReceived(QHash<QString, QString> &userTags);
390
391 /*******************************************************************************
392  * DATA MEMBERS
393  ******************************************************************************/
394 private:
395     bool m_defaultImage;    ///< Indicates if some of the friends/user doesn't have a image
396
397     QList<QNetworkReply *> m_currentRequests;       ///< List of current http requests
398     QList<User *> m_friendsList;                    ///< List of friends(User)
399
400     QString m_session;                          ///< Session data
401
402     Database *m_database;                       ///< Instance of the database
403     ImageFetcher *m_imageFetcher;               ///< Instance of the image fetcher    
404     NetworkAccessManager *m_networkManager;     ///< Pointer to QNetworkAccessManager
405     User *m_user;                               ///< Pointer to User
406 };
407
408 #endif // SITUARESERVICE_H