1 | /* |
2 | Copyright (c) 2007 Tobias Koenig <tokoe@kde.org> |
3 | |
4 | This library is free software; you can redistribute it and/or modify it |
5 | under the terms of the GNU Library General Public License as published by |
6 | the Free Software Foundation; either version 2 of the License, or (at your |
7 | option) any later version. |
8 | |
9 | This library is distributed in the hope that it will be useful, but WITHOUT |
10 | ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
11 | FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public |
12 | License for more details. |
13 | |
14 | You should have received a copy of the GNU Library General Public License |
15 | along with this library; see the file COPYING.LIB. If not, write to the |
16 | Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA |
17 | 02110-1301, USA. |
18 | */ |
19 | |
20 | #ifndef AKONADI_ITEMSYNC_H |
21 | #define AKONADI_ITEMSYNC_H |
22 | |
23 | #include "akonadi_export.h" |
24 | |
25 | #include <akonadi/item.h> |
26 | #include <akonadi/job.h> |
27 | |
28 | namespace Akonadi { |
29 | |
30 | class Collection; |
31 | class ItemFetchScope; |
32 | class ItemSyncPrivate; |
33 | |
34 | /** |
35 | * @short Syncs between items known to a client (usually a resource) and the Akonadi storage. |
36 | * |
37 | * Remote Id must only be set by the resource storing the item, other clients |
38 | * should leave it empty, since the resource responsible for the target collection |
39 | * will be notified about the addition and then create a suitable remote Id. |
40 | * |
41 | * There are two different forms of ItemSync usage: |
42 | * - Full-Sync: meaning the client provides all valid items, i.e. any item not |
43 | * part of the list but currently stored in Akonadi will be removed |
44 | * - Incremental-Sync: meaning the client provides two lists, one for items which |
45 | * are new or modified and one for items which should be removed. Any item not |
46 | * part of either list but currently stored in Akonadi will not be changed. |
47 | * |
48 | * @note This is provided for convenience to implement "save all" like behavior, |
49 | * however it is strongly recommended to use single item jobs whenever |
50 | * possible, e.g. ItemCreateJob, ItemModifyJob and ItemDeleteJob |
51 | * |
52 | * @author Tobias Koenig <tokoe@kde.org> |
53 | */ |
54 | class AKONADI_EXPORT ItemSync : public Job |
55 | { |
56 | Q_OBJECT |
57 | |
58 | public: |
59 | /** |
60 | * Creates a new item synchronizer. |
61 | * |
62 | * @param collection The collection we are syncing. |
63 | * @param parent The parent object. |
64 | */ |
65 | explicit ItemSync(const Collection &collection, QObject *parent = 0); |
66 | |
67 | /** |
68 | * Destroys the item synchronizer. |
69 | */ |
70 | ~ItemSync(); |
71 | |
72 | /** |
73 | * Sets the full item list for the collection. |
74 | * |
75 | * Usually the result of a full item listing. |
76 | * |
77 | * @warning If the client using this is a resource, all items must have |
78 | * a valid remote identifier. |
79 | * |
80 | * @param items A list of items. |
81 | */ |
82 | void setFullSyncItems(const Item::List &items); |
83 | |
84 | /** |
85 | * Set the amount of items which you are going to return in total |
86 | * by using the setFullSyncItems()/setIncrementalSyncItems() methods. |
87 | * |
88 | * @warning By default the item sync will automatically end once |
89 | * sufficient items have been provided. |
90 | * To disable this use setDisableAutomaticDeliveryDone |
91 | * |
92 | * @see setDisableAutomaticDeliveryDone |
93 | * @param amount The amount of items in total. |
94 | */ |
95 | void setTotalItems(int amount); |
96 | |
97 | /** |
98 | Enable item streaming. Item streaming means that the items delivered by setXItems() calls |
99 | are delivered in chunks and you manually indicate when all items have been delivered |
100 | by calling deliveryDone(). |
101 | @param enable @c true to enable item streaming |
102 | */ |
103 | void setStreamingEnabled(bool enable); |
104 | |
105 | /** |
106 | Notify ItemSync that all remote items have been delivered. |
107 | Only call this in streaming mode. |
108 | */ |
109 | void deliveryDone(); |
110 | |
111 | /** |
112 | * Sets the item lists for incrementally syncing the collection. |
113 | * |
114 | * Usually the result of an incremental remote item listing. |
115 | * |
116 | * @warning If the client using this is a resource, all items must have |
117 | * a valid remote identifier. |
118 | * |
119 | * @param changedItems A list of items added or changed by the client. |
120 | * @param removedItems A list of items deleted by the client. |
121 | */ |
122 | void setIncrementalSyncItems(const Item::List &changedItems, |
123 | const Item::List &removedItems); |
124 | |
125 | /** |
126 | * Sets the item fetch scope. |
127 | * |
128 | * The ItemFetchScope controls how much of an item's data is fetched |
129 | * from the server, e.g. whether to fetch the full item payload or |
130 | * only meta data. |
131 | * |
132 | * @param fetchScope The new scope for item fetch operations. |
133 | * |
134 | * @see fetchScope() |
135 | */ |
136 | void setFetchScope(ItemFetchScope &fetchScope); |
137 | |
138 | /** |
139 | * Returns the item fetch scope. |
140 | * |
141 | * Since this returns a reference it can be used to conveniently modify the |
142 | * current scope in-place, i.e. by calling a method on the returned reference |
143 | * without storing it in a local variable. See the ItemFetchScope documentation |
144 | * for an example. |
145 | * |
146 | * @return a reference to the current item fetch scope |
147 | * |
148 | * @see setFetchScope() for replacing the current item fetch scope |
149 | */ |
150 | ItemFetchScope &fetchScope(); |
151 | |
152 | /** |
153 | * Aborts the sync process and rolls back all not yet committed transactions. |
154 | * Use this if an external error occurred during the sync process (such as the |
155 | * user canceling it). |
156 | * @since 4.5 |
157 | */ |
158 | void rollback(); |
159 | |
160 | /** |
161 | * Transaction mode used by ItemSync. |
162 | * @since 4.6 |
163 | */ |
164 | enum TransactionMode { |
165 | SingleTransaction, ///< Use a single transaction for the entire sync process (default), provides maximum consistency ("all or nothing") and best performance |
166 | MultipleTransactions, ///< Use one transaction per chunk of delivered items, good compromise between the other two when using streaming |
167 | NoTransaction ///< Use no transaction at all, provides highest responsiveness (might therefore feel faster even when actually taking slightly longer), no consistency guaranteed (can fail anywhere in the sync process) |
168 | }; |
169 | |
170 | /** |
171 | * Set the transaction mode to use for this sync. |
172 | * @note You must call this method before starting the sync, changes afterwards lead to undefined results. |
173 | * @param mode the transaction mode to use |
174 | * @since 4.6 |
175 | */ |
176 | void setTransactionMode(TransactionMode mode); |
177 | |
178 | /** |
179 | * Minimum number of items required to start processing in streaming mode. |
180 | * When MultipleTransactions is used, one transaction per batch will be created. |
181 | * |
182 | * @see setBatchSize() |
183 | * @since 4.14 |
184 | */ |
185 | int batchSize() const; |
186 | |
187 | /** |
188 | * Set the batch size. |
189 | * |
190 | * The default is 10. |
191 | * |
192 | * @note You must call this method before starting the sync, changes afterwards lead to undefined results. |
193 | * @see batchSize() |
194 | * @since 4.14 |
195 | */ |
196 | void setBatchSize(int); |
197 | |
198 | /** |
199 | * Disables the automatic completion of the item sync, |
200 | * based on the number of delivered items. |
201 | * |
202 | * This ensures that the item sync only finishes once deliveryDone() |
203 | * is called, while still making it possible to use the progress |
204 | * reporting of the ItemSync. |
205 | * |
206 | * @note You must call this method before starting the sync, changes afterwards lead to undefined results. |
207 | * @see setTotalItems |
208 | * @since 4.14 |
209 | */ |
210 | void setDisableAutomaticDeliveryDone(bool disable); |
211 | |
212 | Q_SIGNALS: |
213 | /** |
214 | * Signals the resource that new items can be delivered. |
215 | * @param remainingBatchSize the number of items required to complete the batch (typically the same as batchSize()) |
216 | * |
217 | * @since 4.14 |
218 | */ |
219 | void readyForNextBatch(int remainingBatchSize); |
220 | |
221 | /** |
222 | * @internal |
223 | * Emitted whenever a transaction is committed. This is for testing only. |
224 | * |
225 | * @since 4.14 |
226 | */ |
227 | void transactionCommitted(); |
228 | |
229 | protected: |
230 | void doStart(); |
231 | void slotResult(KJob *job); |
232 | |
233 | /** |
234 | * Reimplement this method to customize the synchronization algorithm. |
235 | * @param storedItem the item as it is now |
236 | * @param newItem the item as it should be |
237 | * You can update the @p newItem according to the @p storedItem before |
238 | * it gets committed. |
239 | * |
240 | * @deprecated This method is disabled internally. |
241 | */ |
242 | AKONADI_DEPRECATED virtual bool updateItem(const Item &storedItem, Item &newItem); |
243 | |
244 | private: |
245 | //@cond PRIVATE |
246 | Q_DECLARE_PRIVATE(ItemSync) |
247 | ItemSyncPrivate *dummy; // for BC. KF5 TODO: REMOVE. |
248 | |
249 | Q_PRIVATE_SLOT(d_func(), void slotLocalListDone(KJob *)) |
250 | Q_PRIVATE_SLOT(d_func(), void slotLocalDeleteDone(KJob *)) |
251 | Q_PRIVATE_SLOT(d_func(), void slotLocalChangeDone(KJob *)) |
252 | Q_PRIVATE_SLOT(d_func(), void slotTransactionResult(KJob *)) |
253 | Q_PRIVATE_SLOT(d_func(), void slotItemsReceived(const Akonadi::Item::List &)) |
254 | //@endcond |
255 | }; |
256 | |
257 | } |
258 | |
259 | #endif |
260 | |