Upstream version 7.36.149.0
[platform/framework/web/crosswalk.git] / src / ui / file_manager / file_manager / background / js / drive_sync_handler.js
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 'use strict';
6
7 /**
8  * Handler of the background page for the drive sync events.
9  * @param {ProgressCenter} progressCenter Progress center to submit the
10  *     progressing items.
11  * @constructor
12  */
13 function DriveSyncHandler(progressCenter) {
14   /**
15    * Progress center to submit the progressing item.
16    * @type {ProgressCenter}
17    * @private
18    */
19   this.progressCenter_ = progressCenter;
20
21   /**
22    * Counter for progress ID.
23    * @type {number}
24    * @private
25    */
26   this.idCounter_ = 0;
27
28   /**
29    * Map of file urls and progress center items.
30    * @type {Object.<string, ProgressCenterItem>}
31    * @private
32    */
33   this.items_ = {};
34
35   /**
36    * Async queue.
37    * @type {AsyncUtil.Queue}
38    * @private
39    */
40   this.queue_ = new AsyncUtil.Queue();
41
42   // Register events.
43   chrome.fileBrowserPrivate.onFileTransfersUpdated.addListener(
44       this.onFileTransfersUpdated_.bind(this));
45   chrome.fileBrowserPrivate.onDriveSyncError.addListener(
46       this.onDriveSyncError_.bind(this));
47 }
48
49 /**
50  * Completed event name.
51  * @type {string}
52  * @const
53  */
54 DriveSyncHandler.COMPLETED_EVENT = 'completed';
55
56 /**
57  * Progress ID of the drive sync.
58  * @type {string}
59  * @const
60  */
61 DriveSyncHandler.PROGRESS_ITEM_ID_PREFIX = 'drive-sync-';
62
63 DriveSyncHandler.prototype = {
64   __proto__: cr.EventTarget.prototype,
65
66   /**
67    * @return {boolean} Whether the handler is having syncing items or not.
68    */
69   get syncing() {
70     // Check if this.items_ has properties or not.
71     for (var url in this.items_) {
72       return true;
73     }
74     return false;
75   }
76 };
77
78 /**
79  * Handles file transfer updated events.
80  * @param {Array.<FileTransferStatus>} statusList List of drive status.
81  * @private
82  */
83 DriveSyncHandler.prototype.onFileTransfersUpdated_ = function(statusList) {
84   var completed = false;
85   for (var i = 0; i < statusList.length; i++) {
86     var status = statusList[i];
87     switch (status.transferState) {
88       case 'in_progress':
89       case 'started':
90         this.updateItem_(status);
91         break;
92       case 'completed':
93       case 'failed':
94         this.removeItem_(status);
95         if (!this.syncing)
96           this.dispatchEvent(new Event(DriveSyncHandler.COMPLETED_EVENT));
97         break;
98       default:
99         throw new Error(
100             'Invalid transfer state: ' + status.transferState + '.');
101     }
102   }
103 };
104
105 /**
106  * Updates the item involved with the given status.
107  * @param {FileTransferStatus} status Transfer status.
108  * @private
109  */
110 DriveSyncHandler.prototype.updateItem_ = function(status) {
111   this.queue_.run(function(callback) {
112     if (this.items_[status.fileUrl]) {
113       callback();
114       return;
115     }
116     webkitResolveLocalFileSystemURL(status.fileUrl, function(entry) {
117       var item = new ProgressCenterItem();
118       item.id =
119           DriveSyncHandler.PROGRESS_ITEM_ID_PREFIX + (this.idCounter_++);
120       item.type = ProgressItemType.SYNC;
121       item.quiet = true;
122       item.message = strf('SYNC_FILE_NAME', entry.name);
123       item.cancelCallback = this.requestCancel_.bind(this, entry);
124       this.items_[status.fileUrl] = item;
125       callback();
126     }.bind(this), function(error) {
127       console.warn('Resolving URL ' + status.fileUrl + ' is failed: ', error);
128       callback();
129     });
130   }.bind(this));
131   this.queue_.run(function(callback) {
132     var item = this.items_[status.fileUrl];
133     if (!item) {
134       callback();
135       return;
136     }
137     item.progressValue = status.processed || 0;
138     item.progressMax = status.total || 1;
139     this.progressCenter_.updateItem(item);
140     callback();
141   }.bind(this));
142 };
143
144 /**
145  * Removes the item involved with the given status.
146  * @param {FileTransferStatus} status Transfer status.
147  * @private
148  */
149 DriveSyncHandler.prototype.removeItem_ = function(status) {
150   this.queue_.run(function(callback) {
151     var item = this.items_[status.fileUrl];
152     if (!item) {
153       callback();
154       return;
155     }
156     item.state = status.transferState === 'completed' ?
157         ProgressItemState.COMPLETED : ProgressItemState.CANCELED;
158     this.progressCenter_.updateItem(item);
159     delete this.items_[status.fileUrl];
160     callback();
161   }.bind(this));
162 };
163
164 /**
165  * Requests to cancel for the given files' drive sync.
166  * @param {Entry} entry Entry to be canceled.
167  * @private
168  */
169 DriveSyncHandler.prototype.requestCancel_ = function(entry) {
170   chrome.fileBrowserPrivate.cancelFileTransfers([entry.toURL()], function() {});
171 };
172
173 /**
174  * Handles drive's sync errors.
175  * @param {DriveSyncErrorEvent} event Drive sync error event.
176  * @private
177  */
178 DriveSyncHandler.prototype.onDriveSyncError_ = function(event) {
179   webkitResolveLocalFileSystemURL(event.fileUrl, function(entry) {
180     var item;
181     item = new ProgressCenterItem();
182     item.id = DriveSyncHandler.PROGRESS_ITEM_ID_PREFIX + (this.idCounter_++);
183     item.type = ProgressItemType.SYNC;
184     item.quiet = true;
185     item.state = ProgressItemState.ERROR;
186     switch (event.type) {
187       case 'delete_without_permission':
188         item.message =
189             strf('SYNC_DELETE_WITHOUT_PERMISSION_ERROR', entry.name);
190         break;
191       case 'service_unavailable':
192         item.message = str('SYNC_SERVICE_UNAVAILABLE_ERROR');
193         break;
194       case 'misc':
195         item.message = strf('SYNC_MISC_ERROR', entry.name);
196         break;
197     }
198     this.progressCenter_.updateItem(item);
199   }.bind(this));
200 };