OLD | NEW |
| (Empty) |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #ifndef COMPONENTS_SYNC_API_ATTACHMENTS_ATTACHMENT_STORE_H_ | |
6 #define COMPONENTS_SYNC_API_ATTACHMENTS_ATTACHMENT_STORE_H_ | |
7 | |
8 #include <memory> | |
9 | |
10 #include "base/callback.h" | |
11 #include "base/macros.h" | |
12 #include "base/memory/ref_counted.h" | |
13 #include "components/sync/api/attachments/attachment.h" | |
14 #include "components/sync/api/attachments/attachment_id.h" | |
15 #include "components/sync/api/attachments/attachment_metadata.h" | |
16 | |
17 namespace base { | |
18 class FilePath; | |
19 class SequencedTaskRunner; | |
20 } // namespace base | |
21 | |
22 namespace syncer { | |
23 | |
24 class AttachmentStoreBackend; | |
25 class AttachmentStoreForSync; | |
26 class AttachmentStoreFrontend; | |
27 | |
28 // AttachmentStore is a place to locally store and access Attachments. | |
29 // | |
30 // AttachmentStore class is an interface exposed to data type and | |
31 // AttachmentService code. | |
32 // It also contains factory methods for default attachment store | |
33 // implementations. | |
34 // Destroying this object does not necessarily cancel outstanding async | |
35 // operations. If you need cancel like semantics, use WeakPtr in the callbacks. | |
36 class AttachmentStore { | |
37 public: | |
38 // TODO(maniscalco): Consider udpating Read and Write methods to support | |
39 // resumable transfers (bug 353292). | |
40 | |
41 // The result status of an attachment store operation. | |
42 // Do not re-order or delete these entries; they are used in a UMA histogram. | |
43 enum Result { | |
44 SUCCESS = 0, // No error, all completed successfully. | |
45 UNSPECIFIED_ERROR = 1, // An unspecified error occurred for >= 1 item. | |
46 STORE_INITIALIZATION_FAILED = 2, // AttachmentStore initialization failed. | |
47 // When adding a value here, you must increment RESULT_SIZE below. | |
48 }; | |
49 static const int RESULT_SIZE = | |
50 10; // Size of the Result enum; used for histograms. | |
51 | |
52 // Each attachment can have references from sync or model type. Tracking these | |
53 // references is needed for lifetime management of attachment, it can only be | |
54 // deleted from the store when it doesn't have references. | |
55 enum Component { | |
56 MODEL_TYPE, | |
57 SYNC, | |
58 }; | |
59 | |
60 typedef base::Callback<void(const Result&)> InitCallback; | |
61 typedef base::Callback<void(const Result&, | |
62 std::unique_ptr<AttachmentMap>, | |
63 std::unique_ptr<AttachmentIdList>)> | |
64 ReadCallback; | |
65 typedef base::Callback<void(const Result&)> WriteCallback; | |
66 typedef base::Callback<void(const Result&)> DropCallback; | |
67 typedef base::Callback<void(const Result&, | |
68 std::unique_ptr<AttachmentMetadataList>)> | |
69 ReadMetadataCallback; | |
70 | |
71 ~AttachmentStore(); | |
72 | |
73 // Asynchronously reads the attachments identified by |ids|. | |
74 // | |
75 // |callback| will be invoked when finished. AttachmentStore will attempt to | |
76 // read all attachments specified in ids. If any of the attachments do not | |
77 // exist or could not be read, |callback|'s Result will be UNSPECIFIED_ERROR. | |
78 // Callback's AttachmentMap will contain all attachments that were | |
79 // successfully read, AttachmentIdList will contain attachment ids of | |
80 // attachments that are unavailable in attachment store, these need to be | |
81 // downloaded from server. | |
82 // | |
83 // Reads on individual attachments are treated atomically; |callback| will not | |
84 // read only part of an attachment. | |
85 void Read(const AttachmentIdList& ids, const ReadCallback& callback); | |
86 | |
87 // Asynchronously writes |attachments| to the store. | |
88 // | |
89 // Will not overwrite stored attachments. Attempting to overwrite an | |
90 // attachment that already exists is not an error. | |
91 // | |
92 // |callback| will be invoked when finished. If any of the attachments could | |
93 // not be written |callback|'s Result will be UNSPECIFIED_ERROR. When this | |
94 // happens, some or none of the attachments may have been written | |
95 // successfully. | |
96 void Write(const AttachmentList& attachments, const WriteCallback& callback); | |
97 | |
98 // Asynchronously drops |attchments| from this store. | |
99 // | |
100 // This does not remove attachments from the server. | |
101 // | |
102 // |callback| will be invoked when finished. Attempting to drop an attachment | |
103 // that does not exist is not an error. If any of the existing attachment | |
104 // could not be dropped, |callback|'s Result will be UNSPECIFIED_ERROR. When | |
105 // this happens, some or none of the attachments may have been dropped | |
106 // successfully. | |
107 void Drop(const AttachmentIdList& ids, const DropCallback& callback); | |
108 | |
109 // Asynchronously reads metadata for the attachments identified by |ids|. | |
110 // | |
111 // |callback| will be invoked when finished. AttachmentStore will attempt to | |
112 // read metadata for all attachments specified in ids. If any of the | |
113 // metadata entries do not exist or could not be read, |callback|'s Result | |
114 // will be UNSPECIFIED_ERROR. | |
115 void ReadMetadataById(const AttachmentIdList& ids, | |
116 const ReadMetadataCallback& callback); | |
117 | |
118 // Asynchronously reads metadata for all attachments with |component_| | |
119 // reference in the store. | |
120 // | |
121 // |callback| will be invoked when finished. If any of the metadata entries | |
122 // could not be read, |callback|'s Result will be UNSPECIFIED_ERROR. | |
123 void ReadMetadata(const ReadMetadataCallback& callback); | |
124 | |
125 // Given current AttachmentStore (this) creates separate AttachmentStore that | |
126 // will be used by sync components (AttachmentService). Resulting | |
127 // AttachmentStore is backed by the same frontend/backend. | |
128 std::unique_ptr<AttachmentStoreForSync> CreateAttachmentStoreForSync() const; | |
129 | |
130 // Creates an AttachmentStore backed by in-memory implementation of attachment | |
131 // store. For now frontend lives on the same thread as backend. | |
132 static std::unique_ptr<AttachmentStore> CreateInMemoryStore(); | |
133 | |
134 // Creates an AttachmentStore backed by on-disk implementation of attachment | |
135 // store. Opens corresponding leveldb database located at |path|. All backend | |
136 // operations are scheduled to |backend_task_runner|. Opening attachment store | |
137 // is asynchronous, once it finishes |callback| will be called on the thread | |
138 // that called CreateOnDiskStore. Calling Read/Write/Drop before | |
139 // initialization completed is allowed. Later if initialization fails these | |
140 // operations will fail with STORE_INITIALIZATION_FAILED error. | |
141 static std::unique_ptr<AttachmentStore> CreateOnDiskStore( | |
142 const base::FilePath& path, | |
143 const scoped_refptr<base::SequencedTaskRunner>& backend_task_runner, | |
144 const InitCallback& callback); | |
145 | |
146 // Creates set of AttachmentStore/AttachmentStoreFrontend instances for tests | |
147 // that provide their own implementation of AttachmentstoreBackend for | |
148 // mocking. | |
149 static std::unique_ptr<AttachmentStore> CreateMockStoreForTest( | |
150 std::unique_ptr<AttachmentStoreBackend> backend); | |
151 | |
152 protected: | |
153 AttachmentStore(const scoped_refptr<AttachmentStoreFrontend>& frontend, | |
154 Component component); | |
155 | |
156 const scoped_refptr<AttachmentStoreFrontend>& frontend() { return frontend_; } | |
157 Component component() const { return component_; } | |
158 | |
159 private: | |
160 scoped_refptr<AttachmentStoreFrontend> frontend_; | |
161 // Modification operations with attachment store will be performed on behalf | |
162 // of |component_|. | |
163 const Component component_; | |
164 | |
165 DISALLOW_COPY_AND_ASSIGN(AttachmentStore); | |
166 }; | |
167 | |
168 // AttachmentStoreForSync extends AttachmentStore and provides additional | |
169 // functions necessary for AttachmentService. These are needed when | |
170 // AttachmentService writes attachment on behalf of model type after download | |
171 // and takes reference on attachment for the duration of upload. | |
172 // Model type implementation shouldn't use this interface. | |
173 class AttachmentStoreForSync : public AttachmentStore { | |
174 public: | |
175 ~AttachmentStoreForSync(); | |
176 | |
177 // Asynchronously adds reference from sync to attachments. | |
178 void SetSyncReference(const AttachmentIdList& ids); | |
179 | |
180 // Asynchronously adds reference from model type to attachments. | |
181 // Needed in GetOrDownloadAttachments when attachment is in local store but | |
182 // doesn't have model type reference. | |
183 void SetModelTypeReference(const AttachmentIdList& ids); | |
184 | |
185 // Asynchronously drops sync reference from attachments. | |
186 void DropSyncReference(const AttachmentIdList& ids); | |
187 | |
188 // Asynchronously reads metadata for all attachments with |sync_component_| | |
189 // reference in the store. | |
190 // | |
191 // |callback| will be invoked when finished. If any of the metadata entries | |
192 // could not be read, |callback|'s Result will be UNSPECIFIED_ERROR. | |
193 void ReadMetadataForSync(const ReadMetadataCallback& callback); | |
194 | |
195 private: | |
196 friend class AttachmentStore; | |
197 AttachmentStoreForSync(const scoped_refptr<AttachmentStoreFrontend>& frontend, | |
198 Component consumer_component, | |
199 Component sync_component); | |
200 | |
201 // |sync_component_| is passed to frontend when sync related operations are | |
202 // perfromed. | |
203 const Component sync_component_; | |
204 | |
205 DISALLOW_COPY_AND_ASSIGN(AttachmentStoreForSync); | |
206 }; | |
207 | |
208 } // namespace syncer | |
209 | |
210 #endif // COMPONENTS_SYNC_API_ATTACHMENTS_ATTACHMENT_STORE_H_ | |
OLD | NEW |