1 // Copyright 2013 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.
5 #include "chrome/browser/sync_file_system/drive_backend/remote_change_handler.h"
7 #include "base/logging.h"
8 #include "webkit/common/fileapi/file_system_util.h"
10 namespace sync_file_system
{
12 RemoteChangeHandler::ChangeQueueItem::ChangeQueueItem()
15 RemoteChangeHandler::ChangeQueueItem::ChangeQueueItem(
17 const fileapi::FileSystemURL
& url
)
18 : changestamp(changestamp
), url(url
) {}
20 bool RemoteChangeHandler::ChangeQueueComparator::operator()(
21 const ChangeQueueItem
& left
,
22 const ChangeQueueItem
& right
) {
23 if (left
.changestamp
!= right
.changestamp
)
24 return left
.changestamp
< right
.changestamp
;
25 return fileapi::FileSystemURL::Comparator()(left
.url
, right
.url
);
28 RemoteChangeHandler::RemoteChange::RemoteChange()
30 change(FileChange::FILE_CHANGE_ADD_OR_UPDATE
, SYNC_FILE_TYPE_UNKNOWN
) {}
32 RemoteChangeHandler::RemoteChange::RemoteChange(
34 const std::string
& resource_id
,
35 const std::string
& md5_checksum
,
36 const base::Time
& updated_time
,
37 const fileapi::FileSystemURL
& url
,
38 const FileChange
& change
)
39 : changestamp(changestamp
),
40 resource_id(resource_id
),
41 md5_checksum(md5_checksum
),
42 updated_time(updated_time
),
46 RemoteChangeHandler::RemoteChange::~RemoteChange() {}
48 bool RemoteChangeHandler::RemoteChangeComparator::operator()(
49 const RemoteChange
& left
,
50 const RemoteChange
& right
) {
51 // This should return true if |right| has higher priority than |left|.
52 // Smaller changestamps have higher priorities (i.e. need to be processed
54 if (left
.changestamp
!= right
.changestamp
)
55 return left
.changestamp
> right
.changestamp
;
59 RemoteChangeHandler::RemoteChangeHandler() {}
61 RemoteChangeHandler::~RemoteChangeHandler() {}
63 bool RemoteChangeHandler::GetChange(RemoteChange
* remote_change
) {
64 const fileapi::FileSystemURL
& url
= changes_
.begin()->url
;
65 const base::FilePath::StringType
& normalized_path
=
66 fileapi::VirtualPath::GetNormalizedFilePath(url
.path());
67 DCHECK(ContainsKey(origin_to_changes_map_
, url
.origin()));
68 PathToChangeMap
* path_to_change
= &origin_to_changes_map_
[url
.origin()];
69 DCHECK(ContainsKey(*path_to_change
, normalized_path
));
70 *remote_change
= (*path_to_change
)[normalized_path
].remote_change
;
74 bool RemoteChangeHandler::GetChangeForURL(
75 const fileapi::FileSystemURL
& url
,
76 RemoteChange
* remote_change
) {
77 OriginToChangesMap::iterator found_origin
=
78 origin_to_changes_map_
.find(url
.origin());
79 if (found_origin
== origin_to_changes_map_
.end())
82 PathToChangeMap
* path_to_change
= &found_origin
->second
;
83 PathToChangeMap::iterator found_change
= path_to_change
->find(
84 fileapi::VirtualPath::GetNormalizedFilePath(url
.path()));
85 if (found_change
== path_to_change
->end())
88 *remote_change
= found_change
->second
.remote_change
;
92 void RemoteChangeHandler::AppendChange(const RemoteChange
& remote_change
) {
93 base::FilePath::StringType normalized_path
=
94 fileapi::VirtualPath::GetNormalizedFilePath(remote_change
.url
.path());
96 PathToChangeMap
* path_to_change
=
97 &origin_to_changes_map_
[remote_change
.url
.origin()];
98 PathToChangeMap::iterator found
= path_to_change
->find(normalized_path
);
100 // Remove an existing change for |remote_change.url.path()|.
101 if (found
!= path_to_change
->end())
102 changes_
.erase(found
->second
.position_in_queue
);
104 std::pair
<PendingChangeQueue::iterator
, bool> inserted_to_queue
=
105 changes_
.insert(ChangeQueueItem(remote_change
.changestamp
,
107 DCHECK(inserted_to_queue
.second
);
109 (*path_to_change
)[normalized_path
] =
110 ChangeMapItem(remote_change
, inserted_to_queue
.first
);
113 bool RemoteChangeHandler::RemoveChangeForURL(
114 const fileapi::FileSystemURL
& url
) {
115 OriginToChangesMap::iterator found_origin
=
116 origin_to_changes_map_
.find(url
.origin());
117 if (found_origin
== origin_to_changes_map_
.end())
120 PathToChangeMap
* path_to_change
= &found_origin
->second
;
121 PathToChangeMap::iterator found_change
= path_to_change
->find(
122 fileapi::VirtualPath::GetNormalizedFilePath(url
.path()));
123 if (found_change
== path_to_change
->end())
126 changes_
.erase(found_change
->second
.position_in_queue
);
127 path_to_change
->erase(found_change
);
128 if (path_to_change
->empty())
129 origin_to_changes_map_
.erase(found_origin
);
133 void RemoteChangeHandler::RemoveChangesForOrigin(const GURL
& origin
) {
134 OriginToChangesMap::iterator found
= origin_to_changes_map_
.find(origin
);
135 if (found
== origin_to_changes_map_
.end())
137 for (PathToChangeMap::iterator itr
= found
->second
.begin();
138 itr
!= found
->second
.end(); ++itr
)
139 changes_
.erase(itr
->second
.position_in_queue
);
140 origin_to_changes_map_
.erase(found
);
143 bool RemoteChangeHandler::HasChangesForOrigin(const GURL
& origin
) const {
144 return ContainsKey(origin_to_changes_map_
, origin
);
147 RemoteChangeHandler::ChangeMapItem::ChangeMapItem() {}
149 RemoteChangeHandler::ChangeMapItem::ChangeMapItem(
150 const RemoteChange
& remote_change
,
151 PendingChangeQueue::iterator position_in_queue
)
152 : remote_change(remote_change
),
153 position_in_queue(position_in_queue
) {}
155 RemoteChangeHandler::ChangeMapItem::~ChangeMapItem() {}
157 } // namespace sync_file_system