Merge lp:~gary-wzl77/mcloud/job_uuid into lp:mcloud/devel
- job_uuid
- Merge into devel
Status: | Merged |
---|---|
Approved by: | Zhang Enwei |
Approved revision: | 60 |
Merged at revision: | 16 |
Proposed branch: | lp:~gary-wzl77/mcloud/job_uuid |
Merge into: | lp:mcloud/devel |
Diff against target: |
8284 lines (+2819/-2895) 52 files modified
CMakeLists.txt (+1/-1) debian/VERSION (+1/-1) debian/VERSION.vivid (+1/-1) debian/changelog (+13/-2) debian/control (+2/-0) debian/control.in (+2/-0) debian/libmcloud0.install (+0/-3) debian/libmcloud1.install (+0/-3) debian/libmcloud2.install (+3/-0) include/mcloud/api/client.h (+32/-34) include/mcloud/api/cloudcontent.h (+18/-18) include/mcloud/api/cloudfolder.h (+14/-14) include/mcloud/api/cloudresource.h (+13/-13) include/mcloud/api/diskinfo.h (+7/-6) include/mcloud/api/downloadtask.h (+16/-19) include/mcloud/api/exceptions.h (+49/-49) include/mcloud/api/outlink.h (+9/-9) include/mcloud/api/syncmanager.h (+12/-12) include/mcloud/api/task.h (+10/-10) include/mcloud/api/taskqueue.h (+11/-10) include/mcloud/api/uploadtask.h (+18/-22) provider/CMakeLists.txt (+2/-2) provider/McloudProvider.cpp (+0/-666) provider/McloudProvider.h (+0/-82) provider/main.cpp (+10/-12) provider/mcloudprovider.cpp (+648/-0) provider/mcloudprovider.h (+82/-0) src/mcloud/api/client.cpp (+45/-53) src/mcloud/api/client_priv.cpp (+628/-632) src/mcloud/api/client_priv.h (+63/-63) src/mcloud/api/cloudcontent.cpp (+53/-50) src/mcloud/api/cloudfolder.cpp (+40/-38) src/mcloud/api/diskinfo.cpp (+8/-5) src/mcloud/api/downloadtask.cpp (+10/-11) src/mcloud/api/downloadtask_priv.cpp (+44/-44) src/mcloud/api/downloadtask_priv.h (+28/-28) src/mcloud/api/outlink.cpp (+11/-8) src/mcloud/api/syncmanager.cpp (+10/-7) src/mcloud/api/syncmanager_priv.cpp (+6/-10) src/mcloud/api/syncmanager_priv.h (+10/-11) src/mcloud/api/syncthread.cpp (+107/-116) src/mcloud/api/syncthread.h (+3/-3) src/mcloud/api/taskhandler.h (+32/-24) src/mcloud/api/uploadtask.cpp (+10/-11) src/mcloud/api/uploadtask_priv.cpp (+46/-46) src/mcloud/api/uploadtask_priv.h (+33/-33) tests/server/server.py (+1/-1) tests/unit/mcloud-provider/CMakeLists.txt (+1/-1) tests/unit/mcloud-provider/mcloud-provider-unit-tests.cpp (+133/-163) tests/unit/mcloud/CMakeLists.txt (+0/-3) tests/unit/mcloud/api/mcloud-rest-test.cpp (+217/-233) tests/unit/mcloud/api/mcloud-sync-test.cpp (+306/-312) |
To merge this branch: | bzr merge lp:~gary-wzl77/mcloud/job_uuid |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
unity-api-1-bot | continuous-integration | Approve | |
Zhang Enwei (community) | Approve | ||
Review via email: mp+308474@code.launchpad.net |
Commit message
1.generate job id with uuid.
2.reduce the size of temporary generated file.
Description of the change
1.generate job id with uuid.
2.reduce the size of temporary generated file.
unity-api-1-bot (unity-api-1-bot) wrote : | # |
unity-api-1-bot (unity-api-1-bot) wrote : | # |
PASSED: Continuous integration, rev:56
https:/
Executed test runs:
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
Click here to trigger a rebuild:
https:/
unity-api-1-bot (unity-api-1-bot) wrote : | # |
PASSED: Continuous integration, rev:60
https:/
Executed test runs:
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
Click here to trigger a rebuild:
https:/
Preview Diff
1 | === modified file 'CMakeLists.txt' |
2 | --- CMakeLists.txt 2016-09-17 14:21:57 +0000 |
3 | +++ CMakeLists.txt 2016-10-26 10:36:06 +0000 |
4 | @@ -28,7 +28,7 @@ |
5 | set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -Werror -Wall -fno-strict-aliasing -fvisibility=hidden -fvisibility-inlines-hidden -pedantic -Wextra") |
6 | set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} -Wl,--no-undefined") |
7 | |
8 | -set(MCLOUD_LIB_VERSION_MAJOR 1) |
9 | +set(MCLOUD_LIB_VERSION_MAJOR 2) |
10 | set(MCLOUD_LIB_VERSION_MINOR 0) |
11 | set(MCLOUD_LIB_VERSION_PATCH 0) |
12 | |
13 | |
14 | === modified file 'debian/VERSION' |
15 | --- debian/VERSION 2016-09-17 14:21:57 +0000 |
16 | +++ debian/VERSION 2016-10-26 10:36:06 +0000 |
17 | @@ -1,1 +1,1 @@ |
18 | -1 |
19 | +2 |
20 | |
21 | === modified file 'debian/VERSION.vivid' |
22 | --- debian/VERSION.vivid 2016-09-17 14:21:57 +0000 |
23 | +++ debian/VERSION.vivid 2016-10-26 10:36:06 +0000 |
24 | @@ -1,1 +1,1 @@ |
25 | -0 |
26 | +1 |
27 | |
28 | === modified file 'debian/changelog' |
29 | --- debian/changelog 2016-09-17 14:21:57 +0000 |
30 | +++ debian/changelog 2016-10-26 10:36:06 +0000 |
31 | @@ -1,4 +1,12 @@ |
32 | -mcloud (1.0.0-0ubuntu1) UNRELEASED; urgency=medium |
33 | +mcloud (2.0.0-0ubuntu1) UNRELEASED; urgency=medium |
34 | + |
35 | + [ Gary.Wzl] |
36 | + * add missing dependency(account-plugin-mcloud) |
37 | + * generate job upload id with uuid. |
38 | + |
39 | + -- Gary.Wang <gary.wang@canonical.com> Wed, 26 Oct 2016 16:58:11 +0800 |
40 | + |
41 | +mcloud (1.0.0+16.10.20160927.3-0ubuntu1) yakkety; urgency=medium |
42 | |
43 | [ Gary Wang ] |
44 | * Update provider to enable data streaming directly without local cache. |
45 | @@ -29,4 +37,7 @@ |
46 | * Add status handler for download and upload task. |
47 | * Remove deprecated API(set_auth_info). |
48 | |
49 | - -- Gary Wang <gary.wang@canonical.com> Mon, 04 Jul 2016 16:09:14 +0800 |
50 | + [ Gary.Wzl ] |
51 | + * First landing of mcloud library. |
52 | + |
53 | + -- Gary.Wang <gary.wang@canonical.com> Tue, 27 Sep 2016 04:44:02 +0000 |
54 | |
55 | === modified file 'debian/control' |
56 | --- debian/control 2016-09-17 14:21:57 +0000 |
57 | +++ debian/control 2016-10-26 10:36:06 +0000 |
58 | @@ -30,6 +30,7 @@ |
59 | python3-dbus, |
60 | python3-gi, |
61 | libglib2.0-dev, |
62 | + lsb-release, |
63 | Standards-Version: 3.9.5 |
64 | Section: libs |
65 | Homepage: https://launchpad.net/mcloud |
66 | @@ -42,6 +43,7 @@ |
67 | Pre-Depends: ${misc:Pre-Depends}, |
68 | Depends: ${misc:Depends}, |
69 | ${shlibs:Depends}, |
70 | + account-plugin-mcloud, |
71 | Description: A C++ library for open API of cmcc mcloud service |
72 | Mcloud API provides developers easily access to authenticated |
73 | user's cmcc mcloud resources. |
74 | |
75 | === modified file 'debian/control.in' |
76 | --- debian/control.in 2016-09-17 14:21:57 +0000 |
77 | +++ debian/control.in 2016-10-26 10:36:06 +0000 |
78 | @@ -25,6 +25,7 @@ |
79 | python3-dbus, |
80 | python3-gi, |
81 | libglib2.0-dev, |
82 | + lsb-release, |
83 | Standards-Version: 3.9.5 |
84 | Section: libs |
85 | Homepage: https://launchpad.net/mcloud |
86 | @@ -37,6 +38,7 @@ |
87 | Pre-Depends: ${misc:Pre-Depends}, |
88 | Depends: ${misc:Depends}, |
89 | ${shlibs:Depends}, |
90 | + account-plugin-mcloud, |
91 | Description: A C++ library for open API of cmcc mcloud service |
92 | Mcloud API provides developers easily access to authenticated |
93 | user's cmcc mcloud resources. |
94 | |
95 | === removed file 'debian/libmcloud0.install' |
96 | --- debian/libmcloud0.install 2016-09-13 02:13:23 +0000 |
97 | +++ debian/libmcloud0.install 1970-01-01 00:00:00 +0000 |
98 | @@ -1,3 +0,0 @@ |
99 | -usr/lib/*/lib*.so.* |
100 | -usr/bin/* |
101 | -usr/share/dbus-1/services/* |
102 | |
103 | === added file 'debian/libmcloud1.install' |
104 | --- debian/libmcloud1.install 1970-01-01 00:00:00 +0000 |
105 | +++ debian/libmcloud1.install 2016-10-26 10:36:06 +0000 |
106 | @@ -0,0 +1,3 @@ |
107 | +usr/lib/*/lib*.so.* |
108 | +usr/bin/* |
109 | +usr/share/dbus-1/services/* |
110 | |
111 | === removed file 'debian/libmcloud1.install' |
112 | --- debian/libmcloud1.install 2016-09-17 14:21:57 +0000 |
113 | +++ debian/libmcloud1.install 1970-01-01 00:00:00 +0000 |
114 | @@ -1,3 +0,0 @@ |
115 | -usr/lib/*/lib*.so.* |
116 | -usr/bin/* |
117 | -usr/share/dbus-1/services/* |
118 | |
119 | === added file 'debian/libmcloud2.install' |
120 | --- debian/libmcloud2.install 1970-01-01 00:00:00 +0000 |
121 | +++ debian/libmcloud2.install 2016-10-26 10:36:06 +0000 |
122 | @@ -0,0 +1,3 @@ |
123 | +usr/lib/*/lib*.so.* |
124 | +usr/bin/* |
125 | +usr/share/dbus-1/services/* |
126 | |
127 | === modified file 'include/mcloud/api/client.h' |
128 | --- include/mcloud/api/client.h 2016-09-26 01:43:23 +0000 |
129 | +++ include/mcloud/api/client.h 2016-10-26 10:36:06 +0000 |
130 | @@ -31,8 +31,6 @@ |
131 | #include <mcloud/api/syncmanager.h> |
132 | |
133 | #include <deque> |
134 | -/*#include <future>*/ |
135 | -/*#include <thread>*/ |
136 | |
137 | namespace mcloud { |
138 | namespace api { |
139 | @@ -59,7 +57,7 @@ |
140 | |
141 | \note Mcloud API covers cloud resourece access and content sync-up between local and cloud. It does not take |
142 | responsibility of account authentication. So before using mcloud APIs, developers need to call \sa set_access_token to |
143 | - manually set a valid access_token or \sa refresh_token to fetch access token, |
144 | + manually set a valid access_token or \sa refresh_token to fetch access token, |
145 | which is used to call mcloud APIs internally to pass through authentication. |
146 | */ |
147 | |
148 | @@ -90,7 +88,7 @@ |
149 | * \brief Set \a access_token to authenticate all mcloud API calls with the bearer HTTP authorization scheme. |
150 | * The access token can be fetched through ubuntu sso services. |
151 | */ |
152 | - void set_access_token(const std::string &access_token); |
153 | + void set_access_token(const std::string& access_token); |
154 | |
155 | /*! |
156 | * \brief Retrieves and refreshes access token by using \a refresh_token. |
157 | @@ -98,14 +96,14 @@ |
158 | * \throw std::runtime_error if error occurs. |
159 | * \returns true if access token is refreshed, otherwise returns false. |
160 | */ |
161 | - bool refresh_token(const std::string &refresh_token); |
162 | + bool refresh_token(const std::string& refresh_token); |
163 | |
164 | /*! |
165 | * \brief Returns login user's clcoud storage info. |
166 | * \throw std::runtime_error if error occurs. |
167 | * @sa DiskInfo |
168 | */ |
169 | - DiskInfo disk_info(); |
170 | + DiskInfo::Ptr disk_info(); |
171 | |
172 | /*! |
173 | * \brief Returns root folder id on mlcoud for third-party app to use, such as mcloud-lib. |
174 | @@ -128,7 +126,7 @@ |
175 | ResourceList cloud_content_list(int start_index, |
176 | int count, |
177 | CloudContent::Type content_type = CloudContent::Type::All, |
178 | - const std::string &folder_id = std::string()); |
179 | + const std::string& folder_id = std::string()); |
180 | |
181 | /*! |
182 | * \brief Returns a cloud content object if a content \a content_id exists on mcloud. |
183 | @@ -136,7 +134,7 @@ |
184 | * \throw std::runtime_error if error occurs. |
185 | * \sa delete_contents(), move_items() |
186 | */ |
187 | - CloudContent::Ptr content_info(const std::string & content_id); |
188 | + CloudContent::Ptr content_info(const std::string& content_id); |
189 | |
190 | /*! |
191 | * \brief Returns a cloud folder object if a folder with \a folder_name is created under a given \a folder_id folder. |
192 | @@ -144,8 +142,8 @@ |
193 | * \throw std::runtime_error if error occurs. |
194 | * \sa delete_contents(), move_items() |
195 | */ |
196 | - CloudFolder::Ptr create_folder(const std::string &folder_name, |
197 | - const std::string &folder_id); |
198 | + CloudFolder::Ptr create_folder(const std::string& folder_name, |
199 | + const std::string& folder_id); |
200 | |
201 | /*! |
202 | * \brief Returns a cloud item list if there are available items that matches with \a name under a given \a folder_id folder. |
203 | @@ -155,25 +153,25 @@ |
204 | */ |
205 | |
206 | [[gnu::deprecated("cmcc closes this api for security reason")]] |
207 | - Client::ResourceList look_up(const std::string &name, |
208 | - const std::string &folder_id, |
209 | + Client::ResourceList look_up(const std::string& name, |
210 | + const std::string& folder_id, |
211 | CloudResource::Property property = CloudResource::Property::Content); |
212 | |
213 | /*! |
214 | - * \brief Creates folders extranet link object with a given \a folder_ids. |
215 | + * \brief Creates folders sharing url object with a given \a folder_ids. |
216 | * \throw std::runtime_error if error occurs. |
217 | - * \sa create_content_extranet_link() |
218 | - * \return a list of Outlink after extranet links are created. |
219 | + * \sa create_content_sharing_url() |
220 | + * \return a list of Outlink after sharing urls are created. |
221 | */ |
222 | - OutlinkList create_folder_extranet_link(const Stringlist &folder_ids); |
223 | + OutlinkList create_folder_sharing_url(const Stringlist& folder_ids); |
224 | |
225 | /*! |
226 | - * \brief Creates a content_extranet link object with a given \a content_ids. |
227 | + * \brief Creates a content_sharing url object with a given \a content_ids. |
228 | * \throw std::runtime_error if error occurs. |
229 | - * \sa create_folder_extranet_link() |
230 | - * \return a list of Outlink after extranet links are created. |
231 | + * \sa create_folder_sharing_url() |
232 | + * \return a list of Outlink after sharing urls are created. |
233 | */ |
234 | - OutlinkList create_content_extranet_link(const Stringlist &content_ids); |
235 | + OutlinkList create_content_sharing_url(const Stringlist& content_ids); |
236 | |
237 | /*! |
238 | * \brief Returns folder id list if folders \a folder_ids are copies to another folder with a given \a folder_id on mcloud |
239 | @@ -181,8 +179,8 @@ |
240 | * \note the destination folder \a folder_id should not be the same as the folders' \a folder_ids folder ids. |
241 | * \sa move_items(), update_folder(), copy_contents() |
242 | */ |
243 | - Client::Stringlist copy_folders(const Stringlist &folder_ids, |
244 | - const std::string &_folder_id); |
245 | + Client::Stringlist copy_folders(const Stringlist& folder_ids, |
246 | + const std::string& folder_id); |
247 | |
248 | /*! |
249 | * \brief Returns content id list if contents \a content_ids are copies to another folder with a given \a folder_id on mcloud. |
250 | @@ -190,8 +188,8 @@ |
251 | * \note the destination folder \a folder_id should not be the same as the contents' \a contents_ids folder id. |
252 | * \sa move_items(), update_folder(), copy_folders() |
253 | */ |
254 | - Client::Stringlist copy_contents(const Stringlist &contents_ids, |
255 | - const std::string &folder_id); |
256 | + Client::Stringlist copy_contents(const Stringlist& contents_ids, |
257 | + const std::string& folder_id); |
258 | |
259 | /*! |
260 | * \brief Returns true if \a folders with a given folder_ids and \a contents with a given \a content_ids |
261 | @@ -199,32 +197,32 @@ |
262 | * \throw std::runtime_error if error occurs. |
263 | * \sa delete_contents(), copy_folders(), copy_contents() |
264 | */ |
265 | - bool move_items(const Stringlist &folder_ids, |
266 | - const Stringlist &content_ids, |
267 | - const std::string &folder_id); |
268 | + bool move_items(const Stringlist& folder_ids, |
269 | + const Stringlist& content_ids, |
270 | + const std::string& folder_id); |
271 | |
272 | /*! |
273 | * \brief Returns true if folder \a folder_id are updated with \a new_folder_name, otherwise return false. |
274 | * \throw std::runtime_error if error occurs. |
275 | * \sa delete_contents(), copy_folders(), |
276 | */ |
277 | - bool update_folder(const std::string &folder_id, |
278 | - const std::string &new_folder_name); |
279 | + bool update_folder(const std::string& folder_id, |
280 | + const std::string& new_folder_name); |
281 | |
282 | /*! |
283 | * \brief Returns true if contents \a content_ids are deleted, otherwise return false. |
284 | * \throw std::runtime_error if error occurs. |
285 | * \sa move_items(), content_info(), copy_contents() |
286 | */ |
287 | - bool delete_contents(const Stringlist &content_ids); |
288 | + bool delete_contents(const Stringlist& content_ids); |
289 | |
290 | /*! |
291 | - * \brief Returns true if a local file \a file_path exists in folder with \a folder_id on cloud, |
292 | + * \brief Returns true if a local file \a file_path exists in folder with \a folder_id on cloud, |
293 | * otherwise return false. Searches root folder if folder_id is empty(); |
294 | * \throw std::runtime_error if error occurs. |
295 | */ |
296 | - bool exist_on_cloud(const std::string &file_path, |
297 | - const std::string &folder_id = std::string()); |
298 | + bool exist_on_cloud(const std::string& file_path, |
299 | + const std::string& folder_id = std::string()); |
300 | |
301 | /*! |
302 | * \brief Returns a sync-up manager running on the background. |
303 | @@ -233,7 +231,7 @@ |
304 | SyncManager::Ptr syncmanager() const; |
305 | |
306 | private: |
307 | - std::shared_ptr<ClientPriv> p_; |
308 | + std::unique_ptr<ClientPriv> p_; |
309 | |
310 | }; |
311 | |
312 | |
313 | === modified file 'include/mcloud/api/cloudcontent.h' |
314 | --- include/mcloud/api/cloudcontent.h 2016-09-26 01:43:23 +0000 |
315 | +++ include/mcloud/api/cloudcontent.h 2016-10-26 10:36:06 +0000 |
316 | @@ -23,7 +23,7 @@ |
317 | #include <mcloud/api/visibility.h> |
318 | |
319 | namespace tinyxml2 { |
320 | - class XMLElement; |
321 | +class XMLElement; |
322 | } |
323 | |
324 | namespace mcloud { |
325 | @@ -36,7 +36,7 @@ |
326 | */ |
327 | |
328 | class MCLOUD_API_DLL_PUBLIC CloudContent: public CloudResource { |
329 | -public: |
330 | + public: |
331 | typedef std::shared_ptr<CloudContent> Ptr; |
332 | |
333 | /*! |
334 | @@ -53,42 +53,42 @@ |
335 | PPT ///< ppt content |
336 | }; |
337 | |
338 | - virtual ~CloudContent() = default; |
339 | + ~CloudContent(); |
340 | |
341 | /*! |
342 | * \brief Returns a unique id of cloud content object. |
343 | */ |
344 | - const std::string &id() const override; |
345 | + const std::string& id() const override; |
346 | |
347 | /*! |
348 | * \brief Returns the name of cloud content object. |
349 | */ |
350 | - const std::string &name() const override; |
351 | + const std::string& name() const override; |
352 | |
353 | /*! |
354 | * \brief Returns the datetime when content was created. |
355 | */ |
356 | - const std::time_t &created_date() const override; |
357 | + const std::time_t& created_date() const override; |
358 | |
359 | /*! |
360 | * \brief Returns the datetime when content was updated. |
361 | */ |
362 | - const std::time_t &updated_date() const override; |
363 | + const std::time_t& updated_date() const override; |
364 | |
365 | /*! |
366 | * \brief Returns a unique parent folder id of cloud content object. |
367 | */ |
368 | - const std::string &parent_catalog_id() const override; |
369 | + const std::string& parent_catalog_id() const override; |
370 | |
371 | /*! |
372 | * \brief Returns etag of a content object. |
373 | */ |
374 | - const std::string &etag() const override; |
375 | + const std::string& etag() const override; |
376 | |
377 | /*! |
378 | * \brief Returns owner id of a content object. |
379 | */ |
380 | - const std::string &owner() const override; |
381 | + const std::string& owner() const override; |
382 | |
383 | /*! |
384 | * \brief Returns resource type of an object. |
385 | @@ -98,7 +98,7 @@ |
386 | /*! |
387 | * \brief Returns extension of a content object. |
388 | */ |
389 | - const std::string &suffix() const; |
390 | + const std::string& suffix() const; |
391 | |
392 | /*! |
393 | * \brief Returns content type of an object. |
394 | @@ -113,33 +113,33 @@ |
395 | /*! |
396 | * \brief Returns the description of a content object. |
397 | */ |
398 | - const std::string &description() const; |
399 | + const std::string& description() const; |
400 | |
401 | /*! |
402 | * \brief Returns thumbnail link of a content object. |
403 | * It will be empty if there is no such a field in response. |
404 | */ |
405 | - const std::string &thumbnail_url() const; |
406 | + const std::string& thumbnail_url() const; |
407 | |
408 | /*! |
409 | * \brief Returns big thumbnail link of a content object, |
410 | * It will be empty if there is no such a field in response. |
411 | */ |
412 | - const std::string &big_thumbnail_url() const; |
413 | + const std::string& big_thumbnail_url() const; |
414 | |
415 | /*! |
416 | * \brief Returns a external playable link of a media content object, |
417 | * It will be empty if there is no such a field in response. |
418 | */ |
419 | - const std::string &present_url() const; |
420 | + const std::string& present_url() const; |
421 | |
422 | -private: |
423 | - CloudContent(const tinyxml2::XMLElement *root); |
424 | + private: |
425 | + CloudContent(const tinyxml2::XMLElement* root); |
426 | |
427 | friend class ClientPriv; |
428 | |
429 | class Priv; |
430 | - std::shared_ptr<Priv> p; |
431 | + std::unique_ptr<Priv> p; |
432 | }; |
433 | |
434 | } |
435 | |
436 | === modified file 'include/mcloud/api/cloudfolder.h' |
437 | --- include/mcloud/api/cloudfolder.h 2016-09-26 01:43:23 +0000 |
438 | +++ include/mcloud/api/cloudfolder.h 2016-10-26 10:36:06 +0000 |
439 | @@ -23,7 +23,7 @@ |
440 | #include <mcloud/api/visibility.h> |
441 | |
442 | namespace tinyxml2 { |
443 | - class XMLElement; |
444 | +class XMLElement; |
445 | } |
446 | |
447 | namespace mcloud { |
448 | @@ -35,7 +35,7 @@ |
449 | */ |
450 | |
451 | class MCLOUD_API_DLL_PUBLIC CloudFolder : public CloudResource { |
452 | -public: |
453 | + public: |
454 | enum class Type { |
455 | Normal = 0, |
456 | Pictures, |
457 | @@ -49,42 +49,42 @@ |
458 | |
459 | typedef std::shared_ptr<CloudFolder> Ptr; |
460 | |
461 | - virtual ~CloudFolder() = default; |
462 | + ~CloudFolder(); |
463 | |
464 | /*! |
465 | * \brief Returns a unique id of cloud folder object. |
466 | */ |
467 | - const std::string &id() const override; |
468 | + const std::string& id() const override; |
469 | |
470 | /*! |
471 | * \brief Returns the name of cloud folder object. |
472 | */ |
473 | - const std::string &name() const override; |
474 | + const std::string& name() const override; |
475 | |
476 | /*! |
477 | * \brief Returns the datetime when folder was created. |
478 | */ |
479 | - const std::time_t &created_date() const override; |
480 | + const std::time_t& created_date() const override; |
481 | |
482 | /*! |
483 | * \brief Returns the datetime when folder was updated. |
484 | */ |
485 | - const std::time_t &updated_date() const override; |
486 | + const std::time_t& updated_date() const override; |
487 | |
488 | /*! |
489 | * \brief Returns a unique id of the parent folder. |
490 | */ |
491 | - const std::string &parent_catalog_id() const override; |
492 | + const std::string& parent_catalog_id() const override; |
493 | |
494 | /*! |
495 | * \brief Returns etag of a folder object. |
496 | */ |
497 | - const std::string &etag() const override; |
498 | + const std::string& etag() const override; |
499 | |
500 | /*! |
501 | * \brief Returns owner id of a folder object. |
502 | */ |
503 | - const std::string &owner() const override; |
504 | + const std::string& owner() const override; |
505 | |
506 | /*! |
507 | * \brief Returns resource property of an object. |
508 | @@ -101,15 +101,15 @@ |
509 | /*! |
510 | * \brief Returns a current folder's path. |
511 | */ |
512 | - const std::string &folder_path() const; |
513 | + const std::string& folder_path() const; |
514 | |
515 | -private: |
516 | - CloudFolder(const tinyxml2::XMLElement *root); |
517 | + private: |
518 | + CloudFolder(const tinyxml2::XMLElement* root); |
519 | |
520 | friend class ClientPriv; |
521 | |
522 | class Priv; |
523 | - std::shared_ptr<Priv> p_; |
524 | + std::unique_ptr<Priv> p_; |
525 | }; |
526 | |
527 | } |
528 | |
529 | === modified file 'include/mcloud/api/cloudresource.h' |
530 | --- include/mcloud/api/cloudresource.h 2016-09-26 01:43:23 +0000 |
531 | +++ include/mcloud/api/cloudresource.h 2016-10-26 10:36:06 +0000 |
532 | @@ -42,19 +42,19 @@ |
533 | |
534 | virtual ~CloudResource() = default; |
535 | |
536 | - virtual const std::string &id() const = 0; |
537 | - |
538 | - virtual const std::string &name() const = 0; |
539 | - |
540 | - virtual const std::time_t &created_date() const = 0; |
541 | - |
542 | - virtual const std::time_t &updated_date() const = 0; |
543 | - |
544 | - virtual const std::string &parent_catalog_id() const = 0; |
545 | - |
546 | - virtual const std::string &etag() const = 0; |
547 | - |
548 | - virtual const std::string &owner() const = 0; |
549 | + virtual const std::string& id() const = 0; |
550 | + |
551 | + virtual const std::string& name() const = 0; |
552 | + |
553 | + virtual const std::time_t& created_date() const = 0; |
554 | + |
555 | + virtual const std::time_t& updated_date() const = 0; |
556 | + |
557 | + virtual const std::string& parent_catalog_id() const = 0; |
558 | + |
559 | + virtual const std::string& etag() const = 0; |
560 | + |
561 | + virtual const std::string& owner() const = 0; |
562 | |
563 | virtual Property property() const = 0; |
564 | }; |
565 | |
566 | === modified file 'include/mcloud/api/diskinfo.h' |
567 | --- include/mcloud/api/diskinfo.h 2016-09-26 01:43:23 +0000 |
568 | +++ include/mcloud/api/diskinfo.h 2016-10-26 10:36:06 +0000 |
569 | @@ -24,7 +24,7 @@ |
570 | #include <memory> |
571 | |
572 | namespace tinyxml2 { |
573 | - class XMLElement; |
574 | +class XMLElement; |
575 | } |
576 | |
577 | namespace mcloud { |
578 | @@ -36,8 +36,9 @@ |
579 | */ |
580 | |
581 | class MCLOUD_API_DLL_PUBLIC DiskInfo { |
582 | -public: |
583 | - virtual ~DiskInfo() = default; |
584 | + public: |
585 | + typedef std::shared_ptr<DiskInfo> Ptr; |
586 | + ~DiskInfo(); |
587 | |
588 | /*! |
589 | * \brief Returns available free disk size of user cloud storage in MB. |
590 | @@ -49,13 +50,13 @@ |
591 | */ |
592 | int disk_size() const; |
593 | |
594 | -private: |
595 | - DiskInfo(const tinyxml2::XMLElement *root); |
596 | + private: |
597 | + DiskInfo(const tinyxml2::XMLElement* root); |
598 | |
599 | friend class ClientPriv; |
600 | |
601 | class Priv; |
602 | - std::shared_ptr<Priv> p_; |
603 | + std::unique_ptr<Priv> p_; |
604 | }; |
605 | |
606 | } |
607 | |
608 | === modified file 'include/mcloud/api/downloadtask.h' |
609 | --- include/mcloud/api/downloadtask.h 2016-09-26 01:43:23 +0000 |
610 | +++ include/mcloud/api/downloadtask.h 2016-10-26 10:36:06 +0000 |
611 | @@ -33,8 +33,7 @@ |
612 | \struct DownloadBufferCb |
613 | \brief DownloadBufferCb is a download request object which consists of a content id and writing callback function allows content data can be received in buffering via call back function. |
614 | */ |
615 | -struct MCLOUD_API_DLL_PUBLIC DownloadBufferCb |
616 | -{ |
617 | +struct MCLOUD_API_DLL_PUBLIC DownloadBufferCb { |
618 | std::string content_id; |
619 | Task::Buffer_Callback write_cb; |
620 | }; |
621 | @@ -48,45 +47,43 @@ |
622 | basic download item information, also it's used for content download by sync manager. |
623 | */ |
624 | class MCLOUD_API_DLL_PUBLIC DownloadTask : public Task { |
625 | -public: |
626 | + public: |
627 | typedef std::shared_ptr<DownloadTask> Ptr; |
628 | |
629 | - virtual ~DownloadTask() = default; |
630 | - |
631 | - DownloadTask(const DownloadTask& ) = delete; |
632 | - |
633 | - DownloadTask& operator=(const DownloadTask& ) = delete; |
634 | + DownloadTask(const DownloadTask&) = delete; |
635 | + |
636 | + DownloadTask& operator=(const DownloadTask&) = delete; |
637 | |
638 | /*! |
639 | * Returns an unique id of download task. |
640 | */ |
641 | - const std::string & task_id() const override; |
642 | + const std::string& task_id() const override; |
643 | |
644 | /*! |
645 | * \brief Returns an unique id of cloud content on mcloud. |
646 | */ |
647 | - const std::string & content_id() const override; |
648 | + const std::string& content_id() const override; |
649 | |
650 | /*! |
651 | * \brief Returns a display name of cloud content on mcloud. |
652 | */ |
653 | - const std::string & content_name() const override; |
654 | + const std::string& content_name() const override; |
655 | |
656 | /*! |
657 | * \brief Returns cloud content local storage file path. |
658 | */ |
659 | - const std::string & file_path() const override; |
660 | + const std::string& file_path() const override; |
661 | |
662 | /*! |
663 | * \brief Returns download url assigned by mcloud for this task. |
664 | * \note this url will be expried after a period of time. |
665 | */ |
666 | - const std::string & task_url() const override; |
667 | + const std::string& task_url() const override; |
668 | |
669 | /*! |
670 | * \brief Contains the error string if an error occurs during content download. |
671 | */ |
672 | - const std::string & error_string() const override; |
673 | + const std::string& error_string() const override; |
674 | |
675 | /*! |
676 | * \brief Returns current sync-up status for this task. |
677 | @@ -98,22 +95,22 @@ |
678 | * \brief Handler for download progress of a task. |
679 | * \sa Task::ProgressHandler |
680 | */ |
681 | - Task::ProgressHandler & progress_changed() override; |
682 | + Task::ProgressHandler& progress_changed() override; |
683 | |
684 | /*! |
685 | * \brief Handler for download status of a task. |
686 | * \sa Task::StatusHandler |
687 | */ |
688 | - Task::StatusHandler & status_changed() override; |
689 | + Task::StatusHandler& status_changed() override; |
690 | |
691 | - /*! |
692 | + /*! |
693 | * \brief cancel the task. |
694 | * \sa Task::StatusHandler |
695 | */ |
696 | void cancel() override; |
697 | |
698 | -private: |
699 | - DownloadTask(std::shared_ptr<DownloadTaskPriv> p); |
700 | + private: |
701 | + DownloadTask(const std::shared_ptr<DownloadTaskPriv>& p); |
702 | |
703 | friend class SyncManagerPriv; |
704 | |
705 | |
706 | === modified file 'include/mcloud/api/exceptions.h' |
707 | --- include/mcloud/api/exceptions.h 2016-08-29 04:15:08 +0000 |
708 | +++ include/mcloud/api/exceptions.h 2016-10-26 10:36:06 +0000 |
709 | @@ -26,55 +26,55 @@ |
710 | namespace mcloud { |
711 | namespace api { |
712 | |
713 | - /** |
714 | - * \brief Indicates an invalid content id when querying content infomation by an id. |
715 | - * or an invalid folder id when listing or looup content in one specific folder. |
716 | - */ |
717 | - |
718 | - class MCLOUD_API_DLL_PUBLIC InvalidIDException : public std::runtime_error { |
719 | - public: |
720 | - using runtime_error::runtime_error; |
721 | - }; |
722 | - |
723 | - /* |
724 | - * \brief Indicates a content or folder can not be found on mcloud. |
725 | - */ |
726 | - class MCLOUD_API_DLL_PUBLIC NonExistentException : public std::runtime_error { |
727 | - public: |
728 | - using runtime_error::runtime_error; |
729 | - }; |
730 | - |
731 | - /** |
732 | - * \brief User ran out of space on mcloud storage. |
733 | - */ |
734 | - class MCLOUD_API_DLL_PUBLIC OutofSpaceException : public std::runtime_error { |
735 | - public: |
736 | - using runtime_error::runtime_error; |
737 | - }; |
738 | - |
739 | - /** |
740 | - * \brief Indicates a timeout on HTTP requests. |
741 | - */ |
742 | - class MCLOUD_API_DLL_PUBLIC HttpTimeoutException : public std::runtime_error { |
743 | - public: |
744 | - using runtime_error::runtime_error; |
745 | - }; |
746 | - |
747 | - /* |
748 | - * \brief Indicates one or more http request parameters are invalid. |
749 | - */ |
750 | - class MCLOUD_API_DLL_PUBLIC ParameterInvalidException : public std::runtime_error { |
751 | - public: |
752 | - using runtime_error::runtime_error; |
753 | - }; |
754 | - |
755 | - /* |
756 | - * \brief Indicates access token is invalid or expired. |
757 | - */ |
758 | - class MCLOUD_API_DLL_PUBLIC CredentialException : public std::runtime_error { |
759 | - public: |
760 | - using runtime_error::runtime_error; |
761 | - }; |
762 | +/** |
763 | + * \brief Indicates an invalid content id when querying content infomation by an id. |
764 | + * or an invalid folder id when listing or looup content in one specific folder. |
765 | + */ |
766 | + |
767 | +class MCLOUD_API_DLL_PUBLIC InvalidIDException : public std::runtime_error { |
768 | + public: |
769 | + using runtime_error::runtime_error; |
770 | +}; |
771 | + |
772 | +/* |
773 | + * \brief Indicates a content or folder can not be found on mcloud. |
774 | + */ |
775 | +class MCLOUD_API_DLL_PUBLIC NonExistentException : public std::runtime_error { |
776 | + public: |
777 | + using runtime_error::runtime_error; |
778 | +}; |
779 | + |
780 | +/** |
781 | + * \brief User ran out of space on mcloud storage. |
782 | + */ |
783 | +class MCLOUD_API_DLL_PUBLIC OutofSpaceException : public std::runtime_error { |
784 | + public: |
785 | + using runtime_error::runtime_error; |
786 | +}; |
787 | + |
788 | +/** |
789 | + * \brief Indicates a timeout on HTTP requests. |
790 | + */ |
791 | +class MCLOUD_API_DLL_PUBLIC HttpTimeoutException : public std::runtime_error { |
792 | + public: |
793 | + using runtime_error::runtime_error; |
794 | +}; |
795 | + |
796 | +/* |
797 | + * \brief Indicates one or more http request parameters are invalid. |
798 | + */ |
799 | +class MCLOUD_API_DLL_PUBLIC ParameterInvalidException : public std::runtime_error { |
800 | + public: |
801 | + using runtime_error::runtime_error; |
802 | +}; |
803 | + |
804 | +/* |
805 | + * \brief Indicates access token is invalid or expired. |
806 | + */ |
807 | +class MCLOUD_API_DLL_PUBLIC CredentialException : public std::runtime_error { |
808 | + public: |
809 | + using runtime_error::runtime_error; |
810 | +}; |
811 | |
812 | } |
813 | } |
814 | |
815 | === modified file 'include/mcloud/api/outlink.h' |
816 | --- include/mcloud/api/outlink.h 2016-09-06 09:12:43 +0000 |
817 | +++ include/mcloud/api/outlink.h 2016-10-26 10:36:06 +0000 |
818 | @@ -25,7 +25,7 @@ |
819 | #include <string> |
820 | |
821 | namespace tinyxml2 { |
822 | - class XMLElement; |
823 | +class XMLElement; |
824 | } |
825 | |
826 | namespace mcloud { |
827 | @@ -33,32 +33,32 @@ |
828 | |
829 | /*! |
830 | \class Outlink |
831 | - \brief Outlink is a cloud extranet link that contains extranet link which can be share by user to others. |
832 | + \brief Outlink is a link object that contains extranet link which can be share by user to others. |
833 | */ |
834 | |
835 | class MCLOUD_API_DLL_PUBLIC Outlink { |
836 | -public: |
837 | + public: |
838 | typedef std::shared_ptr<Outlink> Ptr; |
839 | |
840 | - virtual ~Outlink() = default; |
841 | + ~Outlink(); |
842 | |
843 | /*! |
844 | * \brief Returns a unique id of extranet object assigned by mcloud. |
845 | */ |
846 | - const std::string &id() const; |
847 | + const std::string& id() const; |
848 | |
849 | /*! |
850 | * \brief Returns a unique id of extranet link assigned by mcloud. |
851 | */ |
852 | - const std::string &link() const; |
853 | + const std::string& link() const; |
854 | |
855 | -private: |
856 | - Outlink(const tinyxml2::XMLElement *root); |
857 | + private: |
858 | + Outlink(const tinyxml2::XMLElement* root); |
859 | |
860 | friend class ClientPriv; |
861 | |
862 | class Priv; |
863 | - std::shared_ptr<Priv> p_; |
864 | + std::unique_ptr<Priv> p_; |
865 | }; |
866 | |
867 | } |
868 | |
869 | === modified file 'include/mcloud/api/syncmanager.h' |
870 | --- include/mcloud/api/syncmanager.h 2016-09-26 01:43:23 +0000 |
871 | +++ include/mcloud/api/syncmanager.h 2016-10-26 10:36:06 +0000 |
872 | @@ -35,8 +35,8 @@ |
873 | |
874 | /*! |
875 | \class SyncManager |
876 | - \brief SyncManager handles all the requests to upload and download. |
877 | - It's constructed around two threads for content synchronization. One for content uploading to cloud, another for cloud item downloading to local. |
878 | + \brief SyncManager handles all the requests to upload and download. |
879 | + It's constructed around two threads for content synchronization. One for content uploading to cloud, another for cloud item downloading to local. |
880 | Both thread are running asynchronously. |
881 | Calls \sa add_download_tasks() by passing a content id list for cloud content download, |
882 | Calls \sa add_upload_tasks() by passing a local file list path for local content upload. |
883 | @@ -52,11 +52,11 @@ |
884 | |
885 | typedef std::vector<std::string> Stringlist; |
886 | |
887 | - virtual ~SyncManager() = default; |
888 | + ~SyncManager(); |
889 | |
890 | SyncManager(const SyncManager&) = delete; |
891 | |
892 | - SyncManager& operator=(const SyncManager &) = delete; |
893 | + SyncManager& operator=(const SyncManager&) = delete; |
894 | |
895 | /*! |
896 | * \brief Starts to run download or upload tasks from sync-up thread. |
897 | @@ -85,7 +85,7 @@ |
898 | * \throw std::runtime_error if error occurs. |
899 | * \sa add_download_tasks(), DownloadTask |
900 | */ |
901 | - DownloadTask::Ptr add_download_task(const std::string &content_id); |
902 | + DownloadTask::Ptr add_download_task(const std::string& content_id); |
903 | |
904 | /*! |
905 | * \brief Pushes a download buffer callback item \a buffer_cb to sync manager and add regarding upload task into download queue. |
906 | @@ -99,7 +99,7 @@ |
907 | * \throw std::runtime_error if error occurs. |
908 | * \sa add_download_tasks(), DownloadTask |
909 | */ |
910 | - DownloadTask::Ptr add_download_task(const DownloadBufferCb &buffer_cb); |
911 | + DownloadTask::Ptr add_download_task(const DownloadBufferCb& buffer_cb); |
912 | |
913 | /*! |
914 | * \brief Pushes a upload request item \a request_item to sync manager and add regarding upload task into upload queue. |
915 | @@ -116,11 +116,11 @@ |
916 | * \throw std::runtime_error if error occurs. |
917 | * \note A file name can not contain any of following characters: |
918 | * '\', '/', ':', '*', '?', '"', '<', '>', '|' |
919 | - * \note Sync manager will detect if the uploading file is already existing on cloud, |
920 | + * \note Sync manager will detect if the uploading file is already existing on cloud, |
921 | * if so, it simply sets the status of upload task completed to avoid duplicated upload. |
922 | * \sa add_download_tasks(), UploadRequest, UploadTask, |
923 | */ |
924 | - UploadTask::Ptr add_upload_task(const UploadRequest &request_item); |
925 | + UploadTask::Ptr add_upload_task(const UploadRequest& request_item); |
926 | |
927 | /*! |
928 | * \brief Pushes a new upload request object \a buffer_cb to sync manager and add regarding upload task into upload queue. |
929 | @@ -141,7 +141,7 @@ |
930 | * '\', '/', ':', '*', '?', '"', '<', '>', '|' |
931 | * \sa add_download_tasks(), UploadRequest, UploadTask, |
932 | */ |
933 | - UploadTask::Ptr add_upload_task(const UploadBufferCb &buffer_cb); |
934 | + UploadTask::Ptr add_upload_task(const UploadBufferCb& buffer_cb); |
935 | |
936 | /*! |
937 | * \brief Returns a download task list hold by sync up manager. |
938 | @@ -151,18 +151,18 @@ |
939 | DownloadList download_queue(); |
940 | |
941 | /*! |
942 | - * \brief Returns a upload task list hold by sync up manager. |
943 | + * \brief Returns a upload task list hold by sync up manager. |
944 | * Each item in the list contains basic information of associated task. |
945 | * \sa download_queue(), UploadTask |
946 | */ |
947 | UploadList upload_queue(); |
948 | |
949 | -private: |
950 | + private: |
951 | SyncManager(ClientPriv* client_priv); |
952 | |
953 | friend class ClientPriv; |
954 | |
955 | - std::shared_ptr<SyncManagerPriv> p_; |
956 | + std::unique_ptr<SyncManagerPriv> p_; |
957 | }; |
958 | |
959 | } |
960 | |
961 | === modified file 'include/mcloud/api/task.h' |
962 | --- include/mcloud/api/task.h 2016-09-26 01:43:23 +0000 |
963 | +++ include/mcloud/api/task.h 2016-10-26 10:36:06 +0000 |
964 | @@ -32,7 +32,7 @@ |
965 | */ |
966 | |
967 | class MCLOUD_API_DLL_PUBLIC Task { |
968 | -public: |
969 | + public: |
970 | /*! |
971 | * \brief The Status enum indicates current status of this task. |
972 | */ |
973 | @@ -49,40 +49,40 @@ |
974 | |
975 | typedef std::function<void(Status)> StatusHandler; |
976 | |
977 | - typedef std::function<size_t(void *dest, size_t buf_size)> Buffer_Callback; |
978 | + typedef std::function<size_t(void* dest, size_t buf_size)> Buffer_Callback; |
979 | |
980 | virtual ~Task() = default; |
981 | |
982 | /*! |
983 | * \brief Returns an unique id of task. |
984 | */ |
985 | - virtual const std::string & task_id() const = 0; |
986 | + virtual const std::string& task_id() const = 0; |
987 | |
988 | /*! |
989 | * \brief Returns an unique id of cloud content on mcloud. |
990 | */ |
991 | - virtual const std::string & content_id() const = 0; |
992 | + virtual const std::string& content_id() const = 0; |
993 | |
994 | /*! |
995 | * \brief Returns a display name of cloud content on mcloud. |
996 | */ |
997 | - virtual const std::string & content_name() const = 0; |
998 | + virtual const std::string& content_name() const = 0; |
999 | |
1000 | /*! |
1001 | * \brief Returns cloud content local storage file path. |
1002 | */ |
1003 | - virtual const std::string & file_path() const = 0; |
1004 | + virtual const std::string& file_path() const = 0; |
1005 | |
1006 | /*! |
1007 | * \brief Contains the error string if an error occurs during task running. |
1008 | */ |
1009 | - virtual const std::string & error_string() const = 0; |
1010 | + virtual const std::string& error_string() const = 0; |
1011 | |
1012 | /*! |
1013 | * \brief Returns a item url assigned by mcloud. |
1014 | * \note the url will be expried after a period of time. |
1015 | */ |
1016 | - virtual const std::string & task_url() const = 0; |
1017 | + virtual const std::string& task_url() const = 0; |
1018 | |
1019 | /*! |
1020 | * \brief Returns current download or upload item sync-up status. |
1021 | @@ -93,13 +93,13 @@ |
1022 | * \brief Handler for download or upload progress of a task. |
1023 | * \sa Task::ProgressHandler |
1024 | */ |
1025 | - virtual Task::ProgressHandler & progress_changed() = 0; |
1026 | + virtual Task::ProgressHandler& progress_changed() = 0; |
1027 | |
1028 | /*! |
1029 | * \brief Handler for download or upload progress of a task. |
1030 | * \sa Task::StatusHandler |
1031 | */ |
1032 | - virtual Task::StatusHandler & status_changed() = 0; |
1033 | + virtual Task::StatusHandler& status_changed() = 0; |
1034 | |
1035 | /*! |
1036 | * \brief Cancels the task. |
1037 | |
1038 | === modified file 'include/mcloud/api/taskqueue.h' |
1039 | --- include/mcloud/api/taskqueue.h 2016-05-26 10:47:12 +0000 |
1040 | +++ include/mcloud/api/taskqueue.h 2016-10-26 10:36:06 +0000 |
1041 | @@ -41,17 +41,17 @@ |
1042 | |
1043 | virtual ~TaskQueue() = default; |
1044 | |
1045 | - TaskQueue(TaskQueue &&queue) { |
1046 | + TaskQueue(TaskQueue&& queue) { |
1047 | std::lock_guard<std::mutex> lock(mutex_); |
1048 | tasks_ = std::move(queue.tasks_); |
1049 | } |
1050 | |
1051 | - TaskQueue(const TaskQueue &queue) { |
1052 | + TaskQueue(const TaskQueue& queue) { |
1053 | std::lock_guard<std::mutex> lock(mutex_); |
1054 | tasks_ = queue.tasks_; |
1055 | } |
1056 | |
1057 | - TaskQueue &operator= (const TaskQueue &queue) { |
1058 | + TaskQueue& operator= (const TaskQueue& queue) { |
1059 | if (this != &queue) { |
1060 | std::lock_guard<std::mutex> lock1(mutex_); |
1061 | std::lock_guard<std::mutex> lock2(queue.mutex_); |
1062 | @@ -91,30 +91,31 @@ |
1063 | return tasks_.empty(); |
1064 | } |
1065 | |
1066 | - void push(const T &task) { |
1067 | + void push(const T& task) { |
1068 | std::lock_guard<std::mutex> lock(mutex_); |
1069 | tasks_.push_back(task); |
1070 | } |
1071 | |
1072 | - void push(const TaskQueue & queue) { |
1073 | + void push(const TaskQueue& queue) { |
1074 | std::lock_guard<std::mutex> lock(mutex_); |
1075 | - for (const T & task: queue.tasks_){ |
1076 | + for (const T& task : queue.tasks_) { |
1077 | tasks_.push_back(task); |
1078 | } |
1079 | } |
1080 | |
1081 | - bool try_pop(T &task) { |
1082 | + bool try_pop(T& task) { |
1083 | std::lock_guard<std::mutex> lock(mutex_); |
1084 | |
1085 | - if (tasks_.empty()) |
1086 | - return false; |
1087 | + if (tasks_.empty()) { |
1088 | + return false; |
1089 | + } |
1090 | |
1091 | task = tasks_.front(); |
1092 | tasks_.pop_front(); |
1093 | return true; |
1094 | } |
1095 | |
1096 | - const T & operator[](int index) const { |
1097 | + const T& operator[](int index) const { |
1098 | std::lock_guard<std::mutex> lock(mutex_); |
1099 | return tasks_[index]; |
1100 | } |
1101 | |
1102 | === modified file 'include/mcloud/api/uploadtask.h' |
1103 | --- include/mcloud/api/uploadtask.h 2016-09-26 01:43:23 +0000 |
1104 | +++ include/mcloud/api/uploadtask.h 2016-10-26 10:36:06 +0000 |
1105 | @@ -32,10 +32,9 @@ |
1106 | |
1107 | /*! |
1108 | \struct UploadRequest |
1109 | - \brief UploadRequest is a upload request item which consists of a upload folder id, up-front buffer size, upload content name |
1110 | + \brief UploadRequest is a upload request item which consists of a upload folder id, up-front buffer size, upload content name |
1111 | */ |
1112 | -struct MCLOUD_API_DLL_PUBLIC UploadRequest |
1113 | -{ |
1114 | +struct MCLOUD_API_DLL_PUBLIC UploadRequest { |
1115 | std::string file_path; |
1116 | std::string folder_id; |
1117 | std::string content_name; |
1118 | @@ -44,10 +43,9 @@ |
1119 | |
1120 | /*! |
1121 | \struct UploadBufferCb |
1122 | - \brief UploadBufferCb is a upload request item which consists of a upload folder id, upload buffer size, upload content name and reading callback function allows content data can be received in buffering via call back function. |
1123 | + \brief UploadBufferCb is a upload request item which consists of a upload folder id, upload buffer size, upload content name and reading callback function allows content data can be received in buffering via call back function. |
1124 | */ |
1125 | -struct MCLOUD_API_DLL_PUBLIC UploadBufferCb |
1126 | -{ |
1127 | +struct MCLOUD_API_DLL_PUBLIC UploadBufferCb { |
1128 | Task::Buffer_Callback read_cb; |
1129 | size_t buffer_size; |
1130 | std::string folder_id; |
1131 | @@ -64,45 +62,43 @@ |
1132 | basic upload item information, also it's used for content upload by sync manager. |
1133 | */ |
1134 | class MCLOUD_API_DLL_PUBLIC UploadTask : public Task { |
1135 | -public: |
1136 | + public: |
1137 | typedef std::shared_ptr<UploadTask> Ptr; |
1138 | |
1139 | - virtual ~UploadTask() = default; |
1140 | - |
1141 | - UploadTask(const UploadTask& ) = delete; |
1142 | - |
1143 | - UploadTask& operator=(const UploadTask& ) = delete; |
1144 | + UploadTask(const UploadTask&) = delete; |
1145 | + |
1146 | + UploadTask& operator=(const UploadTask&) = delete; |
1147 | |
1148 | /*! |
1149 | * \brief Returns an unique id of upload task. |
1150 | */ |
1151 | - const std::string & task_id() const override; |
1152 | + const std::string& task_id() const override; |
1153 | |
1154 | /*! |
1155 | * \brief Returns an unique id of cloud content on mcloud. |
1156 | */ |
1157 | - const std::string & content_id() const override; |
1158 | + const std::string& content_id() const override; |
1159 | |
1160 | /*! |
1161 | * \brief Returns a display name of local content. |
1162 | */ |
1163 | - const std::string & content_name() const override; |
1164 | + const std::string& content_name() const override; |
1165 | |
1166 | /*! |
1167 | * \brief Returns uploaded local content file path. |
1168 | */ |
1169 | - const std::string & file_path() const override; |
1170 | + const std::string& file_path() const override; |
1171 | |
1172 | /*! |
1173 | * \brief Contains the error string if an error occurs during content uploading. |
1174 | */ |
1175 | - const std::string & error_string() const override; |
1176 | + const std::string& error_string() const override; |
1177 | |
1178 | /*! |
1179 | * \brief Returns upload url assigned by mcloud for this task. |
1180 | * \note the url will be expired after a period of time. |
1181 | */ |
1182 | - const std::string & task_url() const override; |
1183 | + const std::string& task_url() const override; |
1184 | |
1185 | /*! |
1186 | * \brief Returns current sync-up status for this task. |
1187 | @@ -113,13 +109,13 @@ |
1188 | * \brief Handler for upload progress of a task. |
1189 | * \sa Task::ProgressHandler |
1190 | */ |
1191 | - Task::ProgressHandler & progress_changed() override; |
1192 | + Task::ProgressHandler& progress_changed() override; |
1193 | |
1194 | /*! |
1195 | * \brief Handler for upload status of a task. |
1196 | * \sa Task::StatusHandler |
1197 | */ |
1198 | - Task::StatusHandler & status_changed() override; |
1199 | + Task::StatusHandler& status_changed() override; |
1200 | |
1201 | /*! |
1202 | * \brief cancel the task. |
1203 | @@ -137,8 +133,8 @@ |
1204 | */ |
1205 | bool is_need_upload() const; |
1206 | |
1207 | -private: |
1208 | - UploadTask(std::shared_ptr<UploadTaskPriv> p); |
1209 | + private: |
1210 | + UploadTask(const std::shared_ptr<UploadTaskPriv>& p); |
1211 | |
1212 | friend class SyncManagerPriv; |
1213 | |
1214 | |
1215 | === modified file 'provider/CMakeLists.txt' |
1216 | --- provider/CMakeLists.txt 2016-09-20 02:39:38 +0000 |
1217 | +++ provider/CMakeLists.txt 2016-10-26 10:36:06 +0000 |
1218 | @@ -7,9 +7,9 @@ |
1219 | |
1220 | add_definitions(-DBOOST_THREAD_VERSION=4) |
1221 | |
1222 | -add_executable(mcloud-provider main.cpp McloudProvider.cpp) |
1223 | +add_library(mcloud-provider-static STATIC mcloudprovider.cpp) |
1224 | |
1225 | -add_library(mcloud-provider-static STATIC McloudProvider.cpp) |
1226 | +add_executable(mcloud-provider main.cpp mcloudprovider.cpp) |
1227 | |
1228 | target_link_libraries( |
1229 | mcloud-provider |
1230 | |
1231 | === removed file 'provider/McloudProvider.cpp' |
1232 | --- provider/McloudProvider.cpp 2016-09-26 01:43:23 +0000 |
1233 | +++ provider/McloudProvider.cpp 1970-01-01 00:00:00 +0000 |
1234 | @@ -1,666 +0,0 @@ |
1235 | -/* |
1236 | - * Copyright (C) 2016 Canonical Ltd |
1237 | - * |
1238 | - * This program is free software: you can redistribute it and/or modify |
1239 | - * it under the terms of the GNU Lesser General Public License version 3 as |
1240 | - * published by the Free Software Foundation. |
1241 | - * |
1242 | - * This program is distributed in the hope that it will be useful, |
1243 | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
1244 | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
1245 | - * GNU Lesser General Public License for more details. |
1246 | - * |
1247 | - * You should have received a copy of the GNU Lesser General Public License |
1248 | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
1249 | - * |
1250 | - * Authors: Gary Wang <gary.wang@canonical.com> |
1251 | - */ |
1252 | - |
1253 | -#include "McloudProvider.h" |
1254 | -#include <unity/storage/provider/ProviderBase.h> |
1255 | -#include <unity/storage/provider/TempfileUploadJob.h> |
1256 | -#include <unity/storage/provider/UploadJob.h> |
1257 | -#include <unity/storage/provider/DownloadJob.h> |
1258 | -#include <unity/storage/provider/metadata_keys.h> |
1259 | -#include <unity/storage/provider/Exceptions.h> |
1260 | - |
1261 | -#include <boost/thread.hpp> |
1262 | -#include <boost/thread/future.hpp> |
1263 | -#include <boost/filesystem.hpp> |
1264 | -#include <boost/make_shared.hpp> |
1265 | - |
1266 | -#include <unistd.h> |
1267 | -#include <sys/socket.h> |
1268 | -#include <iostream> |
1269 | -#include <memory> |
1270 | -#include <mutex> |
1271 | -#include <stdexcept> |
1272 | - |
1273 | -#include <mcloud/api/client.h> |
1274 | -#include <mcloud/api/uploadtask.h> |
1275 | -#include <mcloud/api/syncmanager.h> |
1276 | -#include <mcloud/api/cloudresource.h> |
1277 | -#include <mcloud/api/cloudcontent.h> |
1278 | -#include <mcloud/api/cloudfolder.h> |
1279 | -#include <mcloud/api/exceptions.h> |
1280 | - |
1281 | -using namespace std; |
1282 | -using namespace unity::storage; |
1283 | -using namespace unity::storage::provider; |
1284 | -using namespace mcloud::api; |
1285 | - |
1286 | -using boost::make_ready_future; |
1287 | -using boost::make_exceptional_future; |
1288 | - |
1289 | -namespace { |
1290 | - static const int TIME_OUT = 10; |
1291 | - static const int CLIENT_COUNT = 3; |
1292 | - |
1293 | - static const char *FOLDER_TYPE[] = {"normal", "pictures", "music", "videos", "message", "docs", "app", "sync"}; |
1294 | - static const char *CONTENT_TYPE[] = {"all", "image", "audio", "video", "other", "doc", "spreadsheet", "ppt"}; |
1295 | - static const char *STATUS[] = {"unstart", "running", "canceled", "paused", "broken", "complete"}; |
1296 | - |
1297 | - string make_job_id() |
1298 | - { |
1299 | - static int last_upload_id = 0; |
1300 | - return to_string(++last_upload_id); |
1301 | - } |
1302 | - |
1303 | - string status_to_string(Task::Status status) |
1304 | - { |
1305 | - return STATUS[int(status)]; |
1306 | - } |
1307 | - |
1308 | - string folder_type_to_string(CloudFolder::Type type) |
1309 | - { |
1310 | - return FOLDER_TYPE[int(type)]; |
1311 | - } |
1312 | - |
1313 | - string content_type_to_string(CloudContent::Type type) |
1314 | - { |
1315 | - return CONTENT_TYPE[int(type)]; |
1316 | - } |
1317 | - |
1318 | - string time_to_iso(time_t t) |
1319 | - { |
1320 | - char buf[sizeof "2016-08-11T15:10:07+0000"]; |
1321 | - strftime(buf, sizeof buf, "%FT%T%z", gmtime(&t)); |
1322 | - return buf; |
1323 | - } |
1324 | - |
1325 | - int pending_jobs_count(Client::Ptr client, McloudProvider::JobMode mode) |
1326 | - { |
1327 | - int count = 0; |
1328 | - auto syncmanager = client->syncmanager(); |
1329 | - if (mode == McloudProvider::JobMode::Download) { |
1330 | - auto download_task_queue = syncmanager->download_queue(); |
1331 | - for (auto & item_ptr : download_task_queue) { |
1332 | - if (item_ptr->status() == Task::Status::Running |
1333 | - || item_ptr->status() == Task::Status::Paused |
1334 | - || item_ptr->status() == Task::Status::Unstart) { |
1335 | - count++; |
1336 | - } |
1337 | - } |
1338 | - } else if (mode == McloudProvider::JobMode::Upload) { |
1339 | - auto upload_task_queue = syncmanager->upload_queue(); |
1340 | - for (auto & item_ptr : upload_task_queue) { |
1341 | - if (item_ptr->status() == Task::Status::Running |
1342 | - || item_ptr->status() == Task::Status::Paused |
1343 | - || item_ptr->status() == Task::Status::Unstart) { |
1344 | - count++; |
1345 | - } |
1346 | - } |
1347 | - } |
1348 | - |
1349 | - return count; |
1350 | - } |
1351 | - |
1352 | - Item content_to_item(CloudResource::Ptr resource) |
1353 | - { |
1354 | - Item item; |
1355 | - item.item_id = resource->id(); |
1356 | - item.parent_ids = {resource->parent_catalog_id()}; |
1357 | - item.name = resource->name(); |
1358 | - item.etag = resource->etag(); |
1359 | - item.metadata["owner"] = resource->owner(); |
1360 | - item.metadata[provider::CREATION_TIME] = time_to_iso(resource->created_date()); |
1361 | - item.metadata[provider::LAST_MODIFIED_TIME] = time_to_iso(resource->updated_date()); |
1362 | - if (resource->property() == CloudResource::Property::Folder) { |
1363 | - item.type = ItemType::folder; |
1364 | - auto folder = std::static_pointer_cast<mcloud::api::CloudFolder>(resource); |
1365 | - item.metadata["folder_type"] = folder_type_to_string(folder->folder_type()); |
1366 | - item.metadata["folder_path"] = folder->folder_path(); |
1367 | - } else if (resource->property() == CloudResource::Property::Content){ |
1368 | - item.type = ItemType::file; |
1369 | - auto file = std::static_pointer_cast<mcloud::api::CloudContent>(resource); |
1370 | - item.metadata["suffix"] = file->suffix(); |
1371 | - item.metadata["content_type"] = content_type_to_string(file->type()); |
1372 | - |
1373 | - item.metadata[provider::SIZE_IN_BYTES] = file->content_size(); |
1374 | - item.metadata["description"] = file->description(); |
1375 | - item.metadata["thumbnail_url"] = file->thumbnail_url(); |
1376 | - item.metadata["big_thumbnail_url"] = file->big_thumbnail_url(); |
1377 | - item.metadata["present_url"] = file->big_thumbnail_url(); |
1378 | - } |
1379 | - |
1380 | - return item; |
1381 | - } |
1382 | -} |
1383 | - |
1384 | -class McloudUploadJob : public UploadJob |
1385 | -{ |
1386 | -public: |
1387 | - McloudUploadJob(string const& upload_id, |
1388 | - string const& parent_id, |
1389 | - string const& file_name, |
1390 | - int64_t size, |
1391 | - bool allow_overwrite, |
1392 | - Client::Ptr client); |
1393 | - |
1394 | - boost::future<void> cancel() override; |
1395 | - boost::future<Item> finish() override; |
1396 | -private: |
1397 | - boost::future<tuple<bool, string>> upload_data(); |
1398 | - void stop_and_cancel(); |
1399 | -private: |
1400 | - ssize_t feed_size; |
1401 | - string parent_id_; |
1402 | - string file_name_; |
1403 | - int64_t upload_size_; |
1404 | - bool allow_overwrite_; |
1405 | - |
1406 | - boost::future<tuple<bool, string>> upload_future_; |
1407 | - |
1408 | - std::mutex mutex_; |
1409 | - |
1410 | - UploadTask::Ptr task_; |
1411 | - Client::Ptr client_; |
1412 | -}; |
1413 | - |
1414 | -class McloudDownloadJob : public DownloadJob |
1415 | -{ |
1416 | -public: |
1417 | - McloudDownloadJob(string const& download_id, |
1418 | - string const& item_id, |
1419 | - Client::Ptr client); |
1420 | - |
1421 | - boost::future<void> cancel() override; |
1422 | - boost::future<void> finish() override; |
1423 | -private: |
1424 | - boost::future<tuple<bool, string>> download_data(); |
1425 | - void send_data(); |
1426 | - void stop_and_cancel(); |
1427 | -private: |
1428 | - string item_id_; |
1429 | - boost::future<tuple<bool, string>> download_future_; |
1430 | - |
1431 | - std::mutex mutex_; |
1432 | - |
1433 | - DownloadTask::Ptr task_; |
1434 | - Client::Ptr client_; |
1435 | -}; |
1436 | - |
1437 | -McloudProvider::McloudProvider() |
1438 | - : client_list_(CLIENT_COUNT, std::make_shared<Client>(TIME_OUT)) |
1439 | -{ |
1440 | -} |
1441 | - |
1442 | -boost::future<ItemList> McloudProvider::roots(Context const& ctx) |
1443 | -{ |
1444 | - return boost::async([this, ctx](){ |
1445 | - try { |
1446 | - auto client = assign_client(ctx); |
1447 | - auto root_folder_id = client->cloud_root_folder_id(); |
1448 | - |
1449 | - ItemList roots = { |
1450 | - {root_folder_id, {}, "root", "", ItemType::root, {}} |
1451 | - }; |
1452 | - |
1453 | - return make_ready_future<ItemList>(roots); |
1454 | - } catch (runtime_error &e) { |
1455 | - return make_exceptional_future<ItemList>( |
1456 | - RemoteCommsException(string("McloudProvider::roots(): failed: ") + e.what())); |
1457 | - } |
1458 | - }); |
1459 | -} |
1460 | - |
1461 | -boost::future<tuple<ItemList,string>> McloudProvider::list( |
1462 | - string const& item_id, string const& page_token, |
1463 | - Context const& ctx) |
1464 | -{ |
1465 | - int page_token_index = 0; |
1466 | - if (!page_token.empty()) { |
1467 | - try { |
1468 | - page_token_index = stoi(page_token); |
1469 | - } catch (invalid_argument &e) { |
1470 | - return make_exceptional_future<tuple<ItemList,string>>( |
1471 | - InvalidArgumentException(string("McloudProvider::list(): invalid page token: ") + e.what())); |
1472 | - } |
1473 | - } |
1474 | - |
1475 | - return boost::async([this, item_id, page_token_index, ctx](){ |
1476 | - try { |
1477 | - const int count_per_page = 50; |
1478 | - int start_index = 1 + page_token_index * count_per_page; |
1479 | - auto client = assign_client(ctx); |
1480 | - auto content_list = client->cloud_content_list(start_index, count_per_page, |
1481 | - CloudContent::Type::All, item_id); |
1482 | - |
1483 | - ItemList roots; |
1484 | - for (const auto & content: content_list) { |
1485 | - roots.push_back(content_to_item(content)); |
1486 | - } |
1487 | - |
1488 | - int offset = 0; |
1489 | - boost::promise<tuple<ItemList,string>> prom; |
1490 | - if (content_list.size() >= count_per_page) { |
1491 | - offset++; |
1492 | - } |
1493 | - prom.set_value(make_tuple(roots, std::to_string(page_token_index + offset))); |
1494 | - |
1495 | - return prom.get_future(); |
1496 | - } catch (InvalidIDException &e) { |
1497 | - return make_exceptional_future<tuple<ItemList,string>>( |
1498 | - NotExistsException(string("McloudProvider::list(): failed: ") + e.what(), item_id)); |
1499 | - } catch (runtime_error &e) { |
1500 | - return make_exceptional_future<tuple<ItemList,string>>( |
1501 | - RemoteCommsException(string("McloudProvider::list(): failed: ") + e.what())); |
1502 | - } |
1503 | - }); |
1504 | -} |
1505 | - |
1506 | -boost::future<ItemList> McloudProvider::lookup( |
1507 | - string const& parent_id, string const& name, |
1508 | - Context const& ctx) |
1509 | -{ |
1510 | - return boost::async([this, parent_id, name, ctx](){ |
1511 | - try { |
1512 | - const int count_per_page = 50; |
1513 | - int page_token_index = 0; |
1514 | - int start_index = 0; |
1515 | - |
1516 | - ItemList roots; |
1517 | - do { |
1518 | - page_token_index++; |
1519 | - start_index = 1 + (page_token_index - 1) * count_per_page; |
1520 | - auto client = assign_client(ctx); |
1521 | - auto content_list = client->cloud_content_list(start_index, count_per_page, |
1522 | - CloudContent::Type::All, parent_id); |
1523 | - |
1524 | - for (const auto & content: content_list) { |
1525 | - if (content->name().find(name) != string::npos) { |
1526 | - roots.push_back(content_to_item(content)); |
1527 | - } |
1528 | - } |
1529 | - |
1530 | - if (content_list.size() < count_per_page) |
1531 | - break; |
1532 | - } while (true); |
1533 | - |
1534 | - return make_ready_future<ItemList>(roots); |
1535 | - } catch (InvalidIDException &e) { |
1536 | - return make_exceptional_future<ItemList>( |
1537 | - NotExistsException(string("McloudProvider::lookup(): folder not exists: ") + e.what(), parent_id)); |
1538 | - } catch (runtime_error &e) { |
1539 | - return make_exceptional_future<ItemList>( |
1540 | - RemoteCommsException(string("McloudProvider::lookup(): failed: ") + e.what())); |
1541 | - } |
1542 | - }); |
1543 | -} |
1544 | - |
1545 | -boost::future<Item> McloudProvider::metadata(string const& item_id, |
1546 | - Context const& ctx) |
1547 | -{ |
1548 | - return boost::async([this, item_id, ctx](){ |
1549 | - try { |
1550 | - auto client = assign_client(ctx); |
1551 | - auto content = client->content_info(item_id); |
1552 | - return make_ready_future<Item>(content_to_item(content)); |
1553 | - } catch (NonExistentException &e) { |
1554 | - return make_exceptional_future<Item>( |
1555 | - NotExistsException(string("McloudProvider::metadata(): content not exists: ") + e.what(), item_id)); |
1556 | - } catch (runtime_error &e) { |
1557 | - return make_exceptional_future<Item>( |
1558 | - RemoteCommsException(string("McloudProvider::metadata(): failed: ") + e.what())); |
1559 | - } |
1560 | - }); |
1561 | -} |
1562 | - |
1563 | -boost::future<Item> McloudProvider::create_folder( |
1564 | - string const& parent_id, string const& name, |
1565 | - Context const& ctx) |
1566 | -{ |
1567 | - return boost::async([this, parent_id, name, ctx](){ |
1568 | - try { |
1569 | - auto client = assign_client(ctx); |
1570 | - auto content = client->create_folder(name, parent_id); |
1571 | - return make_ready_future<Item>(content_to_item(content)); |
1572 | - } catch (NonExistentException &e) { |
1573 | - return make_exceptional_future<Item>( |
1574 | - NotExistsException(string("McloudProvider::create_folder(): name: ") + e.what(), name)); |
1575 | - } catch (runtime_error &e) { |
1576 | - return make_exceptional_future<Item>( |
1577 | - RemoteCommsException(string("McloudProvider::create_folder(): failed: ") + e.what())); |
1578 | - } |
1579 | - }); |
1580 | -} |
1581 | - |
1582 | -boost::future<unique_ptr<UploadJob>> McloudProvider::create_file( |
1583 | - string const& parent_id, string const& name, |
1584 | - int64_t size, string const& /*content_type*/, bool allow_overwrite, |
1585 | - Context const& ctx) |
1586 | -{ |
1587 | - auto client = assign_client(ctx, JobMode::Upload); |
1588 | - return make_ready_future(unique_ptr<UploadJob>(new McloudUploadJob(make_job_id(), parent_id, name, |
1589 | - size, allow_overwrite, client))); |
1590 | -} |
1591 | - |
1592 | -boost::future<unique_ptr<UploadJob>> McloudProvider::update( |
1593 | - string const& item_id, int64_t size, string const& /*old_etag*/, |
1594 | - Context const& ctx) |
1595 | -{ |
1596 | - //mcloud doesn't have update API so do some workarounds. |
1597 | - //1.fetch metadata to get the content name and parent folder id; |
1598 | - //2.delete that file |
1599 | - //3.create a new file in the original folder with the same file name. |
1600 | - //side effect: the original item id is changed after updated. |
1601 | - |
1602 | - return boost::async([this, item_id, size, ctx](){ |
1603 | - try { |
1604 | - auto client = assign_client(ctx); |
1605 | - auto content = client->content_info(item_id); |
1606 | - auto file_name = content->name(); |
1607 | - auto parent_id = content->parent_catalog_id(); |
1608 | - |
1609 | - delete_item(item_id, ctx); |
1610 | - |
1611 | - return create_file(parent_id, file_name, size, "", true, ctx); |
1612 | - } catch (runtime_error &e) { |
1613 | - return make_exceptional_future<unique_ptr<UploadJob>>( |
1614 | - RemoteCommsException(string("McloudProvider::update(): failed: ") + e.what())); |
1615 | - } |
1616 | - }); |
1617 | -} |
1618 | - |
1619 | -boost::future<unique_ptr<DownloadJob>> McloudProvider::download( |
1620 | - string const& item_id, Context const& ctx) |
1621 | -{ |
1622 | - auto client = assign_client(ctx, JobMode::Download); |
1623 | - return make_ready_future(unique_ptr<DownloadJob>(new McloudDownloadJob(make_job_id(), item_id, client))); |
1624 | -} |
1625 | - |
1626 | -boost::future<void> McloudProvider::delete_item( |
1627 | - string const& item_id, Context const& ctx) |
1628 | -{ |
1629 | - return boost::async([this, item_id, ctx](){ |
1630 | - try { |
1631 | - auto client = assign_client(ctx); |
1632 | - Client::Stringlist content_id_list{{item_id}}; |
1633 | - client->delete_contents(content_id_list); |
1634 | - return make_ready_future(); |
1635 | - } catch (ParameterInvalidException &e) { |
1636 | - return make_exceptional_future<void>( |
1637 | - NotExistsException(string("McloudProvider::delete_item(): failed: ") + e.what(), item_id)); |
1638 | - } catch (runtime_error &e) { |
1639 | - return make_exceptional_future<void>( |
1640 | - RemoteCommsException(string("McloudProvider::delete_item(): failed: ") + e.what())); |
1641 | - } |
1642 | - }); |
1643 | -} |
1644 | - |
1645 | -boost::future<Item> McloudProvider::move( |
1646 | - string const& item_id, string const& new_parent_id, |
1647 | - string const& /*new_name*/, Context const& ctx) |
1648 | -{ |
1649 | - //Mcloud doens't support changing content name when moving content |
1650 | - return boost::async([this, item_id, new_parent_id, ctx](){ |
1651 | - try { |
1652 | - auto client = assign_client(ctx); |
1653 | - Client::Stringlist folderlist; |
1654 | - Client::Stringlist contentlist{{item_id}}; |
1655 | - client->move_items(folderlist, contentlist, new_parent_id); |
1656 | - auto content = client->content_info(item_id); |
1657 | - return make_ready_future<Item>(content_to_item(content)); |
1658 | - } catch (NonExistentException &e) { |
1659 | - return make_exceptional_future<Item>( |
1660 | - NotExistsException(string("McloudProvider::move(): content or folder not exist: ") + e.what(), "")); |
1661 | - } catch (runtime_error &e) { |
1662 | - return make_exceptional_future<Item>( |
1663 | - RemoteCommsException(string("McloudProvider::move(): failed: ") + e.what())); |
1664 | - } |
1665 | - }); |
1666 | -} |
1667 | - |
1668 | -boost::future<Item> McloudProvider::copy( |
1669 | - string const& item_id, string const& new_parent_id, |
1670 | - string const& /*new_name*/, Context const& ctx) |
1671 | -{ |
1672 | - //Mcloud doens't support changing content name when copying content |
1673 | - return boost::async([this, item_id, new_parent_id, ctx](){ |
1674 | - try { |
1675 | - Client::Stringlist content_list{{item_id}}; |
1676 | - auto client = assign_client(ctx); |
1677 | - auto content_id = client->copy_contents(content_list, new_parent_id)[0]; |
1678 | - auto content = client->content_info(content_id); |
1679 | - return make_ready_future<Item>(content_to_item(content)); |
1680 | - } catch (NonExistentException &e) { |
1681 | - return make_exceptional_future<Item>( |
1682 | - NotExistsException(string("McloudProvider::copy(): content or folder not exist: ") + e.what(), item_id)); |
1683 | - } catch (runtime_error &e) { |
1684 | - return make_exceptional_future<Item>( |
1685 | - RemoteCommsException(string("McloudProvider::copy(): failed: ") + e.what())); |
1686 | - } |
1687 | - }); |
1688 | -} |
1689 | - |
1690 | -Client::Ptr McloudProvider::assign_client(Context const& ctx, JobMode mode) { |
1691 | - auto access_token = boost::get<OAuth2Credentials>(ctx.credentials).access_token; |
1692 | - if (getenv("MCLOUD_LOCAL_SERVER_URL")) { |
1693 | - access_token = "valid_token"; |
1694 | - } |
1695 | - |
1696 | - std::cout <<"mcloud access_token: " << access_token << std::endl; |
1697 | - |
1698 | - int index = 0; |
1699 | - if (mode == JobMode::Unknown) { |
1700 | - static int c_index = 0; c_index++; c_index %= CLIENT_COUNT; |
1701 | - index = c_index; |
1702 | - } else { |
1703 | - int min_count = 0; |
1704 | - for (size_t i = 0; i < client_list_.size(); i++) { |
1705 | - auto client_ptr = client_list_[i]; |
1706 | - auto pending_count = pending_jobs_count(client_ptr, mode); |
1707 | - if (i == 0 || pending_count < min_count) { |
1708 | - min_count = pending_count; |
1709 | - index = i; |
1710 | - } |
1711 | - } |
1712 | - } |
1713 | - |
1714 | - auto client = client_list_[index]; |
1715 | - client->set_access_token(access_token); |
1716 | - return client; |
1717 | -} |
1718 | - |
1719 | -McloudUploadJob::McloudUploadJob(string const &upload_id, |
1720 | - string const& parent_id, |
1721 | - string const& file_name, |
1722 | - int64_t size, |
1723 | - bool allow_overwrite, |
1724 | - Client::Ptr client) |
1725 | - : UploadJob(upload_id) |
1726 | - , parent_id_(parent_id) |
1727 | - , file_name_(file_name) |
1728 | - , upload_size_(size) |
1729 | - , allow_overwrite_(allow_overwrite) |
1730 | - , task_(nullptr) |
1731 | - , client_(client) |
1732 | -{ |
1733 | - upload_future_ = upload_data(); |
1734 | -} |
1735 | - |
1736 | -boost::future<void> McloudUploadJob::cancel() |
1737 | -{ |
1738 | - printf("cancel_upload('%s')\n", upload_id().c_str()); |
1739 | - stop_and_cancel(); |
1740 | - |
1741 | - return make_ready_future(); |
1742 | -} |
1743 | - |
1744 | -boost::future<Item> McloudUploadJob::finish() |
1745 | -{ |
1746 | - printf("finish_upload('%s')\n", upload_id().c_str()); |
1747 | - return boost::async([this](){ |
1748 | - try { |
1749 | - auto upload_ctx = upload_future_.get(); |
1750 | - auto upload_ok = get<0>(upload_ctx); |
1751 | - auto error_str = get<1>(upload_ctx); |
1752 | - if (upload_ok){ |
1753 | - auto content = client_->content_info(task_->content_id()); |
1754 | - return make_ready_future<Item>(content_to_item(content)); |
1755 | - } |
1756 | - |
1757 | - return make_exceptional_future<Item>( |
1758 | - RemoteCommsException(string("McloudUploadJob::finish(): failed: ") + error_str)); |
1759 | - } catch (runtime_error &e) { |
1760 | - return make_exceptional_future<Item>( |
1761 | - RemoteCommsException(string("McloudUploadJob::finish(): failed: ") + e.what())); |
1762 | - } |
1763 | - }); |
1764 | -} |
1765 | - |
1766 | -boost::future<tuple<bool, string>> McloudUploadJob::upload_data() |
1767 | -{ |
1768 | - auto prom = boost::make_shared<boost::promise<tuple<bool, string>>>(); |
1769 | - |
1770 | - return boost::async([this, prom](){ |
1771 | - std::lock_guard<std::mutex> guard(mutex_); |
1772 | - |
1773 | - int socket_fd = read_socket(); |
1774 | - UploadBufferCb buffer_cb{[socket_fd](void *dest, size_t buf_size) -> size_t { |
1775 | - //data reading callback. |
1776 | - size_t read_size = read(socket_fd, dest, buf_size); |
1777 | - //explicitly send EOF(-1) if read_size == 0 to notify net-cpp to throw an exception if |
1778 | - //sth wrong with data reading to avoid hangs here. |
1779 | - if (read_size == 0) { |
1780 | - return -1; |
1781 | - } |
1782 | - return read_size; |
1783 | - }, (size_t)upload_size_, parent_id_, file_name_}; |
1784 | - |
1785 | - try { |
1786 | - task_ = client_->syncmanager()->add_upload_task(buffer_cb); |
1787 | - task_->status_changed() = [this, prom](Task::Status status) { |
1788 | - std::cout << " status: " << status_to_string(status) << std::endl; |
1789 | - if (status == Task::Status::Complete){ |
1790 | - prom->set_value(make_tuple(true, string())); |
1791 | - } else if (status == Task::Status::Canceled || |
1792 | - status == Task::Status::Broken) { |
1793 | - prom->set_value(make_tuple(false, task_->error_string())); |
1794 | - } |
1795 | - }; |
1796 | - task_->progress_changed() = [this](float percent) { |
1797 | - cout<< "uploading: " << task_->content_name() << " " << percent << endl; |
1798 | - }; |
1799 | - } catch (runtime_error & e) { |
1800 | - prom->set_value(make_tuple(false, e.what())); |
1801 | - } |
1802 | - |
1803 | - return prom->get_future(); |
1804 | - }); |
1805 | -} |
1806 | - |
1807 | -void McloudUploadJob::stop_and_cancel() |
1808 | -{ |
1809 | - std::lock_guard<std::mutex> guard(mutex_); |
1810 | - |
1811 | - if (task_ != nullptr && |
1812 | - (task_->status() != Task::Status::Broken && |
1813 | - task_->status() != Task::Status::Complete)) { |
1814 | - task_->cancel(); |
1815 | - } |
1816 | -} |
1817 | - |
1818 | -McloudDownloadJob::McloudDownloadJob(string const &download_id, |
1819 | - string const &item_id, |
1820 | - Client::Ptr client) |
1821 | - : DownloadJob(download_id) |
1822 | - , item_id_(item_id) |
1823 | - , task_(nullptr) |
1824 | - , client_(client) |
1825 | -{ |
1826 | - download_future_ = download_data(); |
1827 | -} |
1828 | - |
1829 | -boost::future<void> McloudDownloadJob::cancel() |
1830 | -{ |
1831 | - stop_and_cancel(); |
1832 | - |
1833 | - printf("cancel_download('%s')\n", download_id().c_str()); |
1834 | - return make_ready_future(); |
1835 | -} |
1836 | - |
1837 | -boost::future<void> McloudDownloadJob::finish() |
1838 | -{ |
1839 | - return boost::async([this]() { |
1840 | - auto download_ctx = download_future_.get(); |
1841 | - auto download_ok = get<0>(download_ctx); |
1842 | - auto error_str = get<1>(download_ctx); |
1843 | - if (download_ok){ |
1844 | - return make_ready_future(); |
1845 | - } |
1846 | - |
1847 | - return make_exceptional_future<void>( |
1848 | - RemoteCommsException(string("failed to download from mcloud: ") + error_str)); |
1849 | - }); |
1850 | -} |
1851 | - |
1852 | -boost::future<tuple<bool, string>> McloudDownloadJob::download_data() |
1853 | -{ |
1854 | - auto prom = boost::make_shared<boost::promise<tuple<bool, string>>>(); |
1855 | - |
1856 | - return boost::async([this, prom](){ |
1857 | - std::lock_guard<std::mutex> guard(mutex_); |
1858 | - |
1859 | - int socket_fd = write_socket(); |
1860 | - DownloadBufferCb buffer_cb{item_id_, |
1861 | - [socket_fd](void *dest, size_t buf_size) -> size_t { |
1862 | - //data writing callback. |
1863 | - return write(socket_fd, dest, buf_size); |
1864 | - } |
1865 | - }; |
1866 | - |
1867 | - try { |
1868 | - task_ = client_->syncmanager()->add_download_task(buffer_cb); |
1869 | - task_->status_changed() = [this, prom](Task::Status status) { |
1870 | - std::cout << " status: " << status_to_string(status) << std::endl; |
1871 | - if (status == Task::Status::Complete) { |
1872 | - report_complete(); |
1873 | - prom->set_value(make_tuple(true, string())); |
1874 | - } else if (status == Task::Status::Canceled || |
1875 | - status == Task::Status::Broken) { |
1876 | - prom->set_value(make_tuple(false, task_->error_string())); |
1877 | - } |
1878 | - }; |
1879 | - task_->progress_changed() = [this](float percent) { |
1880 | - cout<< "downloading: " << task_->content_name() << " " << percent << endl; |
1881 | - }; |
1882 | - } catch (runtime_error & e) { |
1883 | - prom->set_value(make_tuple(false, e.what())); |
1884 | - } |
1885 | - |
1886 | - return prom->get_future(); |
1887 | - }); |
1888 | -} |
1889 | - |
1890 | -void McloudDownloadJob::stop_and_cancel() |
1891 | -{ |
1892 | - std::lock_guard<std::mutex> guard(mutex_); |
1893 | - |
1894 | - if (task_ != nullptr && |
1895 | - (task_->status() != Task::Status::Broken && |
1896 | - task_->status() != Task::Status::Complete)) { |
1897 | - task_->cancel(); |
1898 | - } |
1899 | -} |
1900 | - |
1901 | |
1902 | === removed file 'provider/McloudProvider.h' |
1903 | --- provider/McloudProvider.h 2016-09-16 03:38:16 +0000 |
1904 | +++ provider/McloudProvider.h 1970-01-01 00:00:00 +0000 |
1905 | @@ -1,82 +0,0 @@ |
1906 | -/* |
1907 | - * Copyright (C) 2016 Canonical Ltd |
1908 | - * |
1909 | - * This program is free software: you can redistribute it and/or modify |
1910 | - * it under the terms of the GNU Lesser General Public License version 3 as |
1911 | - * published by the Free Software Foundation. |
1912 | - * |
1913 | - * This program is distributed in the hope that it will be useful, |
1914 | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
1915 | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
1916 | - * GNU Lesser General Public License for more details. |
1917 | - * |
1918 | - * You should have received a copy of the GNU Lesser General Public License |
1919 | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
1920 | - * |
1921 | - * Authors: Gary Wang <gary.wang@canonical.com> |
1922 | - */ |
1923 | - |
1924 | -#pragma once |
1925 | - |
1926 | -#include <unity/storage/provider/ProviderBase.h> |
1927 | -#include <mcloud/api/client.h> |
1928 | - |
1929 | -using namespace std; |
1930 | -using namespace mcloud::api; |
1931 | -using unity::storage::provider::Context; |
1932 | -using unity::storage::provider::DownloadJob; |
1933 | -using unity::storage::provider::ProviderBase; |
1934 | -using unity::storage::provider::Item; |
1935 | -using unity::storage::provider::ItemList; |
1936 | -using unity::storage::provider::UploadJob; |
1937 | - |
1938 | - |
1939 | -class McloudProvider : public ProviderBase { |
1940 | -public: |
1941 | - |
1942 | - enum class JobMode { |
1943 | - Upload, |
1944 | - Download, |
1945 | - Unknown |
1946 | - }; |
1947 | - |
1948 | - McloudProvider(); |
1949 | - |
1950 | - boost::future<ItemList> roots(Context const& ctx) override; |
1951 | - boost::future<tuple<ItemList,string>> list( |
1952 | - string const& item_id, string const& page_token, |
1953 | - Context const& ctx) override; |
1954 | - boost::future<ItemList> lookup( |
1955 | - string const& parent_id, string const& name, |
1956 | - Context const& ctx) override; |
1957 | - boost::future<Item> metadata( |
1958 | - string const& item_id, Context const& ctx) override; |
1959 | - boost::future<Item> create_folder( |
1960 | - string const& parent_id, string const& name, |
1961 | - Context const& ctx) override; |
1962 | - |
1963 | - boost::future<unique_ptr<UploadJob>> create_file( |
1964 | - string const& parent_id, string const& name, |
1965 | - int64_t size, string const& content_type, bool allow_overwrite, |
1966 | - Context const& ctx) override; |
1967 | - boost::future<unique_ptr<UploadJob>> update( |
1968 | - string const& item_id, int64_t size, string const& old_etag, |
1969 | - Context const& ctx) override; |
1970 | - |
1971 | - boost::future<unique_ptr<DownloadJob>> download( |
1972 | - string const& item_id, Context const& ctx) override; |
1973 | - |
1974 | - boost::future<void> delete_item( |
1975 | - string const& item_id, Context const& ctx) override; |
1976 | - boost::future<Item> move( |
1977 | - string const& item_id, string const& new_parent_id, |
1978 | - string const& new_name, Context const& ctx) override; |
1979 | - boost::future<Item> copy( |
1980 | - string const& item_id, string const& new_parent_id, |
1981 | - string const& new_name, Context const& ctx) override; |
1982 | - |
1983 | -private: |
1984 | - Client::Ptr assign_client(Context const& ctx, JobMode job = JobMode::Unknown); |
1985 | -private: |
1986 | - vector<Client::Ptr> client_list_; |
1987 | -}; |
1988 | |
1989 | === modified file 'provider/main.cpp' |
1990 | --- provider/main.cpp 2016-09-13 06:55:27 +0000 |
1991 | +++ provider/main.cpp 2016-10-26 10:36:06 +0000 |
1992 | @@ -1,20 +1,18 @@ |
1993 | -#include "McloudProvider.h" |
1994 | +#include "mcloudprovider.h" |
1995 | #include <unity/storage/provider/Server.h> |
1996 | |
1997 | using namespace std; |
1998 | using namespace unity::storage::provider; |
1999 | |
2000 | -int main(int argc, char **argv) |
2001 | +int main(int argc, char** argv) |
2002 | { |
2003 | - const string bus_name = "com.canonical.StorageFramework.Provider.McloudProvider"; |
2004 | - string account_service_id = "com.canonical.scopes.mcloud_mcloud_mcloud"; |
2005 | - if (argc > 1) |
2006 | - { |
2007 | - account_service_id = argv[1]; |
2008 | - } |
2009 | + const string bus_name = "com.canonical.StorageFramework.Provider.McloudProvider"; |
2010 | + string account_service_id = "com.canonical.scopes.mcloud_mcloud_mcloud"; |
2011 | + if (argc > 1) { |
2012 | + account_service_id = argv[1]; |
2013 | + } |
2014 | |
2015 | - Server<McloudProvider> server(bus_name, account_service_id); |
2016 | - server.init(argc, argv); |
2017 | - server.run(); |
2018 | + Server<McloudProvider> server(bus_name, account_service_id); |
2019 | + server.init(argc, argv); |
2020 | + server.run(); |
2021 | } |
2022 | - |
2023 | |
2024 | === added file 'provider/mcloudprovider.cpp' |
2025 | --- provider/mcloudprovider.cpp 1970-01-01 00:00:00 +0000 |
2026 | +++ provider/mcloudprovider.cpp 2016-10-26 10:36:06 +0000 |
2027 | @@ -0,0 +1,648 @@ |
2028 | +/* |
2029 | + * Copyright (C) 2016 Canonical Ltd |
2030 | + * |
2031 | + * This program is free software: you can redistribute it and/or modify |
2032 | + * it under the terms of the GNU Lesser General Public License version 3 as |
2033 | + * published by the Free Software Foundation. |
2034 | + * |
2035 | + * This program is distributed in the hope that it will be useful, |
2036 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
2037 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
2038 | + * GNU Lesser General Public License for more details. |
2039 | + * |
2040 | + * You should have received a copy of the GNU Lesser General Public License |
2041 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
2042 | + * |
2043 | + * Authors: Gary Wang <gary.wang@canonical.com> |
2044 | + */ |
2045 | + |
2046 | +#include "mcloudprovider.h" |
2047 | +#include <unity/storage/provider/ProviderBase.h> |
2048 | +#include <unity/storage/provider/TempfileUploadJob.h> |
2049 | +#include <unity/storage/provider/UploadJob.h> |
2050 | +#include <unity/storage/provider/DownloadJob.h> |
2051 | +#include <unity/storage/provider/metadata_keys.h> |
2052 | +#include <unity/storage/provider/Exceptions.h> |
2053 | + |
2054 | +#include <boost/thread.hpp> |
2055 | +#include <boost/thread/future.hpp> |
2056 | +#include <boost/filesystem.hpp> |
2057 | +#include <boost/make_shared.hpp> |
2058 | +#include <boost/uuid/uuid_generators.hpp> |
2059 | +#include <boost/uuid/uuid_io.hpp> |
2060 | + |
2061 | +#include <unistd.h> |
2062 | +#include <sys/socket.h> |
2063 | +#include <iostream> |
2064 | +#include <memory> |
2065 | +#include <mutex> |
2066 | +#include <stdexcept> |
2067 | + |
2068 | +#include <mcloud/api/client.h> |
2069 | +#include <mcloud/api/uploadtask.h> |
2070 | +#include <mcloud/api/syncmanager.h> |
2071 | +#include <mcloud/api/cloudresource.h> |
2072 | +#include <mcloud/api/cloudcontent.h> |
2073 | +#include <mcloud/api/cloudfolder.h> |
2074 | +#include <mcloud/api/exceptions.h> |
2075 | + |
2076 | +using namespace std; |
2077 | +using namespace unity::storage; |
2078 | +using namespace unity::storage::provider; |
2079 | +using namespace mcloud::api; |
2080 | +using namespace boost::uuids; |
2081 | + |
2082 | +using boost::make_ready_future; |
2083 | +using boost::make_exceptional_future; |
2084 | + |
2085 | +namespace { |
2086 | + static constexpr const int TIME_OUT = 10; |
2087 | + static constexpr const int CLIENT_COUNT = 3; |
2088 | + |
2089 | + static const char* FOLDER_TYPE[] = {"normal", "pictures", "music", "videos", "message", "docs", "app", "sync"}; |
2090 | + static const char* CONTENT_TYPE[] = {"all", "image", "audio", "video", "other", "doc", "spreadsheet", "ppt"}; |
2091 | + static const char* STATUS[] = {"unstart", "running", "canceled", "paused", "broken", "complete"}; |
2092 | + |
2093 | + string make_job_id() { |
2094 | + auto uuid = random_generator()(); |
2095 | + return to_string(uuid); |
2096 | + } |
2097 | + |
2098 | + string status_to_string(Task::Status status) { |
2099 | + return STATUS[int(status)]; |
2100 | + } |
2101 | + |
2102 | + string folder_type_to_string(CloudFolder::Type type) { |
2103 | + return FOLDER_TYPE[int(type)]; |
2104 | + } |
2105 | + |
2106 | + string content_type_to_string(CloudContent::Type type) { |
2107 | + return CONTENT_TYPE[int(type)]; |
2108 | + } |
2109 | + |
2110 | + string time_to_iso(time_t t) { |
2111 | + char buf[sizeof "2016-08-11T15:10:07+0000"]; |
2112 | + strftime(buf, sizeof buf, "%FT%T%z", gmtime(&t)); |
2113 | + return buf; |
2114 | + } |
2115 | + |
2116 | + int pending_jobs_count(Client::Ptr client, McloudProvider::JobMode mode) { |
2117 | + int count = 0; |
2118 | + auto syncmanager = client->syncmanager(); |
2119 | + if (mode == McloudProvider::JobMode::Download) { |
2120 | + auto download_task_queue = syncmanager->download_queue(); |
2121 | + for (auto& item_ptr : download_task_queue) { |
2122 | + if (item_ptr->status() == Task::Status::Running |
2123 | + || item_ptr->status() == Task::Status::Paused |
2124 | + || item_ptr->status() == Task::Status::Unstart) { |
2125 | + count++; |
2126 | + } |
2127 | + } |
2128 | + } else if (mode == McloudProvider::JobMode::Upload) { |
2129 | + auto upload_task_queue = syncmanager->upload_queue(); |
2130 | + for (auto& item_ptr : upload_task_queue) { |
2131 | + if (item_ptr->status() == Task::Status::Running |
2132 | + || item_ptr->status() == Task::Status::Paused |
2133 | + || item_ptr->status() == Task::Status::Unstart) { |
2134 | + count++; |
2135 | + } |
2136 | + } |
2137 | + } |
2138 | + |
2139 | + return count; |
2140 | + } |
2141 | + |
2142 | + Item content_to_item(CloudResource::Ptr resource) { |
2143 | + Item item; |
2144 | + item.item_id = resource->id(); |
2145 | + item.parent_ids = {resource->parent_catalog_id()}; |
2146 | + item.name = resource->name(); |
2147 | + item.etag = resource->etag(); |
2148 | + item.metadata["owner"] = resource->owner(); |
2149 | + item.metadata[provider::CREATION_TIME] = time_to_iso(resource->created_date()); |
2150 | + item.metadata[provider::LAST_MODIFIED_TIME] = time_to_iso(resource->updated_date()); |
2151 | + if (resource->property() == CloudResource::Property::Folder) { |
2152 | + item.type = ItemType::folder; |
2153 | + auto folder = std::static_pointer_cast<mcloud::api::CloudFolder>(resource); |
2154 | + item.metadata["folder_type"] = folder_type_to_string(folder->folder_type()); |
2155 | + item.metadata["folder_path"] = folder->folder_path(); |
2156 | + } else if (resource->property() == CloudResource::Property::Content) { |
2157 | + item.type = ItemType::file; |
2158 | + auto file = std::static_pointer_cast<mcloud::api::CloudContent>(resource); |
2159 | + item.metadata["suffix"] = file->suffix(); |
2160 | + item.metadata["content_type"] = content_type_to_string(file->type()); |
2161 | + |
2162 | + item.metadata[provider::SIZE_IN_BYTES] = file->content_size(); |
2163 | + item.metadata["description"] = file->description(); |
2164 | + item.metadata["thumbnail_url"] = file->thumbnail_url(); |
2165 | + item.metadata["big_thumbnail_url"] = file->big_thumbnail_url(); |
2166 | + item.metadata["present_url"] = file->big_thumbnail_url(); |
2167 | + } |
2168 | + |
2169 | + return item; |
2170 | + } |
2171 | +} |
2172 | + |
2173 | +class McloudUploadJob : public UploadJob { |
2174 | + public: |
2175 | + McloudUploadJob(string const& upload_id, |
2176 | + string const& parent_id, |
2177 | + string const& file_name, |
2178 | + int64_t size, |
2179 | + bool allow_overwrite, |
2180 | + Client::Ptr client); |
2181 | + |
2182 | + boost::future<void> cancel() override; |
2183 | + boost::future<Item> finish() override; |
2184 | + private: |
2185 | + boost::future<tuple<bool, string>> upload_data(); |
2186 | + void stop_and_cancel(); |
2187 | + private: |
2188 | + ssize_t feed_size; |
2189 | + string parent_id_; |
2190 | + string file_name_; |
2191 | + int64_t upload_size_; |
2192 | + bool allow_overwrite_; |
2193 | + |
2194 | + std::mutex mutex_; |
2195 | + UploadTask::Ptr task_; |
2196 | + Client::Ptr client_; |
2197 | + boost::future<tuple<bool, string>> upload_future_; |
2198 | +}; |
2199 | + |
2200 | +class McloudDownloadJob : public DownloadJob { |
2201 | + public: |
2202 | + McloudDownloadJob(string const& download_id, |
2203 | + string const& item_id, |
2204 | + Client::Ptr client); |
2205 | + |
2206 | + boost::future<void> cancel() override; |
2207 | + boost::future<void> finish() override; |
2208 | + private: |
2209 | + boost::future<tuple<bool, string>> download_data(); |
2210 | + void send_data(); |
2211 | + void stop_and_cancel(); |
2212 | + private: |
2213 | + string item_id_; |
2214 | + |
2215 | + std::mutex mutex_; |
2216 | + DownloadTask::Ptr task_; |
2217 | + Client::Ptr client_; |
2218 | + boost::future<tuple<bool, string>> download_future_; |
2219 | +}; |
2220 | + |
2221 | +McloudProvider::McloudProvider() |
2222 | + : client_list_(CLIENT_COUNT, std::make_shared<Client>(TIME_OUT)) { |
2223 | +} |
2224 | + |
2225 | +boost::future<ItemList> McloudProvider::roots(Context const& ctx) { |
2226 | + return boost::async([this, ctx]() { |
2227 | + try { |
2228 | + auto client = assign_client(ctx); |
2229 | + auto root_folder_id = client->cloud_root_folder_id(); |
2230 | + |
2231 | + ItemList roots = { |
2232 | + {root_folder_id, {}, "root", "", ItemType::root, {}} |
2233 | + }; |
2234 | + |
2235 | + return make_ready_future<ItemList>(roots); |
2236 | + } catch (runtime_error& e) { |
2237 | + return make_exceptional_future<ItemList>( |
2238 | + RemoteCommsException(string("McloudProvider::roots() failed: ") + e.what())); |
2239 | + } |
2240 | + }); |
2241 | +} |
2242 | + |
2243 | +boost::future<tuple<ItemList, string>> McloudProvider::list(string const& item_id, |
2244 | + string const& page_token, |
2245 | + Context const& ctx) { |
2246 | + int page_token_index = 0; |
2247 | + if (!page_token.empty()) { |
2248 | + try { |
2249 | + page_token_index = stoi(page_token); |
2250 | + } catch (invalid_argument& e) { |
2251 | + return make_exceptional_future<tuple<ItemList, string>>( |
2252 | + InvalidArgumentException(string("McloudProvider::list() invalid page token: ") + e.what())); |
2253 | + } |
2254 | + } |
2255 | + |
2256 | + return boost::async([this, item_id, page_token_index, ctx]() { |
2257 | + try { |
2258 | + const int count_per_page = 50; |
2259 | + int start_index = 1 + page_token_index * count_per_page; |
2260 | + auto client = assign_client(ctx); |
2261 | + auto content_list = client->cloud_content_list(start_index, count_per_page, |
2262 | + CloudContent::Type::All, item_id); |
2263 | + |
2264 | + ItemList items; |
2265 | + for (const auto& content : content_list) { |
2266 | + items.push_back(content_to_item(content)); |
2267 | + } |
2268 | + |
2269 | + int offset = 0; |
2270 | + boost::promise<tuple<ItemList, string>> prom; |
2271 | + if (content_list.size() >= count_per_page) { |
2272 | + offset++; |
2273 | + } |
2274 | + prom.set_value(make_tuple(items, std::to_string(page_token_index + offset))); |
2275 | + |
2276 | + return prom.get_future(); |
2277 | + } catch (InvalidIDException& e) { |
2278 | + return make_exceptional_future<tuple<ItemList, string>>( |
2279 | + NotExistsException(string("McloudProvider::list() failed: ") + e.what(), item_id)); |
2280 | + } catch (runtime_error& e) { |
2281 | + return make_exceptional_future<tuple<ItemList, string>>( |
2282 | + RemoteCommsException(string("McloudProvider::list() failed: ") + e.what())); |
2283 | + } |
2284 | + }); |
2285 | +} |
2286 | + |
2287 | +boost::future<ItemList> McloudProvider::lookup(string const& parent_id, |
2288 | + string const& name, |
2289 | + Context const& ctx) { |
2290 | + return boost::async([this, parent_id, name, ctx]() { |
2291 | + try { |
2292 | + const int count_per_page = 50; |
2293 | + int page_token_index = 0; |
2294 | + int start_index = 0; |
2295 | + |
2296 | + ItemList items; |
2297 | + do { |
2298 | + page_token_index++; |
2299 | + start_index = 1 + (page_token_index - 1) * count_per_page; |
2300 | + auto client = assign_client(ctx); |
2301 | + auto content_list = client->cloud_content_list(start_index, count_per_page, |
2302 | + CloudContent::Type::All, parent_id); |
2303 | + |
2304 | + for (const auto& content : content_list) { |
2305 | + if (content->name().find(name) != string::npos) { |
2306 | + items.push_back(content_to_item(content)); |
2307 | + } |
2308 | + } |
2309 | + |
2310 | + if (content_list.size() < count_per_page) { |
2311 | + break; |
2312 | + } |
2313 | + } while (true); |
2314 | + |
2315 | + return make_ready_future<ItemList>(items); |
2316 | + } catch (InvalidIDException& e) { |
2317 | + return make_exceptional_future<ItemList>( |
2318 | + NotExistsException(string("McloudProvider::lookup() folder not exists: ") + e.what(), parent_id)); |
2319 | + } catch (runtime_error& e) { |
2320 | + return make_exceptional_future<ItemList>( |
2321 | + RemoteCommsException(string("McloudProvider::lookup() failed: ") + e.what())); |
2322 | + } |
2323 | + }); |
2324 | +} |
2325 | + |
2326 | +boost::future<Item> McloudProvider::metadata(string const& item_id, |
2327 | + Context const& ctx) { |
2328 | + return boost::async([this, item_id, ctx]() { |
2329 | + try { |
2330 | + auto client = assign_client(ctx); |
2331 | + auto content = client->content_info(item_id); |
2332 | + return make_ready_future<Item>(content_to_item(content)); |
2333 | + } catch (NonExistentException& e) { |
2334 | + return make_exceptional_future<Item>( |
2335 | + NotExistsException(string("McloudProvider::metadata() content not exists: ") + e.what(), item_id)); |
2336 | + } catch (runtime_error& e) { |
2337 | + return make_exceptional_future<Item>( |
2338 | + RemoteCommsException(string("McloudProvider::metadata() failed: ") + e.what())); |
2339 | + } |
2340 | + }); |
2341 | +} |
2342 | + |
2343 | +boost::future<Item> McloudProvider::create_folder(string const& parent_id, |
2344 | + string const& name, |
2345 | + Context const& ctx) { |
2346 | + return boost::async([this, parent_id, name, ctx]() { |
2347 | + try { |
2348 | + auto client = assign_client(ctx); |
2349 | + auto content = client->create_folder(name, parent_id); |
2350 | + return make_ready_future<Item>(content_to_item(content)); |
2351 | + } catch (NonExistentException& e) { |
2352 | + return make_exceptional_future<Item>( |
2353 | + NotExistsException(string("McloudProvider::create_folder() failed: ") + e.what(), name)); |
2354 | + } catch (runtime_error& e) { |
2355 | + return make_exceptional_future<Item>( |
2356 | + RemoteCommsException(string("McloudProvider::create_folder() failed: ") + e.what())); |
2357 | + } |
2358 | + }); |
2359 | +} |
2360 | + |
2361 | +boost::future<unique_ptr<UploadJob>> McloudProvider::create_file(string const& parent_id, |
2362 | + string const& name, |
2363 | + int64_t size, |
2364 | + string const& /*content_type*/, |
2365 | + bool allow_overwrite, |
2366 | + Context const& ctx) { |
2367 | + auto client = assign_client(ctx, JobMode::Upload); |
2368 | + return make_ready_future(unique_ptr<UploadJob>(new McloudUploadJob(make_job_id(), parent_id, name, |
2369 | + size, allow_overwrite, client))); |
2370 | +} |
2371 | + |
2372 | +boost::future<unique_ptr<UploadJob>> McloudProvider::update(string const& item_id, |
2373 | + int64_t size, |
2374 | + string const& /*old_etag*/, |
2375 | + Context const& ctx) { |
2376 | + //mcloud doesn't have update API so do some workarounds. |
2377 | + //1.fetch metadata to get the content name and parent folder id; |
2378 | + //2.delete that file |
2379 | + //3.create a new file in the original folder with the same file name. |
2380 | + //side effect: the original item id is changed after updated. |
2381 | + |
2382 | + return boost::async([this, item_id, size, ctx]() { |
2383 | + try { |
2384 | + auto client = assign_client(ctx); |
2385 | + auto content = client->content_info(item_id); |
2386 | + auto file_name = content->name(); |
2387 | + auto parent_id = content->parent_catalog_id(); |
2388 | + |
2389 | + delete_item(item_id, ctx); |
2390 | + |
2391 | + return create_file(parent_id, file_name, size, "", true, ctx); |
2392 | + } catch (runtime_error& e) { |
2393 | + return make_exceptional_future<unique_ptr<UploadJob>>( |
2394 | + RemoteCommsException(string("McloudProvider::update() failed: ") + e.what())); |
2395 | + } |
2396 | + }); |
2397 | +} |
2398 | + |
2399 | +boost::future<unique_ptr<DownloadJob>> McloudProvider::download(string const& item_id, |
2400 | + Context const& ctx) { |
2401 | + auto client = assign_client(ctx, JobMode::Download); |
2402 | + return make_ready_future(unique_ptr<DownloadJob>(new McloudDownloadJob(make_job_id(), item_id, |
2403 | + client))); |
2404 | +} |
2405 | + |
2406 | +boost::future<void> McloudProvider::delete_item(string const& item_id, |
2407 | + Context const& ctx) { |
2408 | + return boost::async([this, item_id, ctx]() { |
2409 | + try { |
2410 | + auto client = assign_client(ctx); |
2411 | + Client::Stringlist content_id_list{{item_id}}; |
2412 | + client->delete_contents(content_id_list); |
2413 | + return make_ready_future(); |
2414 | + } catch (ParameterInvalidException& e) { |
2415 | + return make_exceptional_future<void>( |
2416 | + NotExistsException(string("McloudProvider::delete_item() failed: ") + e.what(), item_id)); |
2417 | + } catch (runtime_error& e) { |
2418 | + return make_exceptional_future<void>( |
2419 | + RemoteCommsException(string("McloudProvider::delete_item() failed: ") + e.what())); |
2420 | + } |
2421 | + }); |
2422 | +} |
2423 | + |
2424 | +boost::future<Item> McloudProvider::move(string const& item_id, |
2425 | + string const& new_parent_id, |
2426 | + string const& /*new_name*/, |
2427 | + Context const& ctx) { |
2428 | + //Mcloud doens't support changing content name when moving content |
2429 | + return boost::async([this, item_id, new_parent_id, ctx]() { |
2430 | + try { |
2431 | + auto client = assign_client(ctx); |
2432 | + Client::Stringlist folderlist; |
2433 | + Client::Stringlist contentlist{{item_id}}; |
2434 | + client->move_items(folderlist, contentlist, new_parent_id); |
2435 | + auto content = client->content_info(item_id); |
2436 | + return make_ready_future<Item>(content_to_item(content)); |
2437 | + } catch (NonExistentException& e) { |
2438 | + return make_exceptional_future<Item>( |
2439 | + NotExistsException(string("McloudProvider::move() content or folder not exist: ") + e.what(), "")); |
2440 | + } catch (runtime_error& e) { |
2441 | + return make_exceptional_future<Item>( |
2442 | + RemoteCommsException(string("McloudProvider::move() failed: ") + e.what())); |
2443 | + } |
2444 | + }); |
2445 | +} |
2446 | + |
2447 | +boost::future<Item> McloudProvider::copy(string const& item_id, |
2448 | + string const& new_parent_id, |
2449 | + string const& /*new_name*/, |
2450 | + Context const& ctx) { |
2451 | + //Mcloud doens't support changing content name when copying content |
2452 | + return boost::async([this, item_id, new_parent_id, ctx]() { |
2453 | + try { |
2454 | + Client::Stringlist content_list{{item_id}}; |
2455 | + auto client = assign_client(ctx); |
2456 | + auto content_id = client->copy_contents(content_list, new_parent_id)[0]; |
2457 | + auto content = client->content_info(content_id); |
2458 | + return make_ready_future<Item>(content_to_item(content)); |
2459 | + } catch (NonExistentException& e) { |
2460 | + return make_exceptional_future<Item>( |
2461 | + NotExistsException(string("McloudProvider::copy() content or folder not exist: ") + e.what(), |
2462 | + item_id)); |
2463 | + } catch (runtime_error& e) { |
2464 | + return make_exceptional_future<Item>( |
2465 | + RemoteCommsException(string("McloudProvider::copy() failed: ") + e.what())); |
2466 | + } |
2467 | + }); |
2468 | +} |
2469 | + |
2470 | +Client::Ptr McloudProvider::assign_client(Context const& ctx, JobMode mode) { |
2471 | + auto access_token = boost::get<OAuth2Credentials>(ctx.credentials).access_token; |
2472 | + if (getenv("MCLOUD_LOCAL_SERVER_URL")) { |
2473 | + access_token = "valid_token"; |
2474 | + } |
2475 | + |
2476 | + std::cout << "mcloud access_token: " << access_token << std::endl; |
2477 | + |
2478 | + int index = 0; |
2479 | + if (mode == JobMode::Unknown) { |
2480 | + static int c_index = 0; c_index++; c_index %= CLIENT_COUNT; |
2481 | + index = c_index; |
2482 | + } else { |
2483 | + int min_count = 0; |
2484 | + for (size_t i = 0; i < client_list_.size(); i++) { |
2485 | + auto client_ptr = client_list_[i]; |
2486 | + auto pending_count = pending_jobs_count(client_ptr, mode); |
2487 | + if (i == 0 || pending_count < min_count) { |
2488 | + min_count = pending_count; |
2489 | + index = i; |
2490 | + } |
2491 | + } |
2492 | + } |
2493 | + |
2494 | + auto client = client_list_[index]; |
2495 | + client->set_access_token(access_token); |
2496 | + return client; |
2497 | +} |
2498 | + |
2499 | +McloudUploadJob::McloudUploadJob(string const& upload_id, |
2500 | + string const& parent_id, |
2501 | + string const& file_name, |
2502 | + int64_t size, |
2503 | + bool allow_overwrite, |
2504 | + Client::Ptr client) |
2505 | + : UploadJob(upload_id) |
2506 | + , parent_id_(parent_id) |
2507 | + , file_name_(file_name) |
2508 | + , upload_size_(size) |
2509 | + , allow_overwrite_(allow_overwrite) |
2510 | + , task_(nullptr) |
2511 | + , client_(client) |
2512 | + , upload_future_(upload_data()) { |
2513 | +} |
2514 | + |
2515 | +boost::future<void> McloudUploadJob::cancel() { |
2516 | + printf("cancel_upload('%s')\n", upload_id().c_str()); |
2517 | + stop_and_cancel(); |
2518 | + |
2519 | + return make_ready_future(); |
2520 | +} |
2521 | + |
2522 | +boost::future<Item> McloudUploadJob::finish() { |
2523 | + printf("finish_upload('%s')\n", upload_id().c_str()); |
2524 | + return boost::async([this]() { |
2525 | + try { |
2526 | + auto upload_ctx = upload_future_.get(); |
2527 | + |
2528 | + static constexpr const size_t succ_index = 0; |
2529 | + static constexpr const size_t err_index = 1; |
2530 | + auto upload_ok = get<succ_index>(upload_ctx); |
2531 | + auto error_str = get<err_index>(upload_ctx); |
2532 | + if (upload_ok) { |
2533 | + auto content = client_->content_info(task_->content_id()); |
2534 | + return make_ready_future<Item>(content_to_item(content)); |
2535 | + } |
2536 | + |
2537 | + return make_exceptional_future<Item>( |
2538 | + RemoteCommsException(string("McloudUploadJob::finish() failed: ") + error_str)); |
2539 | + } catch (runtime_error& e) { |
2540 | + return make_exceptional_future<Item>( |
2541 | + RemoteCommsException(string("McloudUploadJob::finish() failed: ") + e.what())); |
2542 | + } |
2543 | + }); |
2544 | +} |
2545 | + |
2546 | +boost::future<tuple<bool, string>> McloudUploadJob::upload_data() { |
2547 | + auto prom = boost::make_shared<boost::promise<tuple<bool, string>>>(); |
2548 | + |
2549 | + return boost::async([this, prom]() { |
2550 | + std::lock_guard<std::mutex> guard(mutex_); |
2551 | + |
2552 | + int socket_fd = read_socket(); |
2553 | + UploadBufferCb buffer_cb{[socket_fd](void* dest, size_t buf_size) -> size_t { |
2554 | + //data reading callback. |
2555 | + size_t read_size = read(socket_fd, dest, buf_size); |
2556 | + //explicitly send EOF(-1) if read_size == 0 to notify net-cpp to throw an exception if |
2557 | + //sth wrong with data reading to avoid hangs here. |
2558 | + if (read_size == 0) { |
2559 | + return -1; |
2560 | + } |
2561 | + return read_size; |
2562 | + }, (size_t)upload_size_, parent_id_, file_name_}; |
2563 | + |
2564 | + try { |
2565 | + task_ = client_->syncmanager()->add_upload_task(buffer_cb); |
2566 | + task_->status_changed() = [this, prom](Task::Status status) { |
2567 | + std::cout << " status: " << status_to_string(status) << std::endl; |
2568 | + if (status == Task::Status::Complete) { |
2569 | + prom->set_value(make_tuple(true, string())); |
2570 | + } else if (status == Task::Status::Canceled || |
2571 | + status == Task::Status::Broken) { |
2572 | + prom->set_value(make_tuple(false, task_->error_string())); |
2573 | + } |
2574 | + }; |
2575 | + task_->progress_changed() = [this](float percent) { |
2576 | + cout << "uploading: " << task_->content_name() << " " << percent << endl; |
2577 | + }; |
2578 | + } catch (runtime_error& e) { |
2579 | + prom->set_value(make_tuple(false, e.what())); |
2580 | + } |
2581 | + |
2582 | + return prom->get_future(); |
2583 | + }); |
2584 | +} |
2585 | + |
2586 | +void McloudUploadJob::stop_and_cancel() { |
2587 | + std::lock_guard<std::mutex> guard(mutex_); |
2588 | + |
2589 | + if (task_ != nullptr && |
2590 | + (task_->status() != Task::Status::Broken && |
2591 | + task_->status() != Task::Status::Complete)) { |
2592 | + task_->cancel(); |
2593 | + } |
2594 | +} |
2595 | + |
2596 | +McloudDownloadJob::McloudDownloadJob(string const& download_id, |
2597 | + string const& item_id, |
2598 | + Client::Ptr client) |
2599 | + : DownloadJob(download_id) |
2600 | + , item_id_(item_id) |
2601 | + , task_(nullptr) |
2602 | + , client_(client) |
2603 | + , download_future_(download_data()) { |
2604 | +} |
2605 | + |
2606 | +boost::future<void> McloudDownloadJob::cancel() { |
2607 | + stop_and_cancel(); |
2608 | + |
2609 | + printf("cancel_download('%s')\n", download_id().c_str()); |
2610 | + return make_ready_future(); |
2611 | +} |
2612 | + |
2613 | +boost::future<void> McloudDownloadJob::finish() { |
2614 | + return boost::async([this]() { |
2615 | + auto download_ctx = download_future_.get(); |
2616 | + |
2617 | + static constexpr const size_t succ_index = 0; |
2618 | + static constexpr const size_t err_index = 1; |
2619 | + auto download_ok = get<succ_index>(download_ctx); |
2620 | + auto error_str = get<err_index>(download_ctx); |
2621 | + if (download_ok) { |
2622 | + return make_ready_future(); |
2623 | + } |
2624 | + |
2625 | + return make_exceptional_future<void>( |
2626 | + RemoteCommsException(string("failed to download from mcloud: ") + error_str)); |
2627 | + }); |
2628 | +} |
2629 | + |
2630 | +boost::future<tuple<bool, string>> McloudDownloadJob::download_data() { |
2631 | + auto prom = boost::make_shared<boost::promise<tuple<bool, string>>>(); |
2632 | + |
2633 | + return boost::async([this, prom]() { |
2634 | + std::lock_guard<std::mutex> guard(mutex_); |
2635 | + |
2636 | + int socket_fd = write_socket(); |
2637 | + DownloadBufferCb buffer_cb{item_id_, |
2638 | + [socket_fd](void* dest, size_t buf_size) -> size_t { |
2639 | + //data writing callback. |
2640 | + return write(socket_fd, dest, buf_size); |
2641 | + } |
2642 | + }; |
2643 | + |
2644 | + try { |
2645 | + task_ = client_->syncmanager()->add_download_task(buffer_cb); |
2646 | + task_->status_changed() = [this, prom](Task::Status status) { |
2647 | + std::cout << " status: " << status_to_string(status) << std::endl; |
2648 | + if (status == Task::Status::Complete) { |
2649 | + report_complete(); |
2650 | + prom->set_value(make_tuple(true, string())); |
2651 | + } else if (status == Task::Status::Canceled || |
2652 | + status == Task::Status::Broken) { |
2653 | + prom->set_value(make_tuple(false, task_->error_string())); |
2654 | + } |
2655 | + }; |
2656 | + task_->progress_changed() = [this](float percent) { |
2657 | + cout << "downloading: " << task_->content_name() << " " << percent << endl; |
2658 | + }; |
2659 | + } catch (runtime_error& e) { |
2660 | + prom->set_value(make_tuple(false, e.what())); |
2661 | + } |
2662 | + |
2663 | + return prom->get_future(); |
2664 | + }); |
2665 | +} |
2666 | + |
2667 | +void McloudDownloadJob::stop_and_cancel() { |
2668 | + std::lock_guard<std::mutex> guard(mutex_); |
2669 | + |
2670 | + if (task_ != nullptr && |
2671 | + (task_->status() != Task::Status::Broken && |
2672 | + task_->status() != Task::Status::Complete)) { |
2673 | + task_->cancel(); |
2674 | + } |
2675 | +} |
2676 | |
2677 | === added file 'provider/mcloudprovider.h' |
2678 | --- provider/mcloudprovider.h 1970-01-01 00:00:00 +0000 |
2679 | +++ provider/mcloudprovider.h 2016-10-26 10:36:06 +0000 |
2680 | @@ -0,0 +1,82 @@ |
2681 | +/* |
2682 | + * Copyright (C) 2016 Canonical Ltd |
2683 | + * |
2684 | + * This program is free software: you can redistribute it and/or modify |
2685 | + * it under the terms of the GNU Lesser General Public License version 3 as |
2686 | + * published by the Free Software Foundation. |
2687 | + * |
2688 | + * This program is distributed in the hope that it will be useful, |
2689 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
2690 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
2691 | + * GNU Lesser General Public License for more details. |
2692 | + * |
2693 | + * You should have received a copy of the GNU Lesser General Public License |
2694 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
2695 | + * |
2696 | + * Authors: Gary Wang <gary.wang@canonical.com> |
2697 | + */ |
2698 | + |
2699 | +#pragma once |
2700 | + |
2701 | +#include <unity/storage/provider/ProviderBase.h> |
2702 | +#include <mcloud/api/client.h> |
2703 | + |
2704 | +using namespace std; |
2705 | +using namespace mcloud::api; |
2706 | + |
2707 | +using unity::storage::provider::Context; |
2708 | +using unity::storage::provider::DownloadJob; |
2709 | +using unity::storage::provider::ProviderBase; |
2710 | +using unity::storage::provider::Item; |
2711 | +using unity::storage::provider::ItemList; |
2712 | +using unity::storage::provider::UploadJob; |
2713 | + |
2714 | + |
2715 | +class McloudProvider : public ProviderBase { |
2716 | + public: |
2717 | + |
2718 | + enum class JobMode { |
2719 | + Upload, |
2720 | + Download, |
2721 | + Unknown |
2722 | + }; |
2723 | + |
2724 | + McloudProvider(); |
2725 | + |
2726 | + boost::future<ItemList> roots(Context const& ctx) override; |
2727 | + boost::future<tuple<ItemList, string>> list( |
2728 | + string const& item_id, string const& page_token, |
2729 | + Context const& ctx) override; |
2730 | + boost::future<ItemList> lookup( |
2731 | + string const& parent_id, string const& name, |
2732 | + Context const& ctx) override; |
2733 | + boost::future<Item> metadata( |
2734 | + string const& item_id, Context const& ctx) override; |
2735 | + boost::future<Item> create_folder( |
2736 | + string const& parent_id, string const& name, |
2737 | + Context const& ctx) override; |
2738 | + |
2739 | + boost::future<unique_ptr<UploadJob>> create_file( |
2740 | + string const& parent_id, string const& name, |
2741 | + int64_t size, string const& content_type, |
2742 | + bool allow_overwrite, Context const& ctx) override; |
2743 | + boost::future<unique_ptr<UploadJob>> update( |
2744 | + string const& item_id, int64_t size, |
2745 | + string const& old_etag,Context const& ctx) override; |
2746 | + |
2747 | + boost::future<unique_ptr<DownloadJob>> download( |
2748 | + string const& item_id, Context const& ctx) override; |
2749 | + boost::future<void> delete_item( |
2750 | + string const& item_id, Context const& ctx) override; |
2751 | + boost::future<Item> move( |
2752 | + string const& item_id, string const& new_parent_id, |
2753 | + string const& new_name, Context const& ctx) override; |
2754 | + boost::future<Item> copy( |
2755 | + string const& item_id, string const& new_parent_id, |
2756 | + string const& new_name, Context const& ctx) override; |
2757 | + |
2758 | + private: |
2759 | + Client::Ptr assign_client(Context const& ctx, JobMode job = JobMode::Unknown); |
2760 | + private: |
2761 | + vector<Client::Ptr> client_list_; |
2762 | +}; |
2763 | |
2764 | === modified file 'src/mcloud/api/client.cpp' |
2765 | --- src/mcloud/api/client.cpp 2016-09-26 01:43:23 +0000 |
2766 | +++ src/mcloud/api/client.cpp 2016-10-26 10:36:06 +0000 |
2767 | @@ -18,103 +18,95 @@ |
2768 | |
2769 | #include <mcloud/api/client.h> |
2770 | |
2771 | -#include <core/net/error.h> |
2772 | -#include <core/net/uri.h> |
2773 | -#include <core/net/http/client.h> |
2774 | -#include <core/net/http/request.h> |
2775 | -#include <core/net/http/response.h> |
2776 | - |
2777 | -#include <boost/filesystem.hpp> |
2778 | -#include <boost/algorithm/string.hpp> |
2779 | - |
2780 | #include "client_priv.h" |
2781 | |
2782 | using namespace mcloud::api; |
2783 | using namespace std; |
2784 | |
2785 | Client::Client(int request_timeout) |
2786 | - : p_(std::make_shared<ClientPriv>(request_timeout)) { |
2787 | + : p_(new ClientPriv(request_timeout)) { |
2788 | } |
2789 | |
2790 | Client::~Client() { |
2791 | p_->sync_manager()->cancel(); |
2792 | } |
2793 | |
2794 | -void Client::set_access_token(const string &access_token) { |
2795 | +void Client::set_access_token(const string& access_token) { |
2796 | p_->set_access_token(access_token); |
2797 | } |
2798 | |
2799 | +bool Client::refresh_token(const string& refresh_token) { |
2800 | + return p_->refersh_token(refresh_token); |
2801 | +} |
2802 | + |
2803 | string Client::cloud_root_folder_id() { |
2804 | return p_->cloud_sync_folder_id(); |
2805 | } |
2806 | |
2807 | -bool Client::exist_on_cloud(const string &file_path, const string &folder_id) { |
2808 | - return p_->exist_on_cloud(file_path, folder_id); |
2809 | -} |
2810 | - |
2811 | -DiskInfo Client::disk_info() { |
2812 | +DiskInfo::Ptr Client::disk_info() { |
2813 | return p_->disk_info(); |
2814 | } |
2815 | |
2816 | Client::ResourceList Client::cloud_content_list(int start_index, |
2817 | int count, |
2818 | CloudContent::Type type, |
2819 | - const std::string & folder_id) { |
2820 | + const string& folder_id) { |
2821 | return p_->cloud_content_list(start_index, count, type, folder_id); |
2822 | } |
2823 | |
2824 | -CloudContent::Ptr Client::content_info(const string &content_id) { |
2825 | +CloudContent::Ptr Client::content_info(const string& content_id) { |
2826 | return p_->content_info(content_id); |
2827 | } |
2828 | |
2829 | -CloudFolder::Ptr Client::create_folder(const string &folder_name, |
2830 | - const string &folder_id) { |
2831 | +CloudFolder::Ptr Client::create_folder(const string& folder_name, |
2832 | + const string& folder_id) { |
2833 | return p_->create_folder(folder_name, folder_id); |
2834 | } |
2835 | |
2836 | -Client::ResourceList Client::look_up(const string &name, |
2837 | - const string &folder_id, |
2838 | +Client::ResourceList Client::look_up(const string& name, |
2839 | + const string& folder_id, |
2840 | CloudResource::Property property) { |
2841 | return p_->look_up(name, folder_id, property); |
2842 | } |
2843 | |
2844 | -bool Client::move_items(const Client::Stringlist &folder_ids, |
2845 | - const Client::Stringlist &content_ids, |
2846 | - const std::string &folder_id) { |
2847 | +Client::OutlinkList Client::create_folder_sharing_url(const Stringlist& folder_ids) { |
2848 | + return p_->create_folder_sharing_url(folder_ids); |
2849 | +} |
2850 | + |
2851 | +Client::OutlinkList Client::create_content_sharing_url(const Stringlist& content_ids) { |
2852 | + return p_->create_content_sharing_url(content_ids); |
2853 | +} |
2854 | + |
2855 | +Client::Stringlist Client::copy_folders(const Stringlist& folder_ids, |
2856 | + const string& folder_id) { |
2857 | + return p_->copy_folders(folder_ids, folder_id); |
2858 | +} |
2859 | + |
2860 | +Client::Stringlist Client::copy_contents(const Stringlist& contents_ids, |
2861 | + const string& folder_id) { |
2862 | + return p_->copy_contents(contents_ids, folder_id); |
2863 | +} |
2864 | + |
2865 | +bool Client::move_items(const Stringlist& folder_ids, |
2866 | + const Stringlist& content_ids, |
2867 | + const string& folder_id) { |
2868 | return p_->move_items(folder_ids, content_ids, folder_id); |
2869 | } |
2870 | |
2871 | -bool Client::update_folder(const std::string &folder_id, |
2872 | - const std::string &new_folder_name) { |
2873 | +bool Client::update_folder(const string& folder_id, |
2874 | + const string& new_folder_name) { |
2875 | return p_->update_folder(folder_id, new_folder_name); |
2876 | } |
2877 | |
2878 | +bool Client::delete_contents(const vector<string>& content_ids) { |
2879 | + return p_->delete_contents(content_ids); |
2880 | +} |
2881 | + |
2882 | +bool Client::exist_on_cloud(const string& file_path, |
2883 | + const string& folder_id) { |
2884 | + return p_->exist_on_cloud(file_path, folder_id); |
2885 | +} |
2886 | + |
2887 | SyncManager::Ptr Client::syncmanager() const { |
2888 | return p_->sync_manager(); |
2889 | } |
2890 | - |
2891 | -bool Client::delete_contents(const vector<string> &content_ids) { |
2892 | - return p_->delete_contents(content_ids); |
2893 | -} |
2894 | - |
2895 | -Client::OutlinkList Client::create_folder_extranet_link(const Stringlist &folder_ids) { |
2896 | - return p_->create_folder_extranet_link(folder_ids); |
2897 | -} |
2898 | - |
2899 | -Client::OutlinkList Client::create_content_extranet_link(const Stringlist &content_ids) { |
2900 | - return p_->create_content_extranet_link(content_ids); |
2901 | -} |
2902 | - |
2903 | -Client::Stringlist Client::copy_folders(const Client::Stringlist &folder_ids, |
2904 | - const std::string &folder_id) { |
2905 | - return p_->copy_folders(folder_ids, folder_id); |
2906 | -} |
2907 | - |
2908 | -Client::Stringlist Client::copy_contents(const Client::Stringlist &contents_ids, |
2909 | - const string &folder_id) { |
2910 | - return p_->copy_contents(contents_ids, folder_id); |
2911 | -} |
2912 | - |
2913 | -bool Client::refresh_token(const string &refresh_token) { |
2914 | - return p_->refersh_token(refresh_token); |
2915 | -} |
2916 | |
2917 | === modified file 'src/mcloud/api/client_priv.cpp' |
2918 | --- src/mcloud/api/client_priv.cpp 2016-09-26 01:43:23 +0000 |
2919 | +++ src/mcloud/api/client_priv.cpp 2016-10-26 10:36:06 +0000 |
2920 | @@ -27,7 +27,6 @@ |
2921 | #include <mcloud/api/uploadtask.h> |
2922 | #include <mcloud/api/cloudresource.h> |
2923 | #include <mcloud/api/outlink.h> |
2924 | -#include <mcloud/api/syncmanager.h> |
2925 | #include <mcloud/api/exceptions.h> |
2926 | |
2927 | #include <core/net/error.h> |
2928 | @@ -56,422 +55,424 @@ |
2929 | namespace alg = boost::algorithm; |
2930 | |
2931 | using namespace mcloud::api; |
2932 | +using namespace boost::archive::iterators; |
2933 | using namespace std; |
2934 | |
2935 | namespace { |
2936 | - |
2937 | -void log(const std::string &info) { |
2938 | + void log(const string& info) { |
2939 | #ifndef NDEBUG |
2940 | - cout << info << endl; |
2941 | + cout << info << endl; |
2942 | #else |
2943 | - (void)(info); |
2944 | + (void)(info); |
2945 | #endif |
2946 | -} |
2947 | - |
2948 | -static constexpr const char * content_type = "text/xml;UTF-8"; |
2949 | -static constexpr const char * register_app_name = "和彩云ubuntu"; |
2950 | -static constexpr const char * thirdparty_anonymous_account = "thirdparty_anonymous_account"; |
2951 | - |
2952 | -std::string encode64(const string& val) { |
2953 | - using namespace boost::archive::iterators; |
2954 | - typedef base64_from_binary<transform_width<std::string::const_iterator, 6, 8>> iter; |
2955 | - auto tmp = std::string(iter(std::begin(val)), iter(std::end(val))); |
2956 | - return tmp.append((3 - val.size() % 3) % 3, '='); |
2957 | -} |
2958 | - |
2959 | -static std::string md5sum(std::string filepath) { |
2960 | - std::ifstream ifs(filepath, std::ios::binary); |
2961 | - |
2962 | - if (!ifs.good()) { |
2963 | - std::cerr << "file is invalid: " << filepath << std::endl; |
2964 | - return std::string(); |
2965 | - } |
2966 | - |
2967 | - unsigned char hash[MD5_DIGEST_LENGTH]; |
2968 | - MD5_CTX mdContext; |
2969 | - char data[1024]; |
2970 | - |
2971 | - MD5_Init(&mdContext); |
2972 | - while(ifs.good()) { |
2973 | - ifs.read(data, sizeof(data)); |
2974 | - MD5_Update (&mdContext, data, ifs.gcount()); |
2975 | - } |
2976 | - MD5_Final (hash,&mdContext); |
2977 | - |
2978 | - std::stringstream stream; |
2979 | - for(int i = 0; i < MD5_DIGEST_LENGTH; i++) { |
2980 | - stream << std::hex << std::setw(2) << std::setfill('0') << (int)hash[i]; |
2981 | - } |
2982 | - |
2983 | - return stream.str(); |
2984 | -} |
2985 | - |
2986 | -static void append_child(tinyxml2::XMLPrinter &printer, |
2987 | - const std::string & field, |
2988 | - const std::string & value) { |
2989 | - printer.OpenElement(field.c_str()); |
2990 | - printer.PushText(value.c_str()); |
2991 | - printer.CloseElement(); |
2992 | -} |
2993 | - |
2994 | -static string generate_diskinfo_body() { |
2995 | - tinyxml2::XMLPrinter printer; |
2996 | - printer.OpenElement("getDiskInfo"); |
2997 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
2998 | - printer.CloseElement(); |
2999 | - |
3000 | - return string(printer.CStr()); |
3001 | -} |
3002 | - |
3003 | -static string generate_content_list_body(int start_index = -1, |
3004 | + } |
3005 | + |
3006 | + static constexpr const char* content_type = "text/xml;UTF-8"; |
3007 | + static constexpr const char* register_app_name = "和彩云ubuntu"; |
3008 | + static constexpr const char* thirdparty_anonymous_account = "thirdparty_anonymous_account"; |
3009 | + |
3010 | + string encode64(const string& val) { |
3011 | + typedef base64_from_binary<transform_width<string::const_iterator, 6, 8>> iter; |
3012 | + auto tmp = string(iter(std::begin(val)), iter(std::end(val))); |
3013 | + return tmp.append((3 - val.size() % 3) % 3, '='); |
3014 | + } |
3015 | + |
3016 | + static string md5sum(string filepath) { |
3017 | + std::ifstream ifs(filepath, std::ios::binary); |
3018 | + |
3019 | + if (!ifs.good()) { |
3020 | + std::cerr << "file is invalid: " << filepath << std::endl; |
3021 | + return string(); |
3022 | + } |
3023 | + |
3024 | + unsigned char hash[MD5_DIGEST_LENGTH]; |
3025 | + MD5_CTX mdContext; |
3026 | + char data[1024]; |
3027 | + |
3028 | + MD5_Init(&mdContext); |
3029 | + while (ifs.good()) { |
3030 | + ifs.read(data, sizeof(data)); |
3031 | + MD5_Update(&mdContext, data, ifs.gcount()); |
3032 | + } |
3033 | + MD5_Final(hash, &mdContext); |
3034 | + |
3035 | + stringstream stream; |
3036 | + for (int i = 0; i < MD5_DIGEST_LENGTH; i++) { |
3037 | + stream << std::hex << std::setw(2) << std::setfill('0') << (int)hash[i]; |
3038 | + } |
3039 | + |
3040 | + return stream.str(); |
3041 | + } |
3042 | + |
3043 | + static void append_child(tinyxml2::XMLPrinter& printer, |
3044 | + const string& field, |
3045 | + const string& value) { |
3046 | + printer.OpenElement(field.c_str()); |
3047 | + printer.PushText(value.c_str()); |
3048 | + printer.CloseElement(); |
3049 | + } |
3050 | + |
3051 | + static string generate_diskinfo_body() { |
3052 | + tinyxml2::XMLPrinter printer; |
3053 | + printer.OpenElement("getDiskInfo"); |
3054 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3055 | + printer.CloseElement(); |
3056 | + |
3057 | + return string(printer.CStr()); |
3058 | + } |
3059 | + |
3060 | + static string generate_contents_body(int start_index = -1, |
3061 | int count = 200, |
3062 | CloudContent::Type content_type = CloudContent::Type::All, |
3063 | - const std::string & shared_folder_id = std::string()) { |
3064 | - tinyxml2::XMLPrinter printer; |
3065 | - printer.OpenElement("getDisk"); |
3066 | - |
3067 | - //index on mcloud starts from 1, not 0 |
3068 | - if (start_index == 0) |
3069 | - start_index = 1; |
3070 | - |
3071 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3072 | - append_child(printer, "catalogID", shared_folder_id.empty() ? "root" : shared_folder_id.c_str()); |
3073 | - append_child(printer, "filterType", "0"); |
3074 | - append_child(printer, "catalogSortType", "0"); |
3075 | - append_child(printer, "contentType", std::to_string((int)content_type).c_str()); |
3076 | - append_child(printer, "contentSortType", "0"); |
3077 | - append_child(printer, "sortDirection", "1"); |
3078 | - append_child(printer, "startNumber",std::to_string(start_index).c_str()); |
3079 | - append_child(printer, "endNumber", std::to_string(start_index + count - 1).c_str()); |
3080 | - append_child(printer, "catalogType", "-1"); |
3081 | - |
3082 | - printer.CloseElement(); |
3083 | - |
3084 | - return string(printer.CStr()); |
3085 | -} |
3086 | - |
3087 | -static string generate_content_body(const std::string &content_id) { |
3088 | - tinyxml2::XMLPrinter printer; |
3089 | - printer.OpenElement("getContentInfo"); |
3090 | - append_child(printer, "ContentID", content_id); |
3091 | - append_child(printer, "CatalogID", ""); |
3092 | - append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3093 | - printer.CloseElement(); |
3094 | - |
3095 | - return string(printer.CStr()); |
3096 | -} |
3097 | - |
3098 | -static string generate_delete_body(const std::vector<std::string> &item_ids) { |
3099 | - tinyxml2::XMLPrinter printer; |
3100 | - printer.OpenElement("delCatalogContent"); |
3101 | - |
3102 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3103 | - printer.OpenElement("catalogIDs"); |
3104 | - printer.PushAttribute("length", std::to_string(item_ids.size()).c_str()); |
3105 | - for (auto & item_id: item_ids) { |
3106 | - append_child(printer, "ID", item_id.c_str()); |
3107 | - } |
3108 | - printer.CloseElement(); |
3109 | - |
3110 | - printer.OpenElement("contentIDs"); |
3111 | - printer.PushAttribute("length", std::to_string(item_ids.size()).c_str()); |
3112 | - for (auto & content_id: item_ids) { |
3113 | - append_child(printer, "ID", content_id.c_str()); |
3114 | - } |
3115 | - printer.CloseElement(); |
3116 | - |
3117 | - printer.CloseElement(); |
3118 | - |
3119 | - return string(printer.CStr()); |
3120 | -} |
3121 | - |
3122 | -static string generate_copy_body(const std::vector<std::string> &dir_ids, |
3123 | - const std::vector<std::string> &content_ids, |
3124 | - const std::string &new_folder_id) { |
3125 | - tinyxml2::XMLPrinter printer; |
3126 | - printer.OpenElement("copyContentCatalog"); |
3127 | - |
3128 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3129 | - printer.OpenElement("contentInfoList"); |
3130 | - printer.PushAttribute("length", std::to_string(content_ids.size()).c_str()); |
3131 | - for (auto & content_id: content_ids) { |
3132 | - append_child(printer, "ID", content_id.c_str()); |
3133 | - } |
3134 | - printer.CloseElement(); |
3135 | - |
3136 | - printer.OpenElement("catalogInfoList"); |
3137 | - printer.PushAttribute("length", std::to_string(dir_ids.size()).c_str()); |
3138 | - for (auto & dir_id: dir_ids) { |
3139 | - append_child(printer, "ID", dir_id.c_str()); |
3140 | - } |
3141 | - printer.CloseElement(); |
3142 | - |
3143 | - append_child(printer, "newCatalogID", new_folder_id); |
3144 | - |
3145 | - printer.CloseElement(); |
3146 | - |
3147 | - return string(printer.CStr()); |
3148 | -} |
3149 | - |
3150 | -static string generate_update_folder_body(const std::string &folder_id, |
3151 | - const std::string &new_folder_name) { |
3152 | - tinyxml2::XMLPrinter printer; |
3153 | - printer.OpenElement("updateCatalogInfo"); |
3154 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3155 | - append_child(printer, "catalogID", folder_id); |
3156 | - append_child(printer, "catalogName", new_folder_name); |
3157 | - printer.CloseElement(); |
3158 | - |
3159 | - return string(printer.CStr()); |
3160 | -} |
3161 | - |
3162 | -static string generate_create_folder_body(const std::string &folder_name, |
3163 | - const std::string &folder_id) { |
3164 | - tinyxml2::XMLPrinter printer; |
3165 | - printer.OpenElement("createCatalogExt"); |
3166 | - printer.OpenElement("createCatalogExtReq"); |
3167 | - |
3168 | - append_child(printer, "parentCatalogID", folder_id); |
3169 | - append_child(printer, "newCatalogName", folder_name); |
3170 | - append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3171 | - append_child(printer, "catalogType", "0"); |
3172 | - |
3173 | - printer.CloseElement(); |
3174 | - printer.CloseElement(); |
3175 | - |
3176 | - return string(printer.CStr()); |
3177 | -} |
3178 | - |
3179 | -static string generate_look_up_body(const std::string &name, |
3180 | - const std::string &folder_id, |
3181 | - CloudResource::Property property) { |
3182 | + const string& shared_folder_id = string()) { |
3183 | + tinyxml2::XMLPrinter printer; |
3184 | + printer.OpenElement("getDisk"); |
3185 | + |
3186 | + //index on mcloud starts from 1, not 0 |
3187 | + if (start_index == 0) { |
3188 | + start_index = 1; |
3189 | + } |
3190 | + |
3191 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3192 | + append_child(printer, "catalogID", shared_folder_id.empty() ? "root" : shared_folder_id.c_str()); |
3193 | + append_child(printer, "filterType", "0"); |
3194 | + append_child(printer, "catalogSortType", "0"); |
3195 | + append_child(printer, "contentType", std::to_string((int)content_type).c_str()); |
3196 | + append_child(printer, "contentSortType", "0"); |
3197 | + append_child(printer, "sortDirection", "1"); |
3198 | + append_child(printer, "startNumber", std::to_string(start_index).c_str()); |
3199 | + append_child(printer, "endNumber", std::to_string(start_index + count - 1).c_str()); |
3200 | + append_child(printer, "catalogType", "-1"); |
3201 | + |
3202 | + printer.CloseElement(); |
3203 | + |
3204 | + return string(printer.CStr()); |
3205 | + } |
3206 | + |
3207 | + static string generate_content_body(const string& content_id) { |
3208 | + tinyxml2::XMLPrinter printer; |
3209 | + printer.OpenElement("getContentInfo"); |
3210 | + append_child(printer, "ContentID", content_id); |
3211 | + append_child(printer, "CatalogID", ""); |
3212 | + append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3213 | + printer.CloseElement(); |
3214 | + |
3215 | + return string(printer.CStr()); |
3216 | + } |
3217 | + |
3218 | + static string generate_delete_body(const std::vector<string>& item_ids) { |
3219 | + tinyxml2::XMLPrinter printer; |
3220 | + printer.OpenElement("delCatalogContent"); |
3221 | + |
3222 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3223 | + printer.OpenElement("catalogIDs"); |
3224 | + printer.PushAttribute("length", std::to_string(item_ids.size()).c_str()); |
3225 | + for (auto& item_id : item_ids) { |
3226 | + append_child(printer, "ID", item_id.c_str()); |
3227 | + } |
3228 | + printer.CloseElement(); |
3229 | + |
3230 | + printer.OpenElement("contentIDs"); |
3231 | + printer.PushAttribute("length", std::to_string(item_ids.size()).c_str()); |
3232 | + for (auto& content_id : item_ids) { |
3233 | + append_child(printer, "ID", content_id.c_str()); |
3234 | + } |
3235 | + printer.CloseElement(); |
3236 | + |
3237 | + printer.CloseElement(); |
3238 | + |
3239 | + return string(printer.CStr()); |
3240 | + } |
3241 | + |
3242 | + static string generate_copy_body(const vector<string>& dir_ids, |
3243 | + const vector<string>& content_ids, |
3244 | + const string& new_folder_id) { |
3245 | + tinyxml2::XMLPrinter printer; |
3246 | + printer.OpenElement("copyContentCatalog"); |
3247 | + |
3248 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3249 | + printer.OpenElement("contentInfoList"); |
3250 | + printer.PushAttribute("length", std::to_string(content_ids.size()).c_str()); |
3251 | + for (auto& content_id : content_ids) { |
3252 | + append_child(printer, "ID", content_id.c_str()); |
3253 | + } |
3254 | + printer.CloseElement(); |
3255 | + |
3256 | + printer.OpenElement("catalogInfoList"); |
3257 | + printer.PushAttribute("length", std::to_string(dir_ids.size()).c_str()); |
3258 | + for (auto& dir_id : dir_ids) { |
3259 | + append_child(printer, "ID", dir_id.c_str()); |
3260 | + } |
3261 | + printer.CloseElement(); |
3262 | + |
3263 | + append_child(printer, "newCatalogID", new_folder_id); |
3264 | + |
3265 | + printer.CloseElement(); |
3266 | + |
3267 | + return string(printer.CStr()); |
3268 | + } |
3269 | + |
3270 | + static string generate_update_folder_body(const string& folder_id, |
3271 | + const string& new_folder_name) { |
3272 | + tinyxml2::XMLPrinter printer; |
3273 | + printer.OpenElement("updateCatalogInfo"); |
3274 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3275 | + append_child(printer, "catalogID", folder_id); |
3276 | + append_child(printer, "catalogName", new_folder_name); |
3277 | + printer.CloseElement(); |
3278 | + |
3279 | + return string(printer.CStr()); |
3280 | + } |
3281 | + |
3282 | + static string generate_create_folder_body(const string& folder_name, |
3283 | + const string& folder_id) { |
3284 | + tinyxml2::XMLPrinter printer; |
3285 | + printer.OpenElement("createCatalogExt"); |
3286 | + printer.OpenElement("createCatalogExtReq"); |
3287 | + |
3288 | + append_child(printer, "parentCatalogID", folder_id); |
3289 | + append_child(printer, "newCatalogName", folder_name); |
3290 | + append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3291 | + append_child(printer, "catalogType", "0"); |
3292 | + |
3293 | + printer.CloseElement(); |
3294 | + printer.CloseElement(); |
3295 | + |
3296 | + return string(printer.CStr()); |
3297 | + } |
3298 | + |
3299 | + static string generate_look_up_body(const string& name, |
3300 | + const string& folder_id, |
3301 | + CloudResource::Property property) { |
3302 | #if 1 |
3303 | - tinyxml2::XMLPrinter printer; |
3304 | - printer.OpenElement("advanceSearch"); |
3305 | - printer.OpenElement("advanceSearchReq"); |
3306 | - |
3307 | - append_child(printer, "account", thirdparty_anonymous_account); |
3308 | - append_child(printer, "scope", std::to_string((int)property)); |
3309 | - |
3310 | - printer.OpenElement("fileCond"); |
3311 | - |
3312 | - append_child(printer, "prtCtlgID", folder_id); |
3313 | - append_child(printer, "name", name); |
3314 | - |
3315 | - printer.CloseElement(); |
3316 | - |
3317 | - printer.CloseElement(); |
3318 | - printer.CloseElement(); |
3319 | + tinyxml2::XMLPrinter printer; |
3320 | + printer.OpenElement("advanceSearch"); |
3321 | + printer.OpenElement("advanceSearchReq"); |
3322 | + |
3323 | + append_child(printer, "account", thirdparty_anonymous_account); |
3324 | + append_child(printer, "scope", std::to_string((int)property)); |
3325 | + |
3326 | + printer.OpenElement("fileCond"); |
3327 | + |
3328 | + append_child(printer, "prtCtlgID", folder_id); |
3329 | + append_child(printer, "name", name); |
3330 | + |
3331 | + printer.CloseElement(); |
3332 | + |
3333 | + printer.CloseElement(); |
3334 | + printer.CloseElement(); |
3335 | #else |
3336 | - tinyxml2::XMLPrinter printer; |
3337 | - printer.OpenElement("simpleSearch"); |
3338 | - printer.OpenElement("simpleSearchReq"); |
3339 | - |
3340 | - append_child(printer, "account", thirdparty_anonymous_account); |
3341 | - append_child(printer, "scope", "1100000000000000"); |
3342 | - append_child(printer, "keyword", name); |
3343 | - |
3344 | - printer.CloseElement(); |
3345 | - printer.CloseElement(); |
3346 | + tinyxml2::XMLPrinter printer; |
3347 | + printer.OpenElement("simpleSearch"); |
3348 | + printer.OpenElement("simpleSearchReq"); |
3349 | + |
3350 | + append_child(printer, "account", thirdparty_anonymous_account); |
3351 | + append_child(printer, "scope", "1100000000000000"); |
3352 | + append_child(printer, "keyword", name); |
3353 | + |
3354 | + printer.CloseElement(); |
3355 | + printer.CloseElement(); |
3356 | #endif |
3357 | - return string(printer.CStr()); |
3358 | -} |
3359 | - |
3360 | -static string generate_move_body(const Client::Stringlist &dir_ids, |
3361 | - const Client::Stringlist &content_ids, |
3362 | - const std::string &folder_id) { |
3363 | - tinyxml2::XMLPrinter printer; |
3364 | - printer.OpenElement("moveContentCatalog"); |
3365 | - |
3366 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3367 | - |
3368 | - printer.OpenElement("contentInfoList"); |
3369 | - printer.PushAttribute("length", std::to_string(content_ids.size()).c_str()); |
3370 | - for (auto & content_id: content_ids) { |
3371 | - append_child(printer, "ID", content_id.c_str()); |
3372 | - } |
3373 | - printer.CloseElement(); |
3374 | - |
3375 | - printer.OpenElement("catalogInfoList"); |
3376 | - printer.PushAttribute("length", std::to_string(dir_ids.size()).c_str()); |
3377 | - for (auto & dir_id: dir_ids) { |
3378 | - append_child(printer, "ID", dir_id.c_str()); |
3379 | - } |
3380 | - printer.CloseElement(); |
3381 | - |
3382 | - append_child(printer, "newCatalogID", folder_id); |
3383 | - |
3384 | - printer.CloseElement(); |
3385 | - |
3386 | - return string(printer.CStr()); |
3387 | -} |
3388 | - |
3389 | -static string generate_extranet_body(const Client::Stringlist &dir_ids, |
3390 | - const Client::Stringlist &content_ids) { |
3391 | - tinyxml2::XMLPrinter printer; |
3392 | - printer.OpenElement("getOutLink"); |
3393 | - printer.OpenElement("getOutLinkReq"); |
3394 | - |
3395 | - append_child(printer, "account", thirdparty_anonymous_account); |
3396 | - printer.OpenElement("caIDLst"); |
3397 | - printer.PushAttribute("length", std::to_string(dir_ids.size()).c_str()); |
3398 | - for (auto & dir_id: dir_ids) { |
3399 | - append_child(printer, "item", dir_id.c_str()); |
3400 | - } |
3401 | - printer.CloseElement(); |
3402 | - |
3403 | - printer.OpenElement("coIDLst"); |
3404 | - printer.PushAttribute("length", std::to_string(content_ids.size()).c_str()); |
3405 | - for (auto & content_id: content_ids) { |
3406 | - append_child(printer, "item", content_id.c_str()); |
3407 | - } |
3408 | - printer.CloseElement(); |
3409 | - |
3410 | - append_child(printer, "pubType", "1"); |
3411 | - |
3412 | - printer.CloseElement(); |
3413 | - printer.CloseElement(); |
3414 | - |
3415 | - return string(printer.CStr()); |
3416 | -} |
3417 | - |
3418 | -static string generate_download_body(const std::string &content_id) { |
3419 | - tinyxml2::XMLPrinter printer; |
3420 | - printer.OpenElement("downloadRequest"); |
3421 | - append_child(printer, "appName", register_app_name); |
3422 | - append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3423 | - |
3424 | - vector<string> content_ids = {{content_id}}; |
3425 | - string content_list = alg::join(content_ids, "|"); |
3426 | - |
3427 | - append_child(printer, "contentID", content_list.c_str()); |
3428 | - append_child(printer, "OwnerMSISDN", ""); |
3429 | - append_child(printer, "entryShareCatalogID", ""); |
3430 | - append_child(printer, "operation", "0"); |
3431 | - append_child(printer, "fileVersion", "-1"); |
3432 | - |
3433 | - printer.CloseElement(); |
3434 | - |
3435 | - return string(printer.CStr()); |
3436 | -} |
3437 | - |
3438 | -static string generate_upload_body(const UploadRequest & request_item) { |
3439 | - tinyxml2::XMLPrinter printer; |
3440 | - printer.OpenElement("pcUploadFileRequest"); |
3441 | - append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3442 | - append_child(printer, "fileCount", "1"); |
3443 | - |
3444 | - int64_t file_size = 0; |
3445 | - if (fs::exists(request_item.file_path)) { |
3446 | - file_size = fs::file_size(request_item.file_path); |
3447 | - } else { |
3448 | - throw std::runtime_error("file not exists"); |
3449 | - } |
3450 | - append_child(printer, "totalSize", std::to_string(file_size).c_str()); |
3451 | - |
3452 | - printer.OpenElement("uploadContentList"); |
3453 | - printer.PushAttribute("length", "1"); |
3454 | - |
3455 | - printer.OpenElement("uploadContentInfo"); |
3456 | - append_child(printer, "contentName", request_item.content_name.empty() ? |
3457 | - fs::path(request_item.file_path).filename().c_str() : request_item.content_name); |
3458 | - append_child(printer, "contentSize", std::to_string(file_size).c_str()); |
3459 | - append_child(printer, "contentDesc", ""); |
3460 | - append_child(printer, "contentTAGList", ""); |
3461 | - |
3462 | - //The parameter to check upload files' md5sum |
3463 | - //"isNeedupload" field in response body will indicate if the file exists in mcloud. |
3464 | - append_child(printer, "digest", md5sum(request_item.file_path)); |
3465 | - |
3466 | - printer.CloseElement(); |
3467 | - printer.CloseElement(); |
3468 | - |
3469 | - append_child(printer, "newCatalogName", ""); |
3470 | - append_child(printer, "parentCatalogID", request_item.folder_id); |
3471 | - printer.CloseElement(); |
3472 | - |
3473 | - return string(printer.CStr()); |
3474 | -} |
3475 | - |
3476 | -static string generate_upload_body(const UploadBufferCb & buffer_cb) { |
3477 | - tinyxml2::XMLPrinter printer; |
3478 | - printer.OpenElement("pcUploadFileRequest"); |
3479 | - append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3480 | - append_child(printer, "fileCount", "1"); |
3481 | - |
3482 | - append_child(printer, "totalSize", std::to_string(buffer_cb.buffer_size).c_str()); |
3483 | - |
3484 | - printer.OpenElement("uploadContentList"); |
3485 | - printer.PushAttribute("length", "1"); |
3486 | - |
3487 | - printer.OpenElement("uploadContentInfo"); |
3488 | - append_child(printer, "contentName", buffer_cb.content_name); |
3489 | - append_child(printer, "contentSize", std::to_string(buffer_cb.buffer_size).c_str()); |
3490 | - append_child(printer, "contentDesc", ""); |
3491 | - append_child(printer, "contentTAGList", ""); |
3492 | - |
3493 | - printer.CloseElement(); |
3494 | - |
3495 | - printer.CloseElement(); |
3496 | - |
3497 | - append_child(printer, "newCatalogName", ""); |
3498 | - append_child(printer, "parentCatalogID", buffer_cb.folder_id); |
3499 | - printer.CloseElement(); |
3500 | - |
3501 | - return string(printer.CStr()); |
3502 | -} |
3503 | - |
3504 | -template<typename T> |
3505 | -static void set_auth_exception(std::shared_ptr<std::promise<T>> prom, |
3506 | - const std::string json_data) { |
3507 | - |
3508 | - std::string error_info = json_data; |
3509 | - boost::cmatch cap; |
3510 | - const boost::regex exp("{\"error\":\"(.*?)\".*"); |
3511 | - if(boost::regex_match(json_data.c_str(), cap, exp)){ |
3512 | - error_info = cap[1]; |
3513 | - } |
3514 | - |
3515 | - prom->set_exception(make_exception_ptr(CredentialException(error_info))); |
3516 | -} |
3517 | - |
3518 | -template<typename T> |
3519 | -static void set_exception(std::shared_ptr<std::promise<T>> prom, |
3520 | - const tinyxml2::XMLElement *root) { |
3521 | - ClientPriv::ServerCode err_code= (ClientPriv::ServerCode)stoi(root->Attribute("resultCode")); |
3522 | - switch(err_code) { |
3523 | - case ClientPriv::ServerCode::CATALOGID_INVALID: |
3524 | - case ClientPriv::ServerCode::CONTENTID_INVALID: |
3525 | - prom->set_exception(make_exception_ptr(InvalidIDException(root->Attribute("desc")))); |
3526 | - break; |
3527 | - case ClientPriv::ServerCode::CATALOG_NOT_EXIST: |
3528 | - case ClientPriv::ServerCode::CONTENT_AND_CATALOG_NOT_EXIST: |
3529 | - case ClientPriv::ServerCode::CONTENT_NOT_EXIST: |
3530 | - prom->set_exception(make_exception_ptr(NonExistentException(root->Attribute("desc")))); |
3531 | - break; |
3532 | - case ClientPriv::ServerCode::USER_SPACE_LACKED: |
3533 | - prom->set_exception(make_exception_ptr(OutofSpaceException(root->Attribute("desc")))); |
3534 | - break; |
3535 | - case ClientPriv::ServerCode::PARAMETER_INVALID: |
3536 | - prom->set_exception(make_exception_ptr(ParameterInvalidException(root->Attribute("desc")))); |
3537 | - break; |
3538 | - case ClientPriv::ServerCode::CREDENTIAL_FAILED: |
3539 | - prom->set_exception(make_exception_ptr(CredentialException(root->Attribute("desc")))); |
3540 | - break; |
3541 | - default: |
3542 | - prom->set_exception(make_exception_ptr(runtime_error(root->Attribute("desc")))); |
3543 | - break; |
3544 | - } |
3545 | -} |
3546 | + return string(printer.CStr()); |
3547 | + } |
3548 | + |
3549 | + static string generate_move_body(const Client::Stringlist& dir_ids, |
3550 | + const Client::Stringlist& content_ids, |
3551 | + const string& folder_id) { |
3552 | + tinyxml2::XMLPrinter printer; |
3553 | + printer.OpenElement("moveContentCatalog"); |
3554 | + |
3555 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3556 | + |
3557 | + printer.OpenElement("contentInfoList"); |
3558 | + printer.PushAttribute("length", std::to_string(content_ids.size()).c_str()); |
3559 | + for (auto& content_id : content_ids) { |
3560 | + append_child(printer, "ID", content_id.c_str()); |
3561 | + } |
3562 | + printer.CloseElement(); |
3563 | + |
3564 | + printer.OpenElement("catalogInfoList"); |
3565 | + printer.PushAttribute("length", std::to_string(dir_ids.size()).c_str()); |
3566 | + for (auto& dir_id : dir_ids) { |
3567 | + append_child(printer, "ID", dir_id.c_str()); |
3568 | + } |
3569 | + printer.CloseElement(); |
3570 | + |
3571 | + append_child(printer, "newCatalogID", folder_id); |
3572 | + |
3573 | + printer.CloseElement(); |
3574 | + |
3575 | + return string(printer.CStr()); |
3576 | + } |
3577 | + |
3578 | + static string generate_extranet_body(const Client::Stringlist& dir_ids, |
3579 | + const Client::Stringlist& content_ids) { |
3580 | + tinyxml2::XMLPrinter printer; |
3581 | + printer.OpenElement("getOutLink"); |
3582 | + printer.OpenElement("getOutLinkReq"); |
3583 | + |
3584 | + append_child(printer, "account", thirdparty_anonymous_account); |
3585 | + printer.OpenElement("caIDLst"); |
3586 | + printer.PushAttribute("length", std::to_string(dir_ids.size()).c_str()); |
3587 | + for (auto& dir_id : dir_ids) { |
3588 | + append_child(printer, "item", dir_id.c_str()); |
3589 | + } |
3590 | + printer.CloseElement(); |
3591 | + |
3592 | + printer.OpenElement("coIDLst"); |
3593 | + printer.PushAttribute("length", std::to_string(content_ids.size()).c_str()); |
3594 | + for (auto& content_id : content_ids) { |
3595 | + append_child(printer, "item", content_id.c_str()); |
3596 | + } |
3597 | + printer.CloseElement(); |
3598 | + |
3599 | + append_child(printer, "pubType", "1"); |
3600 | + |
3601 | + printer.CloseElement(); |
3602 | + printer.CloseElement(); |
3603 | + |
3604 | + return string(printer.CStr()); |
3605 | + } |
3606 | + |
3607 | + static string generate_download_body(const string& content_id) { |
3608 | + tinyxml2::XMLPrinter printer; |
3609 | + printer.OpenElement("downloadRequest"); |
3610 | + append_child(printer, "appName", register_app_name); |
3611 | + append_child(printer, "MSISDN", thirdparty_anonymous_account); |
3612 | + |
3613 | + vector<string> content_ids = {{content_id}}; |
3614 | + string content_list = alg::join(content_ids, "|"); |
3615 | + |
3616 | + append_child(printer, "contentID", content_list.c_str()); |
3617 | + append_child(printer, "OwnerMSISDN", ""); |
3618 | + append_child(printer, "entryShareCatalogID", ""); |
3619 | + append_child(printer, "operation", "0"); |
3620 | + append_child(printer, "fileVersion", "-1"); |
3621 | + |
3622 | + printer.CloseElement(); |
3623 | + |
3624 | + return string(printer.CStr()); |
3625 | + } |
3626 | + |
3627 | + static string generate_upload_body(const UploadRequest& request_item) { |
3628 | + tinyxml2::XMLPrinter printer; |
3629 | + printer.OpenElement("pcUploadFileRequest"); |
3630 | + append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3631 | + append_child(printer, "fileCount", "1"); |
3632 | + |
3633 | + int64_t file_size = 0; |
3634 | + if (fs::exists(request_item.file_path)) { |
3635 | + file_size = fs::file_size(request_item.file_path); |
3636 | + } else { |
3637 | + throw std::runtime_error("file not exists"); |
3638 | + } |
3639 | + append_child(printer, "totalSize", std::to_string(file_size).c_str()); |
3640 | + |
3641 | + printer.OpenElement("uploadContentList"); |
3642 | + printer.PushAttribute("length", "1"); |
3643 | + |
3644 | + printer.OpenElement("uploadContentInfo"); |
3645 | + append_child(printer, "contentName", request_item.content_name.empty() ? |
3646 | + fs::path(request_item.file_path).filename().c_str() : request_item.content_name); |
3647 | + append_child(printer, "contentSize", std::to_string(file_size).c_str()); |
3648 | + append_child(printer, "contentDesc", ""); |
3649 | + append_child(printer, "contentTAGList", ""); |
3650 | + |
3651 | + //The parameter to check upload files' md5sum |
3652 | + //"isNeedupload" field in response body will indicate if the file exists in mcloud. |
3653 | + append_child(printer, "digest", md5sum(request_item.file_path)); |
3654 | + |
3655 | + printer.CloseElement(); |
3656 | + printer.CloseElement(); |
3657 | + |
3658 | + append_child(printer, "newCatalogName", ""); |
3659 | + append_child(printer, "parentCatalogID", request_item.folder_id); |
3660 | + printer.CloseElement(); |
3661 | + |
3662 | + return string(printer.CStr()); |
3663 | + } |
3664 | + |
3665 | + static string generate_upload_body(const UploadBufferCb& buffer_cb) { |
3666 | + tinyxml2::XMLPrinter printer; |
3667 | + printer.OpenElement("pcUploadFileRequest"); |
3668 | + append_child(printer, "ownerMSISDN", thirdparty_anonymous_account); |
3669 | + append_child(printer, "fileCount", "1"); |
3670 | + |
3671 | + append_child(printer, "totalSize", std::to_string(buffer_cb.buffer_size).c_str()); |
3672 | + |
3673 | + printer.OpenElement("uploadContentList"); |
3674 | + printer.PushAttribute("length", "1"); |
3675 | + |
3676 | + printer.OpenElement("uploadContentInfo"); |
3677 | + append_child(printer, "contentName", buffer_cb.content_name); |
3678 | + append_child(printer, "contentSize", std::to_string(buffer_cb.buffer_size).c_str()); |
3679 | + append_child(printer, "contentDesc", ""); |
3680 | + append_child(printer, "contentTAGList", ""); |
3681 | + |
3682 | + printer.CloseElement(); |
3683 | + |
3684 | + printer.CloseElement(); |
3685 | + |
3686 | + append_child(printer, "newCatalogName", ""); |
3687 | + append_child(printer, "parentCatalogID", buffer_cb.folder_id); |
3688 | + printer.CloseElement(); |
3689 | + |
3690 | + return string(printer.CStr()); |
3691 | + } |
3692 | + |
3693 | + template<typename T> |
3694 | + static void set_auth_exception(const shared_ptr<std::promise<T>>& prom, |
3695 | + const string json_data) { |
3696 | + |
3697 | + string error_info = json_data; |
3698 | + boost::cmatch cap; |
3699 | + const boost::regex exp("{\"error\":\"(.*?)\".*"); |
3700 | + if (boost::regex_match(json_data.c_str(), cap, exp)) { |
3701 | + error_info = cap[1]; |
3702 | + } |
3703 | + |
3704 | + prom->set_exception(make_exception_ptr(CredentialException(error_info))); |
3705 | + } |
3706 | + |
3707 | + template<typename T> |
3708 | + static void set_exception(const shared_ptr<std::promise<T>>& prom, |
3709 | + const tinyxml2::XMLElement* root) { |
3710 | + ClientPriv::ServerCode err_code = (ClientPriv::ServerCode)stoi(root->Attribute("resultCode")); |
3711 | + switch (err_code) { |
3712 | + case ClientPriv::ServerCode::CATALOGID_INVALID: |
3713 | + case ClientPriv::ServerCode::CONTENTID_INVALID: |
3714 | + prom->set_exception(make_exception_ptr(InvalidIDException(root->Attribute("desc")))); |
3715 | + break; |
3716 | + case ClientPriv::ServerCode::CATALOG_NOT_EXIST: |
3717 | + case ClientPriv::ServerCode::CONTENT_AND_CATALOG_NOT_EXIST: |
3718 | + case ClientPriv::ServerCode::CONTENT_NOT_EXIST: |
3719 | + prom->set_exception(make_exception_ptr(NonExistentException(root->Attribute("desc")))); |
3720 | + break; |
3721 | + case ClientPriv::ServerCode::USER_SPACE_LACKED: |
3722 | + prom->set_exception(make_exception_ptr(OutofSpaceException(root->Attribute("desc")))); |
3723 | + break; |
3724 | + case ClientPriv::ServerCode::PARAMETER_INVALID: |
3725 | + prom->set_exception(make_exception_ptr(ParameterInvalidException(root->Attribute("desc")))); |
3726 | + break; |
3727 | + case ClientPriv::ServerCode::CREDENTIAL_FAILED: |
3728 | + prom->set_exception(make_exception_ptr(CredentialException(root->Attribute("desc")))); |
3729 | + break; |
3730 | + default: |
3731 | + prom->set_exception(make_exception_ptr(runtime_error(root->Attribute("desc")))); |
3732 | + break; |
3733 | + } |
3734 | + } |
3735 | |
3736 | } |
3737 | |
3738 | class ClientPriv::HttpClient { |
3739 | -public: |
3740 | + public: |
3741 | HttpClient(int request_timeout) : |
3742 | client_(http::make_client()), |
3743 | - worker_ { [this]() {client_->run();} }, |
3744 | - cancelled_(false) { |
3745 | + cancelled_(false), |
3746 | + worker_ {[this]() { |
3747 | + client_->run(); |
3748 | + }} { |
3749 | config_.request_timeout = request_timeout; |
3750 | } |
3751 | |
3752 | @@ -482,9 +483,7 @@ |
3753 | } |
3754 | } |
3755 | |
3756 | - std::shared_ptr<core::net::http::Client> client_; |
3757 | - |
3758 | - std::thread worker_; |
3759 | + std::shared_ptr<http::Client> client_; |
3760 | |
3761 | Config config_; |
3762 | |
3763 | @@ -492,9 +491,11 @@ |
3764 | |
3765 | std::atomic<bool> cancelled_; |
3766 | |
3767 | - void get(const net::Uri::Path &path, |
3768 | - const net::Uri::QueryParameters ¶meters, |
3769 | - http::Request::Handler &handler) { |
3770 | + std::thread worker_; |
3771 | + |
3772 | + void get(const net::Uri::Path& path, |
3773 | + const net::Uri::QueryParameters& parameters, |
3774 | + http::Request::Handler& handler) { |
3775 | auto configuration = net_config(path, parameters); |
3776 | configuration.header.add("User-Agent", config_.user_agent); |
3777 | |
3778 | @@ -502,11 +503,11 @@ |
3779 | request->async_execute(handler); |
3780 | } |
3781 | |
3782 | - void post(const net::Uri::Path &path, |
3783 | - const net::Uri::QueryParameters ¶meters, |
3784 | - const std::string &postbody, |
3785 | - const std::string &content_type, |
3786 | - http::Request::Handler &handler) { |
3787 | + void post(const net::Uri::Path& path, |
3788 | + const net::Uri::QueryParameters& parameters, |
3789 | + const string& postbody, |
3790 | + const string& content_type, |
3791 | + http::Request::Handler& handler) { |
3792 | std::lock_guard<std::mutex> lock(config_mutex_); |
3793 | http::Request::Configuration configuration = net_config(path, parameters); |
3794 | configuration.header.add("User-Agent", config_.user_agent); |
3795 | @@ -517,16 +518,16 @@ |
3796 | request->async_execute(handler); |
3797 | } |
3798 | |
3799 | - http::Request::Configuration net_config(const net::Uri::Path &path, |
3800 | - const net::Uri::QueryParameters ¶meters) { |
3801 | + http::Request::Configuration net_config(const net::Uri::Path& path, |
3802 | + const net::Uri::QueryParameters& parameters) { |
3803 | http::Request::Configuration configuration; |
3804 | net::Uri::QueryParameters complete_parameters(parameters); |
3805 | if (!config_.access_token.empty()) { |
3806 | configuration.header.add("Authorization", |
3807 | - "Bearer " + config_.access_token); |
3808 | + "Bearer " + config_.access_token); |
3809 | } else { |
3810 | configuration.header.add("Authorization", |
3811 | - "Basic " + encode64(config_.client_id + ":" + config_.client_password)); |
3812 | + "Basic " + encode64(config_.client_id + ":" + config_.client_password)); |
3813 | } |
3814 | |
3815 | if (getenv("MCLOUD_LOCAL_SERVER_URL")) { |
3816 | @@ -535,48 +536,42 @@ |
3817 | } |
3818 | |
3819 | net::Uri uri = net::make_uri(config_.apiroot, path, |
3820 | - complete_parameters); |
3821 | + complete_parameters); |
3822 | configuration.uri = client_->uri_to_string(uri); |
3823 | |
3824 | return configuration; |
3825 | } |
3826 | |
3827 | - http::Request::Progress::Next progress_changed( |
3828 | - const http::Request::Progress&) { |
3829 | - return cancelled_ ? |
3830 | - http::Request::Progress::Next::abort_operation : |
3831 | - http::Request::Progress::Next::continue_operation; |
3832 | - } |
3833 | - |
3834 | template<typename T> |
3835 | - future<T> async_get(const net::Uri::Path &path, |
3836 | - const net::Uri::QueryParameters ¶meters, |
3837 | - const function<T(const tinyxml2::XMLElement *root)> &func) { |
3838 | + future<T> async_get(const net::Uri::Path& path, |
3839 | + const net::Uri::QueryParameters& parameters, |
3840 | + const function<T(const tinyxml2::XMLElement* root)>& func) { |
3841 | auto prom = make_shared<promise<T>>(); |
3842 | |
3843 | http::Request::Handler handler; |
3844 | handler.on_progress( |
3845 | - bind(&ClientPriv::HttpClient::progress_changed, this, placeholders::_1)); |
3846 | - handler.on_error([prom](const net::Error& e) |
3847 | - { |
3848 | + [this](const http::Request::Progress& /*progress*/) { |
3849 | + return cancelled_ ? |
3850 | + http::Request::Progress::Next::abort_operation : |
3851 | + http::Request::Progress::Next::continue_operation; |
3852 | + }); |
3853 | + handler.on_error([prom](const net::Error & e) { |
3854 | prom->set_exception(make_exception_ptr(runtime_error(e.what()))); |
3855 | }); |
3856 | handler.on_response( |
3857 | - [prom,func](const http::Response& response) |
3858 | - { |
3859 | - tinyxml2::XMLDocument doc; |
3860 | - tinyxml2::XMLError error = doc.Parse(response.body.c_str()); |
3861 | - const tinyxml2::XMLElement *root = doc.FirstChildElement(); |
3862 | + [prom, func](const http::Response & response) { |
3863 | + tinyxml2::XMLDocument doc; |
3864 | + tinyxml2::XMLError error = doc.Parse(response.body.c_str()); |
3865 | + const tinyxml2::XMLElement* root = doc.FirstChildElement(); |
3866 | |
3867 | - if (error != tinyxml2::XML_SUCCESS) { |
3868 | - prom->set_exception(make_exception_ptr(runtime_error("xml parse failed"))); |
3869 | - } else if (response.status != http::Status::ok) { |
3870 | - prom->set_exception(make_exception_ptr(runtime_error(root->GetText()))); |
3871 | - } else { |
3872 | - prom->set_value(func(root)); |
3873 | - } |
3874 | + if (error != tinyxml2::XML_SUCCESS) { |
3875 | + prom->set_exception(make_exception_ptr(runtime_error("xml parse failed"))); |
3876 | + } else if (response.status != http::Status::ok) { |
3877 | + prom->set_exception(make_exception_ptr(runtime_error(root->GetText()))); |
3878 | + } else { |
3879 | + prom->set_value(func(root)); |
3880 | } |
3881 | - ); |
3882 | + }); |
3883 | |
3884 | get(path, parameters, handler); |
3885 | |
3886 | @@ -584,53 +579,54 @@ |
3887 | } |
3888 | |
3889 | template<typename T> |
3890 | - future<T> async_post(const net::Uri::Path &path, |
3891 | - const net::Uri::QueryParameters ¶meters, |
3892 | - const std::string &postmsg, |
3893 | - const std::string &content_type, |
3894 | - const function<T(const tinyxml2::XMLElement *root)> &func) { |
3895 | + future<T> async_post(const net::Uri::Path& path, |
3896 | + const net::Uri::QueryParameters& parameters, |
3897 | + const string& postmsg, |
3898 | + const string& content_type, |
3899 | + const function<T(const tinyxml2::XMLElement* root)>& func) { |
3900 | auto prom = make_shared<promise<T>>(); |
3901 | |
3902 | http::Request::Handler handler; |
3903 | handler.on_progress( |
3904 | - bind(&ClientPriv::HttpClient::progress_changed, this, placeholders::_1)); |
3905 | - handler.on_error([prom](const net::Error& e) |
3906 | - { |
3907 | + [this](const http::Request::Progress& /*progress*/) { |
3908 | + return cancelled_ ? |
3909 | + http::Request::Progress::Next::abort_operation : |
3910 | + http::Request::Progress::Next::continue_operation; |
3911 | + }); |
3912 | + handler.on_error([prom](const net::Error & e) { |
3913 | prom->set_exception(make_exception_ptr(runtime_error(e.what()))); |
3914 | }); |
3915 | handler.on_response( |
3916 | - [path, prom,func](const http::Response& response) |
3917 | - { |
3918 | - auto iter = std::find_if(path.cbegin(), path.cend(), [=](const string & pathitem){ |
3919 | - return (pathitem == "OAuth2"); |
3920 | - }); |
3921 | - |
3922 | - //mcloud seperate authentication server and content server, |
3923 | - //1.if authentication failed, responses server gives it back are json-based data. |
3924 | - //2.for generaic content access, responses server gives it back are xml-based data, |
3925 | - //just as API document mentioned. |
3926 | - tinyxml2::XMLDocument doc; |
3927 | - tinyxml2::XMLError error = tinyxml2::XML_SUCCESS; |
3928 | - if (iter != path.end()) { |
3929 | - std::string xml_response = "<result resultCode=\"0\"><![CDATA[" + response.body + "]]></result>"; |
3930 | - error = doc.Parse(xml_response.c_str()); |
3931 | - } else { |
3932 | - error = doc.Parse(response.body.c_str()); |
3933 | - } |
3934 | - const tinyxml2::XMLElement *result = doc.FirstChildElement(); |
3935 | - |
3936 | - if (error != tinyxml2::XML_SUCCESS) { |
3937 | - set_auth_exception(prom, response.body); |
3938 | - } else if ((response.status != http::Status::created && |
3939 | - response.status != http::Status::ok && |
3940 | - response.status != http::Status::no_content ) || |
3941 | + [path, prom, func](const http::Response & response) { |
3942 | + auto iter = std::find_if(path.cbegin(), path.cend(), [ = ](const string & pathitem) { |
3943 | + return (pathitem == "OAuth2"); |
3944 | + }); |
3945 | + |
3946 | + //mcloud seperate authentication server and content server, |
3947 | + //1.if authentication failed, responses server gives it back are json-based data. |
3948 | + //2.for generaic content access, responses server gives it back are xml-based data, |
3949 | + //just as API document mentioned. |
3950 | + tinyxml2::XMLDocument doc; |
3951 | + tinyxml2::XMLError error = tinyxml2::XML_SUCCESS; |
3952 | + if (iter != path.end()) { |
3953 | + string xml_response = "<result resultCode=\"0\"><![CDATA[" + response.body + "]]></result>"; |
3954 | + error = doc.Parse(xml_response.c_str()); |
3955 | + } else { |
3956 | + error = doc.Parse(response.body.c_str()); |
3957 | + } |
3958 | + const tinyxml2::XMLElement* result = doc.FirstChildElement(); |
3959 | + |
3960 | + if (error != tinyxml2::XML_SUCCESS) { |
3961 | + set_auth_exception(prom, response.body); |
3962 | + } else if ((response.status != http::Status::created && |
3963 | + response.status != http::Status::ok && |
3964 | + response.status != http::Status::no_content) || |
3965 | strcmp(result->Attribute("resultCode"), "0") != 0) { |
3966 | - set_exception(prom, result); |
3967 | - } else { |
3968 | - prom->set_value(func(result)); |
3969 | - } |
3970 | + set_exception(prom, result); |
3971 | + } else { |
3972 | + prom->set_value(func(result)); |
3973 | } |
3974 | - ); |
3975 | + }); |
3976 | |
3977 | post(path, parameters, postmsg, content_type, handler); |
3978 | |
3979 | @@ -639,8 +635,8 @@ |
3980 | }; |
3981 | |
3982 | ClientPriv::ClientPriv(int request_timeout) |
3983 | - : httpclient_(std::make_shared<HttpClient>(request_timeout)) |
3984 | - , sync_manager_(std::shared_ptr<SyncManager>(new SyncManager(this))) { |
3985 | + : httpclient_(new HttpClient(request_timeout)) |
3986 | + , sync_manager_(new SyncManager(this)) { |
3987 | } |
3988 | |
3989 | ClientPriv::~ClientPriv() { |
3990 | @@ -649,24 +645,25 @@ |
3991 | |
3992 | string ClientPriv::cloud_sync_folder_id() { |
3993 | Client::ResourceList folderlist = cloud_root_folder_list(); |
3994 | - for (auto &folder: folderlist) { |
3995 | - mcloud::api::CloudFolder::Ptr cloudfolder = std::static_pointer_cast<mcloud::api::CloudFolder>(folder); |
3996 | - if (cloudfolder->folder_type() == mcloud::api::CloudFolder::Type::Sync){ |
3997 | + for (auto& folder : folderlist) { |
3998 | + CloudFolder::Ptr cloudfolder = std::static_pointer_cast<CloudFolder>(folder); |
3999 | + if (cloudfolder->folder_type() == CloudFolder::Type::Sync) { |
4000 | return cloudfolder->id(); |
4001 | } |
4002 | } |
4003 | |
4004 | - return std::string(); |
4005 | + return string(); |
4006 | } |
4007 | |
4008 | -void ClientPriv::set_access_token(const string &access_token) { |
4009 | +void ClientPriv::set_access_token(const string& access_token) { |
4010 | httpclient_->config_.access_token = access_token; |
4011 | } |
4012 | |
4013 | -bool ClientPriv::exist_on_cloud(const std::string &file_path, |
4014 | - const std::string &folder_id) { |
4015 | - if (!fs::exists(file_path)) |
4016 | +bool ClientPriv::exist_on_cloud(const string& file_path, |
4017 | + const string& folder_id) { |
4018 | + if (!fs::exists(file_path)) { |
4019 | throw std::runtime_error(string("file not exists: ").append(file_path)); |
4020 | + } |
4021 | |
4022 | UploadRequest request_item{file_path, folder_id, ""}; |
4023 | string postbody = generate_upload_body(request_item); |
4024 | @@ -674,107 +671,105 @@ |
4025 | return exist_on_cloud_internal(postbody); |
4026 | } |
4027 | |
4028 | -DiskInfo ClientPriv::disk_info() { |
4029 | - std::string postbody = generate_diskinfo_body(); |
4030 | +DiskInfo::Ptr ClientPriv::disk_info() { |
4031 | + string postbody = generate_diskinfo_body(); |
4032 | |
4033 | log(postbody); |
4034 | |
4035 | - auto disk_future = httpclient_->async_post<DiskInfo>( |
4036 | + auto disk_future = httpclient_->async_post<DiskInfo::Ptr>( |
4037 | { "richlifeApp", "devapp", "IUser" }, { }, postbody, content_type, |
4038 | - [](const tinyxml2::XMLElement *root) { |
4039 | - return DiskInfo(root); |
4040 | + [](const tinyxml2::XMLElement * root) { |
4041 | + return std::shared_ptr<DiskInfo>(new DiskInfo(root)); |
4042 | }); |
4043 | |
4044 | return get_or_throw(disk_future); |
4045 | } |
4046 | |
4047 | Client::ResourceList ClientPriv::cloud_content_list(int start_index, |
4048 | - int count, |
4049 | - CloudContent::Type type, |
4050 | - const std::string & folder_id) { |
4051 | - std::string postbody = generate_content_list_body(start_index, |
4052 | - count, |
4053 | - type, |
4054 | - folder_id); |
4055 | + int count, |
4056 | + CloudContent::Type type, |
4057 | + const string& folder_id) { |
4058 | + string postbody = generate_contents_body(start_index, |
4059 | + count, |
4060 | + type, |
4061 | + folder_id); |
4062 | return cloud_content_list_internal(postbody); |
4063 | } |
4064 | |
4065 | -CloudContent::Ptr ClientPriv::content_info(const string &content_id) { |
4066 | +CloudContent::Ptr ClientPriv::content_info(const string& content_id) { |
4067 | string postbody = generate_content_body(content_id); |
4068 | return content_item_internal(postbody); |
4069 | } |
4070 | |
4071 | -CloudFolder::Ptr ClientPriv::create_folder(const string &folder_name, |
4072 | - const string &folder_id) { |
4073 | +CloudFolder::Ptr ClientPriv::create_folder(const string& folder_name, |
4074 | + const string& folder_id) { |
4075 | string postbody = generate_create_folder_body(folder_name, folder_id); |
4076 | return create_folder_internal(postbody); |
4077 | } |
4078 | |
4079 | -Client::ResourceList ClientPriv::look_up(const string &name, |
4080 | - const string &folder_id, |
4081 | +Client::ResourceList ClientPriv::look_up(const string& name, |
4082 | + const string& folder_id, |
4083 | CloudResource::Property property) { |
4084 | string postbody = generate_look_up_body(name, folder_id, property); |
4085 | return look_up_internal(postbody); |
4086 | } |
4087 | |
4088 | -bool ClientPriv::move_items(const Client::Stringlist &folder_ids, |
4089 | - const Client::Stringlist &content_ids, |
4090 | - const std::string &folder_id) { |
4091 | +bool ClientPriv::move_items(const Client::Stringlist& folder_ids, |
4092 | + const Client::Stringlist& content_ids, |
4093 | + const string& folder_id) { |
4094 | string postbody = generate_move_body(folder_ids, content_ids, |
4095 | folder_id); |
4096 | return move_items_internal(postbody); |
4097 | } |
4098 | |
4099 | -bool ClientPriv::update_folder(const string &folder_id, |
4100 | - const string &new_folder_name) { |
4101 | +bool ClientPriv::update_folder(const string& folder_id, |
4102 | + const string& new_folder_name) { |
4103 | string postbody = generate_update_folder_body(folder_id, new_folder_name); |
4104 | return update_internal(postbody); |
4105 | } |
4106 | |
4107 | -bool ClientPriv::delete_contents(const Client::Stringlist &content_ids) { |
4108 | +bool ClientPriv::delete_contents(const Client::Stringlist& content_ids) { |
4109 | string postbody = generate_delete_body(content_ids); |
4110 | return delete_internal(postbody); |
4111 | } |
4112 | |
4113 | -Client::Stringlist ClientPriv::copy_folders(const Client::Stringlist &folder_ids, |
4114 | - const std::string &folder_id) { |
4115 | - string postbody = generate_copy_body(folder_ids, vector<string>{}, |
4116 | - folder_id); |
4117 | - return copy_internal(postbody); |
4118 | -} |
4119 | - |
4120 | -Client::Stringlist ClientPriv::copy_contents(const Client::Stringlist &content_ids, |
4121 | - const std::string &folder_id) { |
4122 | - string postbody = generate_copy_body(vector<string>{}, content_ids, |
4123 | - folder_id); |
4124 | - return copy_internal(postbody); |
4125 | -} |
4126 | - |
4127 | -Client::OutlinkList ClientPriv::create_folder_extranet_link( |
4128 | - const Client::Stringlist &folder_ids) { |
4129 | +Client::Stringlist ClientPriv::copy_folders(const Client::Stringlist& folder_ids, |
4130 | + const string& folder_id) { |
4131 | + string postbody = generate_copy_body(folder_ids, vector<string> {}, |
4132 | + folder_id); |
4133 | + return copy_internal(postbody); |
4134 | +} |
4135 | + |
4136 | +Client::Stringlist ClientPriv::copy_contents(const Client::Stringlist& content_ids, |
4137 | + const string& folder_id) { |
4138 | + string postbody = generate_copy_body(Client::Stringlist{}, content_ids, |
4139 | + folder_id); |
4140 | + return copy_internal(postbody); |
4141 | +} |
4142 | + |
4143 | +Client::OutlinkList ClientPriv::create_folder_sharing_url(const Client::Stringlist& folder_ids) { |
4144 | string postbody = generate_extranet_body(folder_ids, Client::Stringlist{}); |
4145 | - return create_extranet_internal(postbody); |
4146 | + return create_url_internal(postbody); |
4147 | } |
4148 | |
4149 | -Client::OutlinkList ClientPriv::create_content_extranet_link( |
4150 | - const Client::Stringlist &content_ids) { |
4151 | +Client::OutlinkList ClientPriv::create_content_sharing_url(const Client::Stringlist& content_ids) { |
4152 | string postbody = generate_extranet_body(Client::Stringlist{}, content_ids); |
4153 | - return create_extranet_internal(postbody); |
4154 | + return create_url_internal(postbody); |
4155 | } |
4156 | |
4157 | -DownloadTaskPriv::Ptr ClientPriv::create_download_link(const string &content_id) { |
4158 | +DownloadTaskPriv::Ptr ClientPriv::create_download_link(const string& content_id) { |
4159 | string postbody = generate_download_body({{content_id}}); |
4160 | |
4161 | log(postbody); |
4162 | |
4163 | auto future = httpclient_->async_post<DownloadTaskPriv::Ptr>( |
4164 | - { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4165 | - [](const tinyxml2::XMLElement *root) { |
4166 | + { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4167 | + [](const tinyxml2::XMLElement * root) { |
4168 | |
4169 | auto link_list = root->FirstChildElement("String"); |
4170 | if (link_list) { |
4171 | auto link = link_list->FirstChildElement(); |
4172 | - while(link) { |
4173 | + while (link) { |
4174 | return std::make_shared<DownloadTaskPriv>(link); |
4175 | } |
4176 | |
4177 | @@ -788,19 +783,19 @@ |
4178 | return get_or_throw(future); |
4179 | } |
4180 | |
4181 | -DownloadTaskPriv::Ptr ClientPriv::create_download_link(const DownloadBufferCb &buffer_cb) { |
4182 | +DownloadTaskPriv::Ptr ClientPriv::create_download_link(const DownloadBufferCb& buffer_cb) { |
4183 | string postbody = generate_download_body(buffer_cb.content_id); |
4184 | |
4185 | log(postbody); |
4186 | |
4187 | auto future = httpclient_->async_post<DownloadTaskPriv::Ptr>( |
4188 | - { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4189 | - [buffer_cb](const tinyxml2::XMLElement *root) { |
4190 | + { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4191 | + [buffer_cb](const tinyxml2::XMLElement * root) { |
4192 | |
4193 | auto link_list = root->FirstChildElement("String"); |
4194 | if (link_list) { |
4195 | auto link = link_list->FirstChildElement(); |
4196 | - while(link) { |
4197 | + while (link) { |
4198 | return std::make_shared<DownloadTaskPriv>(link, buffer_cb.write_cb); |
4199 | } |
4200 | |
4201 | @@ -814,20 +809,21 @@ |
4202 | return get_or_throw(future); |
4203 | } |
4204 | |
4205 | -UploadTaskPriv::Ptr ClientPriv::create_upload_link(const UploadRequest &request_item) { |
4206 | - if (!fs::exists(request_item.file_path)) |
4207 | +UploadTaskPriv::Ptr ClientPriv::create_upload_link(const UploadRequest& request_item) { |
4208 | + if (!fs::exists(request_item.file_path)) { |
4209 | throw std::runtime_error(string("file not exists: ").append(request_item.file_path)); |
4210 | - |
4211 | + } |
4212 | + |
4213 | string postbody = generate_upload_body(request_item); |
4214 | |
4215 | log(postbody); |
4216 | |
4217 | auto future = httpclient_->async_post<UploadTaskPriv::Ptr>( |
4218 | - { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4219 | - [request_item](const tinyxml2::XMLElement *root) { |
4220 | + { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4221 | + [request_item](const tinyxml2::XMLElement * root) { |
4222 | auto upload_res = root->FirstChildElement("uploadResult"); |
4223 | - std::string task_id = upload_res->FirstChildElement("uploadTaskID")->GetText(); |
4224 | - std::string redirection_url; |
4225 | + string task_id = upload_res->FirstChildElement("uploadTaskID")->GetText(); |
4226 | + string redirection_url; |
4227 | if (upload_res->FirstChildElement("redirectionUrl")) { |
4228 | redirection_url = upload_res->FirstChildElement("redirectionUrl")->GetText(); |
4229 | } |
4230 | @@ -835,7 +831,7 @@ |
4231 | auto content_list = upload_res->FirstChildElement("newContentIDList"); |
4232 | if (content_list) { |
4233 | auto content = content_list->FirstChildElement(); |
4234 | - while(content) { |
4235 | + while (content) { |
4236 | return std::make_shared<UploadTaskPriv>(content, |
4237 | task_id, |
4238 | redirection_url, |
4239 | @@ -849,20 +845,20 @@ |
4240 | return get_or_throw(future); |
4241 | } |
4242 | |
4243 | -UploadTaskPriv::Ptr ClientPriv::create_upload_link(const UploadBufferCb &buffer_cb) { |
4244 | +UploadTaskPriv::Ptr ClientPriv::create_upload_link(const UploadBufferCb& buffer_cb) { |
4245 | string postbody = generate_upload_body(buffer_cb); |
4246 | |
4247 | log(postbody); |
4248 | |
4249 | auto future = httpclient_->async_post<UploadTaskPriv::Ptr>( |
4250 | - { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4251 | - [buffer_cb](const tinyxml2::XMLElement *root) { |
4252 | + { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4253 | + [buffer_cb](const tinyxml2::XMLElement * root) { |
4254 | SyncManager::UploadList results; |
4255 | |
4256 | auto upload_res = root->FirstChildElement("uploadResult"); |
4257 | - std::string task_id = upload_res->FirstChildElement("uploadTaskID")->GetText(); |
4258 | + string task_id = upload_res->FirstChildElement("uploadTaskID")->GetText(); |
4259 | |
4260 | - std::string redirection_url; |
4261 | + string redirection_url; |
4262 | if (upload_res->FirstChildElement("redirectionUrl")) { |
4263 | redirection_url = upload_res->FirstChildElement("redirectionUrl")->GetText(); |
4264 | } |
4265 | @@ -870,12 +866,12 @@ |
4266 | auto content_list = upload_res->FirstChildElement("newContentIDList"); |
4267 | if (content_list) { |
4268 | auto content = content_list->FirstChildElement(); |
4269 | - while(content) { |
4270 | + while (content) { |
4271 | return std::make_shared<UploadTaskPriv>(content, |
4272 | - task_id, |
4273 | - redirection_url, |
4274 | - buffer_cb.buffer_size, |
4275 | - buffer_cb.read_cb); |
4276 | + task_id, |
4277 | + redirection_url, |
4278 | + buffer_cb.buffer_size, |
4279 | + buffer_cb.read_cb); |
4280 | } |
4281 | } |
4282 | |
4283 | @@ -886,20 +882,20 @@ |
4284 | } |
4285 | |
4286 | Client::ResourceList ClientPriv::cloud_root_folder_list() { |
4287 | - std::string postbody = generate_content_list_body(); |
4288 | + string postbody = generate_contents_body(); |
4289 | |
4290 | log(postbody); |
4291 | |
4292 | auto future = httpclient_->async_post<Client::ResourceList>( |
4293 | - { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4294 | - [](const tinyxml2::XMLElement *res) { |
4295 | + { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4296 | + [](const tinyxml2::XMLElement * res) { |
4297 | auto root = res->FirstChildElement(); |
4298 | Client::ResourceList results; |
4299 | |
4300 | auto folder_list = root->FirstChildElement("catalogList"); |
4301 | if (folder_list) { |
4302 | auto folder = folder_list->FirstChildElement(); |
4303 | - while(folder) { |
4304 | + while (folder) { |
4305 | results.emplace_back(std::shared_ptr<CloudFolder>(new CloudFolder(folder))); |
4306 | folder = folder->NextSiblingElement(); |
4307 | } |
4308 | @@ -911,19 +907,19 @@ |
4309 | return get_or_throw(future); |
4310 | } |
4311 | |
4312 | -Client::ResourceList ClientPriv::cloud_content_list_internal(const string &postbody) { |
4313 | +Client::ResourceList ClientPriv::cloud_content_list_internal(const string& postbody) { |
4314 | log(postbody); |
4315 | |
4316 | auto future = httpclient_->async_post<Client::ResourceList>( |
4317 | - { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4318 | - [](const tinyxml2::XMLElement *root) { |
4319 | + { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4320 | + [](const tinyxml2::XMLElement * root) -> Client::ResourceList { |
4321 | Client::ResourceList results; |
4322 | |
4323 | auto res = root->FirstChildElement(); |
4324 | auto folder_list = res->FirstChildElement("catalogList"); |
4325 | if (folder_list) { |
4326 | auto folder_ele = folder_list->FirstChildElement(); |
4327 | - while(folder_ele) { |
4328 | + while (folder_ele) { |
4329 | results.emplace_back(std::shared_ptr<CloudFolder>( |
4330 | new CloudFolder(folder_ele))); |
4331 | folder_ele = folder_ele->NextSiblingElement(); |
4332 | @@ -933,9 +929,8 @@ |
4333 | auto content_list = res->FirstChildElement("contentList"); |
4334 | if (content_list) { |
4335 | auto content = content_list->FirstChildElement(); |
4336 | - while(content) { |
4337 | - results.emplace_back(std::shared_ptr<CloudContent>( |
4338 | - new CloudContent(content))); |
4339 | + while (content) { |
4340 | + results.emplace_back(std::shared_ptr<CloudContent>(new CloudContent(content))); |
4341 | content = content->NextSiblingElement(); |
4342 | } |
4343 | } |
4344 | @@ -946,12 +941,12 @@ |
4345 | return get_or_throw(future); |
4346 | } |
4347 | |
4348 | -CloudContent::Ptr ClientPriv::content_item_internal(const string &postbody) { |
4349 | +CloudContent::Ptr ClientPriv::content_item_internal(const string& postbody) { |
4350 | log(postbody); |
4351 | |
4352 | auto future = httpclient_->async_post<CloudContent::Ptr>( |
4353 | - { "richlifeApp", "devapp", "IContent" }, { }, postbody, content_type, |
4354 | - [](const tinyxml2::XMLElement *root) -> CloudContent::Ptr { |
4355 | + { "richlifeApp", "devapp", "IContent" }, { }, postbody, content_type, |
4356 | + [](const tinyxml2::XMLElement * root) -> CloudContent::Ptr { |
4357 | if (strcmp(root->Attribute("resultCode"), "0")) |
4358 | return nullptr; |
4359 | |
4360 | @@ -962,12 +957,12 @@ |
4361 | return get_or_throw(future); |
4362 | } |
4363 | |
4364 | -CloudFolder::Ptr ClientPriv::create_folder_internal(const string &postbody) { |
4365 | +CloudFolder::Ptr ClientPriv::create_folder_internal(const string& postbody) { |
4366 | log(postbody); |
4367 | |
4368 | auto future = httpclient_->async_post<CloudFolder::Ptr>( |
4369 | - { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4370 | - [](const tinyxml2::XMLElement *root) -> CloudFolder::Ptr { |
4371 | + { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4372 | + [](const tinyxml2::XMLElement * root) -> CloudFolder::Ptr { |
4373 | if (strcmp(root->Attribute("resultCode"), "0")) |
4374 | return nullptr; |
4375 | |
4376 | @@ -978,19 +973,19 @@ |
4377 | return get_or_throw(future); |
4378 | } |
4379 | |
4380 | -Client::ResourceList ClientPriv::look_up_internal(const string &postbody) { |
4381 | +Client::ResourceList ClientPriv::look_up_internal(const string& postbody) { |
4382 | log(postbody); |
4383 | |
4384 | auto future = httpclient_->async_post<Client::ResourceList>( |
4385 | - { "richlifeApp", "devapp", "ISearch" }, { }, postbody, content_type, |
4386 | - [](const tinyxml2::XMLElement *root) { |
4387 | + { "richlifeApp", "devapp", "ISearch" }, { }, postbody, content_type, |
4388 | + [](const tinyxml2::XMLElement * root) -> Client::ResourceList { |
4389 | Client::ResourceList results; |
4390 | |
4391 | auto res = root->FirstChildElement(); |
4392 | auto folder_list = res->FirstChildElement("srchCtlgList"); |
4393 | if (folder_list) { |
4394 | auto folder_ele = folder_list->FirstChildElement(); |
4395 | - while(folder_ele) { |
4396 | + while (folder_ele) { |
4397 | results.emplace_back(std::shared_ptr<CloudFolder>( |
4398 | new CloudFolder(folder_ele))); |
4399 | folder_ele = folder_ele->NextSiblingElement(); |
4400 | @@ -1000,9 +995,8 @@ |
4401 | auto content_list = res->FirstChildElement("srchCntList"); |
4402 | if (content_list) { |
4403 | auto content_ele = content_list->FirstChildElement(); |
4404 | - while(content_ele) { |
4405 | - results.emplace_back(std::shared_ptr<CloudContent>( |
4406 | - new CloudContent(content_ele))); |
4407 | + while (content_ele) { |
4408 | + results.emplace_back(std::shared_ptr<CloudContent>(new CloudContent(content_ele))); |
4409 | content_ele = content_ele->NextSiblingElement(); |
4410 | } |
4411 | } |
4412 | @@ -1013,19 +1007,19 @@ |
4413 | return get_or_throw(future); |
4414 | } |
4415 | |
4416 | -bool ClientPriv::exist_on_cloud_internal(const string &postbody) { |
4417 | +bool ClientPriv::exist_on_cloud_internal(const string& postbody) { |
4418 | log(postbody); |
4419 | |
4420 | auto future = httpclient_->async_post<bool>( |
4421 | - { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4422 | - [](const tinyxml2::XMLElement *root) { |
4423 | + { "richlifeApp", "devapp", "IUploadAndDownload" }, { }, postbody, content_type, |
4424 | + [](const tinyxml2::XMLElement * root) { |
4425 | bool is_exists = false; |
4426 | |
4427 | auto upload_ele = root->FirstChildElement("uploadResult"); |
4428 | auto new_content_list = upload_ele->FirstChildElement("newContentIDList"); |
4429 | if (new_content_list) { |
4430 | auto new_content_ele = new_content_list->FirstChildElement(); |
4431 | - if(new_content_ele) { |
4432 | + if (new_content_ele) { |
4433 | is_exists = strcmp(new_content_ele->FirstChildElement("isNeedUpload")->GetText(), "1"); |
4434 | } |
4435 | } |
4436 | @@ -1036,43 +1030,44 @@ |
4437 | return get_or_throw(future); |
4438 | } |
4439 | |
4440 | -bool ClientPriv::move_items_internal(const string &postbody) { |
4441 | +bool ClientPriv::move_items_internal(const string& postbody) { |
4442 | return update_internal(postbody); |
4443 | } |
4444 | |
4445 | -bool ClientPriv::update_internal(const string &postbody) { |
4446 | - log(postbody); |
4447 | - |
4448 | - auto future = httpclient_->async_post<bool>( |
4449 | - { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4450 | - [](const tinyxml2::XMLElement *root) { |
4451 | - return !strcmp(root->Attribute("resultCode"), "0"); |
4452 | - }); |
4453 | - |
4454 | - return get_or_throw(future); |
4455 | -} |
4456 | - |
4457 | -bool ClientPriv::delete_internal(const string &postbody) { |
4458 | - log(postbody); |
4459 | - |
4460 | - auto future = httpclient_->async_post<bool>( |
4461 | - { "richlifeApp", "devapp", "IContent" }, { }, postbody, content_type, |
4462 | - [](const tinyxml2::XMLElement *root) { |
4463 | - return !strcmp(root->Attribute("resultCode"), "0"); |
4464 | - }); |
4465 | - |
4466 | - return get_or_throw(future); |
4467 | -} |
4468 | - |
4469 | -Client::Stringlist ClientPriv::copy_internal(const string &postbody) { |
4470 | +bool ClientPriv::update_internal(const string& postbody) { |
4471 | + log(postbody); |
4472 | + |
4473 | + auto future = httpclient_->async_post<bool>( |
4474 | + { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4475 | + [](const tinyxml2::XMLElement * root) { |
4476 | + return !strcmp(root->Attribute("resultCode"), "0"); |
4477 | + }); |
4478 | + |
4479 | + return get_or_throw(future); |
4480 | +} |
4481 | + |
4482 | +bool ClientPriv::delete_internal(const string& postbody) { |
4483 | + log(postbody); |
4484 | + |
4485 | + auto future = httpclient_->async_post<bool>( |
4486 | + { "richlifeApp", "devapp", "IContent" }, { }, postbody, content_type, |
4487 | + [](const tinyxml2::XMLElement * root) { |
4488 | + return !strcmp(root->Attribute("resultCode"), "0"); |
4489 | + }); |
4490 | + |
4491 | + return get_or_throw(future); |
4492 | +} |
4493 | + |
4494 | +Client::Stringlist ClientPriv::copy_internal(const string& postbody) { |
4495 | log(postbody); |
4496 | |
4497 | auto future = httpclient_->async_post<Client::Stringlist>( |
4498 | - { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4499 | - [](const tinyxml2::XMLElement *root) { |
4500 | + { "richlifeApp", "devapp", "ICatalog" }, { }, postbody, content_type, |
4501 | + [](const tinyxml2::XMLElement * root) -> Client::Stringlist { |
4502 | Client::Stringlist results; |
4503 | - if (strcmp(root->Attribute("resultCode"), "0")) |
4504 | + if (strcmp(root->Attribute("resultCode"), "0")) { |
4505 | return results; |
4506 | + } |
4507 | |
4508 | auto new_item = root->FirstChildElement("array")->FirstChildElement("item"); |
4509 | while (new_item) { |
4510 | @@ -1086,18 +1081,18 @@ |
4511 | return get_or_throw(future); |
4512 | } |
4513 | |
4514 | -Client::OutlinkList ClientPriv::create_extranet_internal(const string &postbody) { |
4515 | +Client::OutlinkList ClientPriv::create_url_internal(const string& postbody) { |
4516 | log(postbody); |
4517 | |
4518 | auto future = httpclient_->async_post<Client::OutlinkList>( |
4519 | - { "richlifeApp", "devapp", "IOutLink" }, { }, postbody, content_type, |
4520 | - [](const tinyxml2::XMLElement *root) { |
4521 | + { "richlifeApp", "devapp", "IOutLink" }, { }, postbody, content_type, |
4522 | + [](const tinyxml2::XMLElement * root) { |
4523 | Client::OutlinkList results; |
4524 | |
4525 | auto link_list = root->FirstChildElement("getOutLinkRes")->FirstChildElement("getOutLinkResSet"); |
4526 | if (link_list) { |
4527 | auto link = link_list->FirstChildElement(); |
4528 | - while(link) { |
4529 | + while (link) { |
4530 | results.emplace_back(new Outlink(link)); |
4531 | link = link->NextSiblingElement(); |
4532 | } |
4533 | @@ -1109,15 +1104,15 @@ |
4534 | return get_or_throw(future); |
4535 | } |
4536 | |
4537 | -bool ClientPriv::refersh_token(const string &refresh_token) { |
4538 | - const std::string content_type = "application/x-www-form-urlencoded"; |
4539 | - const std::string postbody = "grant_type=refresh_token&refresh_token=" |
4540 | - + refresh_token; |
4541 | +bool ClientPriv::refersh_token(const string& refresh_token) { |
4542 | + const string content_type = "application/x-www-form-urlencoded"; |
4543 | + const string postbody = "grant_type=refresh_token&refresh_token=" |
4544 | + + refresh_token; |
4545 | log(postbody); |
4546 | |
4547 | auto future = httpclient_->async_post<bool>( |
4548 | - { "oauthApp", "OAuth2", "refreshToken" }, { }, postbody, content_type, |
4549 | - [this](const tinyxml2::XMLElement *root) { |
4550 | + { "oauthApp", "OAuth2", "refreshToken" }, { }, postbody, content_type, |
4551 | + [this](const tinyxml2::XMLElement * root) { |
4552 | boost::cmatch cap; |
4553 | const boost::regex exp(".*\"(.*?)\"\\}"); |
4554 | if (boost::regex_match(root->GetText(), cap, exp)) { |
4555 | @@ -1130,16 +1125,17 @@ |
4556 | return get_or_throw(future); |
4557 | } |
4558 | |
4559 | -void ClientPriv::cancel() { |
4560 | - httpclient_->cancelled_ = true; |
4561 | -} |
4562 | - |
4563 | SyncManager::Ptr ClientPriv::sync_manager() { |
4564 | return sync_manager_; |
4565 | } |
4566 | |
4567 | -template<typename T> T ClientPriv::get_or_throw(std::future<T> &f) { |
4568 | - if (f.wait_for(std::chrono::seconds(httpclient_->config_.request_timeout)) != std::future_status::ready) { |
4569 | +void ClientPriv::cancel() { |
4570 | + httpclient_->cancelled_ = true; |
4571 | +} |
4572 | + |
4573 | +template<typename T> T ClientPriv::get_or_throw(std::future<T>& f) { |
4574 | + if (f.wait_for(std::chrono::seconds(httpclient_->config_.request_timeout)) != |
4575 | + std::future_status::ready) { |
4576 | throw HttpTimeoutException("HTTP request timeout"); |
4577 | } |
4578 | |
4579 | |
4580 | === modified file 'src/mcloud/api/client_priv.h' |
4581 | --- src/mcloud/api/client_priv.h 2016-09-26 01:43:23 +0000 |
4582 | +++ src/mcloud/api/client_priv.h 2016-10-26 10:36:06 +0000 |
4583 | @@ -53,94 +53,94 @@ |
4584 | |
4585 | virtual ~ClientPriv(); |
4586 | |
4587 | - DiskInfo disk_info(); |
4588 | + DiskInfo::Ptr disk_info(); |
4589 | |
4590 | std::string cloud_sync_folder_id(); |
4591 | |
4592 | - void set_access_token(const std::string &access_token); |
4593 | - |
4594 | - CloudContent::Ptr content_info(const std::string &content_id); |
4595 | - |
4596 | - CloudFolder::Ptr create_folder(const std::string &folder_name, |
4597 | - const std::string &folder_id); |
4598 | - |
4599 | - Client::ResourceList look_up(const std::string &name, |
4600 | - const std::string &folder_id, |
4601 | + void set_access_token(const std::string& access_token); |
4602 | + |
4603 | + CloudContent::Ptr content_info(const std::string& content_id); |
4604 | + |
4605 | + CloudFolder::Ptr create_folder(const std::string& folder_name, |
4606 | + const std::string& folder_id); |
4607 | + |
4608 | + Client::ResourceList look_up(const std::string& name, |
4609 | + const std::string& folder_id, |
4610 | CloudResource::Property property = CloudResource::Property::Content); |
4611 | |
4612 | - bool refersh_token(const std::string &refresh_token); |
4613 | - |
4614 | - bool move_items(const Client::Stringlist &folder_ids, |
4615 | - const Client::Stringlist &content_ids, |
4616 | - const std::string &folder_id); |
4617 | - |
4618 | - bool exist_on_cloud(const std::string &file_path, const std::string &folder_id); |
4619 | - |
4620 | - bool update_folder(const std::string &folder_id, |
4621 | - const std::string &new_name); |
4622 | - |
4623 | - bool delete_contents(const Client::Stringlist &content_ids); |
4624 | - |
4625 | - Client::Stringlist copy_folders(const Client::Stringlist &folder_ids, |
4626 | - const std::string &folder_id); |
4627 | - |
4628 | - Client::Stringlist copy_contents(const Client::Stringlist &content_ids, |
4629 | - const std::string &folder_id); |
4630 | + bool refersh_token(const std::string& refresh_token); |
4631 | + |
4632 | + bool move_items(const Client::Stringlist& folder_ids, |
4633 | + const Client::Stringlist& content_ids, |
4634 | + const std::string& folder_id); |
4635 | + |
4636 | + bool exist_on_cloud(const std::string& file_path, const std::string& folder_id); |
4637 | + |
4638 | + bool update_folder(const std::string& folder_id, |
4639 | + const std::string& new_name); |
4640 | + |
4641 | + bool delete_contents(const Client::Stringlist& content_ids); |
4642 | + |
4643 | + Client::Stringlist copy_folders(const Client::Stringlist& folder_ids, |
4644 | + const std::string& folder_id); |
4645 | + |
4646 | + Client::Stringlist copy_contents(const Client::Stringlist& content_ids, |
4647 | + const std::string& folder_id); |
4648 | |
4649 | Client::ResourceList cloud_content_list(int start_index, |
4650 | int count, |
4651 | CloudContent::Type content_type = CloudContent::Type::All, |
4652 | - const std::string &folder_id = std::string()); |
4653 | - |
4654 | - Client::OutlinkList create_folder_extranet_link(const Client::Stringlist &folder_ids); |
4655 | - |
4656 | - Client::OutlinkList create_content_extranet_link(const Client::Stringlist &content_ids); |
4657 | - |
4658 | - DownloadTaskPriv::Ptr create_download_link(const std::string &content_id); |
4659 | - |
4660 | - DownloadTaskPriv::Ptr create_download_link(const DownloadBufferCb &buffer_cb); |
4661 | + const std::string& folder_id = std::string()); |
4662 | + |
4663 | + Client::OutlinkList create_folder_sharing_url(const Client::Stringlist& folder_ids); |
4664 | + |
4665 | + Client::OutlinkList create_content_sharing_url(const Client::Stringlist& content_ids); |
4666 | + |
4667 | + DownloadTaskPriv::Ptr create_download_link(const std::string& content_id); |
4668 | + |
4669 | + DownloadTaskPriv::Ptr create_download_link(const DownloadBufferCb& buffer_cb); |
4670 | |
4671 | //Same name files in different directories are not allowed to upload to mcloud because of file names conflicts. |
4672 | - UploadTaskPriv::Ptr create_upload_link(const UploadRequest &reqeust_item); |
4673 | + UploadTaskPriv::Ptr create_upload_link(const UploadRequest& reqeust_item); |
4674 | |
4675 | - UploadTaskPriv::Ptr create_upload_link(const UploadBufferCb &buffer_cb); |
4676 | + UploadTaskPriv::Ptr create_upload_link(const UploadBufferCb& buffer_cb); |
4677 | |
4678 | void cancel(); |
4679 | |
4680 | - std::shared_ptr<SyncManager> sync_manager(); |
4681 | + SyncManager::Ptr sync_manager(); |
4682 | |
4683 | private: |
4684 | Client::ResourceList cloud_root_folder_list(); |
4685 | |
4686 | - Client::ResourceList cloud_content_list_internal(const std::string &postbody); |
4687 | - |
4688 | - CloudContent::Ptr content_item_internal(const std::string &postbody); |
4689 | - |
4690 | - CloudFolder::Ptr create_folder_internal(const std::string &postbody); |
4691 | - |
4692 | - Client::ResourceList look_up_internal(const std::string &postbody); |
4693 | - |
4694 | - bool exist_on_cloud_internal(const std::string &postbody); |
4695 | - |
4696 | - bool move_items_internal(const std::string &postbody); |
4697 | - |
4698 | - bool update_internal(const std::string &postbody); |
4699 | - |
4700 | - bool delete_internal(const std::string &postbody); |
4701 | - |
4702 | - Client::Stringlist copy_internal(const std::string &postbody); |
4703 | - |
4704 | - Client::OutlinkList create_extranet_internal(const std::string &postbody); |
4705 | - |
4706 | - template<typename T> T get_or_throw(std::future<T> &f); |
4707 | + Client::ResourceList cloud_content_list_internal(const std::string& postbody); |
4708 | + |
4709 | + CloudContent::Ptr content_item_internal(const std::string& postbody); |
4710 | + |
4711 | + CloudFolder::Ptr create_folder_internal(const std::string& postbody); |
4712 | + |
4713 | + Client::ResourceList look_up_internal(const std::string& postbody); |
4714 | + |
4715 | + bool exist_on_cloud_internal(const std::string& postbody); |
4716 | + |
4717 | + bool move_items_internal(const std::string& postbody); |
4718 | + |
4719 | + bool update_internal(const std::string& postbody); |
4720 | + |
4721 | + bool delete_internal(const std::string& postbody); |
4722 | + |
4723 | + Client::Stringlist copy_internal(const std::string& postbody); |
4724 | + |
4725 | + Client::OutlinkList create_url_internal(const std::string& postbody); |
4726 | + |
4727 | + template<typename T> T get_or_throw(std::future<T>& f); |
4728 | |
4729 | private: |
4730 | |
4731 | class HttpClient; |
4732 | |
4733 | - std::shared_ptr<HttpClient> httpclient_; |
4734 | + std::unique_ptr<HttpClient> httpclient_; |
4735 | |
4736 | - std::shared_ptr<SyncManager> sync_manager_; |
4737 | + SyncManager::Ptr sync_manager_; |
4738 | }; |
4739 | |
4740 | } |
4741 | |
4742 | === modified file 'src/mcloud/api/cloudcontent.cpp' |
4743 | --- src/mcloud/api/cloudcontent.cpp 2016-09-26 01:43:23 +0000 |
4744 | +++ src/mcloud/api/cloudcontent.cpp 2016-10-26 10:36:06 +0000 |
4745 | @@ -23,12 +23,12 @@ |
4746 | using namespace mcloud::api; |
4747 | using namespace std; |
4748 | |
4749 | -extern std::time_t string_to_time(const std::string dt); |
4750 | +extern time_t string_to_time(const string& dt); |
4751 | |
4752 | class CloudContent::Priv { |
4753 | -public: |
4754 | - Priv(const tinyxml2::XMLElement *root) { |
4755 | - name_= root->FirstChildElement("contentName")->GetText(); |
4756 | + public: |
4757 | + Priv(const tinyxml2::XMLElement* root) { |
4758 | + name_ = root->FirstChildElement("contentName")->GetText(); |
4759 | id_ = root->FirstChildElement("contentID")->GetText(); |
4760 | created_date_ = string_to_time(root->FirstChildElement("uploadTime")->GetText()); |
4761 | updated_date_ = string_to_time(root->FirstChildElement("updateTime")->GetText()); |
4762 | @@ -67,69 +67,72 @@ |
4763 | etag_ = etag_ele->GetText(); |
4764 | } |
4765 | |
4766 | - #ifndef NDEBUG |
4767 | - cout << "id: "<< id_ << " name: " << name_ << " etag: "<< etag_ << endl; |
4768 | - #endif |
4769 | +#ifndef NDEBUG |
4770 | + cout << "id: " << id_ << " name: " << name_ << " etag: " << etag_ << endl; |
4771 | +#endif |
4772 | } |
4773 | |
4774 | - std::string id_; |
4775 | - |
4776 | - std::string name_; |
4777 | - |
4778 | - std::time_t created_date_; |
4779 | - |
4780 | - std::time_t updated_date_; |
4781 | - |
4782 | - std::string etag_; |
4783 | - |
4784 | - std::string owner_; |
4785 | - |
4786 | - std::string suffix_; |
4787 | - |
4788 | - CloudContent::Type type_; |
4789 | - |
4790 | - int64_t content_size_; |
4791 | - |
4792 | - std::string description_; |
4793 | - |
4794 | - std::string thumbnail_url_; |
4795 | - |
4796 | - std::string big_thumbnail_url_; |
4797 | - |
4798 | - std::string present_url_; |
4799 | - |
4800 | - std::string parent_catalog_id_; |
4801 | + string id_; |
4802 | + |
4803 | + string name_; |
4804 | + |
4805 | + time_t created_date_; |
4806 | + |
4807 | + time_t updated_date_; |
4808 | + |
4809 | + string etag_; |
4810 | + |
4811 | + string owner_; |
4812 | + |
4813 | + string suffix_; |
4814 | + |
4815 | + CloudContent::Type type_; |
4816 | + |
4817 | + int64_t content_size_; |
4818 | + |
4819 | + string description_; |
4820 | + |
4821 | + string thumbnail_url_; |
4822 | + |
4823 | + string big_thumbnail_url_; |
4824 | + |
4825 | + string present_url_; |
4826 | + |
4827 | + string parent_catalog_id_; |
4828 | }; |
4829 | |
4830 | -CloudContent::CloudContent(const tinyxml2::XMLElement *root) |
4831 | - : p(std::make_shared<Priv>(root)){ |
4832 | -} |
4833 | - |
4834 | -const string &CloudContent::id() const { |
4835 | +CloudContent::CloudContent(const tinyxml2::XMLElement* root) |
4836 | + : p(new Priv(root)) { |
4837 | +} |
4838 | + |
4839 | +CloudContent::~CloudContent() { |
4840 | +} |
4841 | + |
4842 | +const string& CloudContent::id() const { |
4843 | return p->id_; |
4844 | } |
4845 | |
4846 | -const string &CloudContent::name() const { |
4847 | +const string& CloudContent::name() const { |
4848 | return p->name_; |
4849 | } |
4850 | |
4851 | -const time_t &CloudContent::created_date() const { |
4852 | +const time_t& CloudContent::created_date() const { |
4853 | return p->created_date_; |
4854 | } |
4855 | |
4856 | -const time_t &CloudContent::updated_date() const { |
4857 | +const time_t& CloudContent::updated_date() const { |
4858 | return p->updated_date_; |
4859 | } |
4860 | |
4861 | -const string &CloudContent::parent_catalog_id() const { |
4862 | +const string& CloudContent::parent_catalog_id() const { |
4863 | return p->parent_catalog_id_; |
4864 | } |
4865 | |
4866 | -const string &CloudContent::etag() const { |
4867 | +const string& CloudContent::etag() const { |
4868 | return p->etag_; |
4869 | } |
4870 | |
4871 | -const string &CloudContent::owner() const { |
4872 | +const string& CloudContent::owner() const { |
4873 | return p->owner_; |
4874 | } |
4875 | |
4876 | @@ -137,7 +140,7 @@ |
4877 | return CloudResource::Property::Content; |
4878 | } |
4879 | |
4880 | -const string &CloudContent::suffix() const { |
4881 | +const string& CloudContent::suffix() const { |
4882 | return p->suffix_; |
4883 | } |
4884 | |
4885 | @@ -149,18 +152,18 @@ |
4886 | return p->content_size_; |
4887 | } |
4888 | |
4889 | -const string &CloudContent::description() const { |
4890 | +const string& CloudContent::description() const { |
4891 | return p->description_; |
4892 | } |
4893 | |
4894 | -const string &CloudContent::thumbnail_url() const { |
4895 | +const string& CloudContent::thumbnail_url() const { |
4896 | return p->thumbnail_url_; |
4897 | } |
4898 | |
4899 | -const string &CloudContent::big_thumbnail_url() const { |
4900 | +const string& CloudContent::big_thumbnail_url() const { |
4901 | return p->big_thumbnail_url_; |
4902 | } |
4903 | |
4904 | -const string &CloudContent::present_url() const { |
4905 | +const string& CloudContent::present_url() const { |
4906 | return p->present_url_; |
4907 | } |
4908 | |
4909 | === modified file 'src/mcloud/api/cloudfolder.cpp' |
4910 | --- src/mcloud/api/cloudfolder.cpp 2016-09-26 01:43:23 +0000 |
4911 | +++ src/mcloud/api/cloudfolder.cpp 2016-10-26 10:36:06 +0000 |
4912 | @@ -27,17 +27,17 @@ |
4913 | using namespace mcloud::api; |
4914 | using namespace std; |
4915 | |
4916 | -std::time_t string_to_time(const std::string dt) { |
4917 | - struct std::tm tm; |
4918 | - std::istringstream ss(dt); |
4919 | - strptime(dt.c_str(), "%Y%m%d%H%M%S",&tm); // std::get std::put only available in GCC 5 |
4920 | - return std::mktime(&tm); |
4921 | +time_t string_to_time(const string& dt) { |
4922 | + struct tm tm; |
4923 | + istringstream ss(dt); |
4924 | + strptime(dt.c_str(), "%Y%m%d%H%M%S", &tm); // get put only available in GCC 5 |
4925 | + return mktime(&tm); |
4926 | } |
4927 | |
4928 | class CloudFolder::Priv { |
4929 | -public: |
4930 | - Priv(const tinyxml2::XMLElement *root) { |
4931 | - name_= root->FirstChildElement("catalogName")->GetText(); |
4932 | + public: |
4933 | + Priv(const tinyxml2::XMLElement* root) { |
4934 | + name_ = root->FirstChildElement("catalogName")->GetText(); |
4935 | id_ = root->FirstChildElement("catalogID")->GetText(); |
4936 | created_date_ = string_to_time(root->FirstChildElement("createTime")->GetText()); |
4937 | update_date_ = string_to_time(root->FirstChildElement("updateTime")->GetText()); |
4938 | @@ -72,64 +72,67 @@ |
4939 | folder_type_ = (Type)atoi(root->FirstChildElement("catalogType")->GetText()); |
4940 | |
4941 | |
4942 | - #ifndef NDEBUG |
4943 | - cout << "id: "<< id_ << " name: " << name_ << " etag: "<< etag_ << endl; |
4944 | - #endif |
4945 | +#ifndef NDEBUG |
4946 | + cout << "id: " << id_ << " name: " << name_ << " etag: " << etag_ << endl; |
4947 | +#endif |
4948 | |
4949 | } |
4950 | |
4951 | - std::string id_; |
4952 | - |
4953 | - std::string name_; |
4954 | - |
4955 | - std::time_t created_date_; |
4956 | - |
4957 | - std::time_t update_date_; |
4958 | - |
4959 | - std::string parent_catalog_id_; |
4960 | - |
4961 | - std::string etag_; |
4962 | - |
4963 | - std::string owner_; |
4964 | + string id_; |
4965 | + |
4966 | + string name_; |
4967 | + |
4968 | + time_t created_date_; |
4969 | + |
4970 | + time_t update_date_; |
4971 | + |
4972 | + string parent_catalog_id_; |
4973 | + |
4974 | + string etag_; |
4975 | + |
4976 | + string owner_; |
4977 | |
4978 | CloudFolder::Type folder_type_; |
4979 | |
4980 | - std::string folder_path_; |
4981 | + string folder_path_; |
4982 | }; |
4983 | |
4984 | -CloudFolder::CloudFolder(const tinyxml2::XMLElement *root) |
4985 | - :p_(std::make_shared<Priv>(root)){ |
4986 | -} |
4987 | - |
4988 | -const string &CloudFolder::id() const { |
4989 | +CloudFolder::CloudFolder(const tinyxml2::XMLElement* root) |
4990 | + : p_(new Priv(root)) { |
4991 | +} |
4992 | + |
4993 | +CloudFolder::~CloudFolder() { |
4994 | +} |
4995 | + |
4996 | +const string& CloudFolder::id() const { |
4997 | return p_->id_; |
4998 | } |
4999 | |
5000 | -const string &CloudFolder::name() const { |
PASSED: Continuous integration, rev:54 /jenkins. canonical. com/unity- api-1/job/ lp-mcloud- ci/26/ /jenkins. canonical. com/unity- api-1/job/ build/886 /jenkins. canonical. com/unity- api-1/job/ build-0- fetch/893 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=amd64, release= vivid+overlay/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=amd64, release= vivid+overlay/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=amd64, release= xenial+ overlay/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=amd64, release= xenial+ overlay/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=amd64, release= yakkety/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=amd64, release= yakkety/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=armhf, release= vivid+overlay/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=armhf, release= vivid+overlay/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=armhf, release= xenial+ overlay/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=armhf, release= xenial+ overlay/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=armhf, release= yakkety/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=armhf, release= yakkety/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=i386, release= vivid+overlay/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=i386, release= vivid+overlay/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=i386, release= xenial+ overlay/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=i386, release= xenial+ overlay/ 699/artifact/ output/ *zip*/output. zip /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=i386, release= yakkety/ 699 /jenkins. canonical. com/unity- api-1/job/ build-2- binpkg/ arch=i386, release= yakkety/ 699/artifact/ output/ *zip*/output. zip
https:/
Executed test runs:
SUCCESS: https:/
SUCCESS: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
SUCCESS: https:/
deb: https:/
Click here to trigger a rebuild: /jenkins. canonical. com/unity- api-1/job/ lp-mcloud- ci/26/rebuild
https:/