Changeset View
Changeset View
Standalone View
Standalone View
examples/webdavcommon/webdav.cpp
Show First 20 Lines • Show All 57 Lines • ▼ Show 20 Line(s) | 57 | } else { | |||
---|---|---|---|---|---|
58 | future.setFinished(); | 58 | future.setFinished(); | ||
59 | } | 59 | } | ||
60 | }); | 60 | }); | ||
61 | SinkTrace() << "Starting job: " << job->metaObject()->className(); | 61 | SinkTrace() << "Starting job: " << job->metaObject()->className(); | ||
62 | job->start(); | 62 | job->start(); | ||
63 | }); | 63 | }); | ||
64 | } | 64 | } | ||
65 | 65 | | |||
66 | template <typename T> | ||||
67 | static KAsync::Job<T> runJob(KJob *job, const std::function<T(KJob *)> &func) | ||||
68 | { | ||||
69 | return KAsync::start<T>([job, func](KAsync::Future<T> &future) { | ||||
70 | QObject::connect(job, &KJob::result, [&future, func](KJob *job) { | ||||
71 | SinkTrace() << "Job done: " << job->metaObject()->className(); | ||||
72 | if (job->error()) { | ||||
73 | SinkWarning() << "Job failed: " << job->errorString() << job->metaObject()->className() << job->error(); | ||||
74 | auto proxyError = translateDavError(job); | ||||
75 | future.setError(proxyError, job->errorString()); | ||||
76 | } else { | ||||
77 | future.setValue(func(job)); | ||||
78 | future.setFinished(); | ||||
79 | } | ||||
80 | }); | ||||
81 | SinkTrace() << "Starting job: " << job->metaObject()->className(); | ||||
82 | job->start(); | ||||
83 | }); | ||||
84 | } | ||||
85 | | ||||
66 | WebDavSynchronizer::WebDavSynchronizer(const Sink::ResourceContext &context, | 86 | WebDavSynchronizer::WebDavSynchronizer(const Sink::ResourceContext &context, | ||
67 | KDAV2::Protocol protocol, QByteArray collectionName, QByteArray itemName) | 87 | KDAV2::Protocol protocol, QByteArray collectionName, QByteArray itemName) | ||
68 | : Sink::Synchronizer(context), | 88 | : Sink::Synchronizer(context), | ||
69 | protocol(protocol), | 89 | protocol(protocol), | ||
70 | collectionName(std::move(collectionName)), | 90 | collectionName(std::move(collectionName)), | ||
71 | itemName(std::move(itemName)) | 91 | itemName(std::move(itemName)) | ||
72 | { | 92 | { | ||
73 | auto config = ResourceConfig::getConfiguration(context.instanceId()); | 93 | auto config = ResourceConfig::getConfiguration(context.instanceId()); | ||
Show All 21 Lines | |||||
95 | KAsync::Job<void> WebDavSynchronizer::synchronizeWithSource(const Sink::QueryBase &query) | 115 | KAsync::Job<void> WebDavSynchronizer::synchronizeWithSource(const Sink::QueryBase &query) | ||
96 | { | 116 | { | ||
97 | if (query.type() != collectionName && query.type() != itemName) { | 117 | if (query.type() != collectionName && query.type() != itemName) { | ||
98 | return KAsync::null<void>(); | 118 | return KAsync::null<void>(); | ||
99 | } | 119 | } | ||
100 | 120 | | |||
101 | SinkLog() << "Synchronizing" << query.type() << "through WebDAV at:" << serverUrl().url(); | 121 | SinkLog() << "Synchronizing" << query.type() << "through WebDAV at:" << serverUrl().url(); | ||
102 | 122 | | |||
103 | auto collectionsFetchJob = new KDAV2::DavCollectionsFetchJob{serverUrl()}; | 123 | auto collectionsFetchJob = new KDAV2::DavCollectionsFetchJob{ serverUrl() }; | ||
104 | auto job = runJob(collectionsFetchJob).then([this, collectionsFetchJob](const KAsync::Error &error) { | 124 | auto job = runJob<KDAV2::DavCollection::List>(collectionsFetchJob, | ||
cmollekopf: The idea is not to replace the continuation, but just to have a result extractor. Normally this… | |||||
105 | if (error) { | 125 | [](KJob *job) { return static_cast<KDAV2::DavCollectionsFetchJob *>(job)->collections(); }) | ||
106 | SinkWarning() << "Failed to synchronize collections:" << error; | 126 | .then([this](const KDAV2::DavCollection::List &collections) { | ||
107 | } else { | 127 | updateLocalCollections(collections); | ||
108 | updateLocalCollections(collectionsFetchJob->collections()); | 128 | return collections; | ||
109 | } | | |||
110 | | ||||
111 | return collectionsFetchJob->collections(); | | |||
112 | }); | 129 | }); | ||
113 | 130 | | |||
114 | if (query.type() == collectionName) { | 131 | if (query.type() == collectionName) { | ||
115 | // Do nothing more | 132 | // Do nothing more | ||
116 | return job; | 133 | return job; | ||
117 | } else if (query.type() == itemName) { | 134 | } else if (query.type() == itemName) { | ||
118 | auto progress = QSharedPointer<int>::create(0); | 135 | auto progress = QSharedPointer<int>::create(0); | ||
119 | auto total = QSharedPointer<int>::create(0); | 136 | auto total = QSharedPointer<int>::create(0); | ||
▲ Show 20 Lines • Show All 42 Lines • ▼ Show 20 Line(s) | 177 | { | |||
162 | auto ctag = collection.CTag().toLatin1(); | 179 | auto ctag = collection.CTag().toLatin1(); | ||
163 | 180 | | |||
164 | auto localRid = collectionLocalResourceID(collection); | 181 | auto localRid = collectionLocalResourceID(collection); | ||
165 | 182 | | |||
166 | // The ETag cache is useless here, since `sinkStore()` IS the cache. | 183 | // The ETag cache is useless here, since `sinkStore()` IS the cache. | ||
167 | auto cache = std::make_shared<KDAV2::EtagCache>(); | 184 | auto cache = std::make_shared<KDAV2::EtagCache>(); | ||
168 | auto davItemsListJob = new KDAV2::DavItemsListJob(collection.url(), std::move(cache)); | 185 | auto davItemsListJob = new KDAV2::DavItemsListJob(collection.url(), std::move(cache)); | ||
169 | 186 | | |||
170 | return runJob(davItemsListJob) | 187 | return runJob<KDAV2::DavItem::List>(davItemsListJob, | ||
171 | .then([this, davItemsListJob, total] { | 188 | [](KJob *job) { return static_cast<KDAV2::DavItemsListJob *>(job)->items(); }) | ||
172 | auto items = davItemsListJob->items(); | 189 | .then([this, total](const KDAV2::DavItem::List &items) { | ||
173 | *total += items.size(); | 190 | *total += items.size(); | ||
174 | return KAsync::value(items); | 191 | return items; | ||
175 | }) | 192 | }) | ||
176 | .serialEach([this, collectionRid, localRid, progress(std::move(progress)), total(std::move(total)), | 193 | .serialEach([this, collectionRid, localRid, progress(std::move(progress)), total(std::move(total)), | ||
177 | itemsResourceIDs(std::move(itemsResourceIDs))](const KDAV2::DavItem &item) { | 194 | itemsResourceIDs(std::move(itemsResourceIDs))](const KDAV2::DavItem &item) { | ||
178 | auto itemRid = resourceID(item); | 195 | auto itemRid = resourceID(item); | ||
179 | 196 | | |||
180 | itemsResourceIDs->insert(itemRid); | 197 | itemsResourceIDs->insert(itemRid); | ||
181 | 198 | | |||
182 | if (unchanged(item)) { | 199 | if (unchanged(item)) { | ||
Show All 11 Lines | |||||
194 | } | 211 | } | ||
195 | 212 | | |||
196 | KAsync::Job<void> WebDavSynchronizer::synchronizeItem(const KDAV2::DavItem &item, | 213 | KAsync::Job<void> WebDavSynchronizer::synchronizeItem(const KDAV2::DavItem &item, | ||
197 | const QByteArray &collectionLocalRid, QSharedPointer<int> progress, QSharedPointer<int> total) | 214 | const QByteArray &collectionLocalRid, QSharedPointer<int> progress, QSharedPointer<int> total) | ||
198 | { | 215 | { | ||
199 | auto etag = item.etag().toLatin1(); | 216 | auto etag = item.etag().toLatin1(); | ||
200 | 217 | | |||
201 | auto itemFetchJob = new KDAV2::DavItemFetchJob(item); | 218 | auto itemFetchJob = new KDAV2::DavItemFetchJob(item); | ||
202 | return runJob(itemFetchJob) | 219 | return runJob<KDAV2::DavItem>( | ||
203 | .then([this, itemFetchJob(std::move(itemFetchJob)), collectionLocalRid] { | 220 | itemFetchJob, [](KJob *job) { return static_cast<KDAV2::DavItemFetchJob *>(job)->item(); }) | ||
204 | auto item = itemFetchJob->item(); | 221 | .then([this, collectionLocalRid](const KDAV2::DavItem &item) { | ||
If you are sure of what you're getting, and in this case you are, you can replace the dynamic_cast with a static_cast. cmollekopf: If you are sure of what you're getting, and in this case you are, you can replace the… | |||||
205 | updateLocalItem(item, collectionLocalRid); | 222 | updateLocalItem(item, collectionLocalRid); | ||
206 | return item; | 223 | return item; | ||
207 | }) | 224 | }) | ||
208 | .then([this, etag, progress(std::move(progress)), total(std::move(total))](const KDAV2::DavItem &item) { | 225 | .then([this, etag, progress(std::move(progress)), total(std::move(total))](const KDAV2::DavItem &item) { | ||
209 | // Update the local ETag to be able to tell if the item is unchanged | 226 | // Update the local ETag to be able to tell if the item is unchanged | ||
210 | syncStore().writeValue(resourceID(item) + "_etag", etag); | 227 | syncStore().writeValue(resourceID(item) + "_etag", etag); | ||
211 | 228 | | |||
212 | *progress += 1; | 229 | *progress += 1; | ||
▲ Show 20 Lines • Show All 41 Lines • Show Last 20 Lines |
The idea is not to replace the continuation, but just to have a result extractor. Normally this extractor should not capture anything.
In this case you definitely need the continuation because otherwise you can't do the error handling properly.