Commit f6bc2704 authored by Luciano Pacheco's avatar Luciano Pacheco Committed by Commit Bot

Files app: ES6 class for metadata_cache_item.js, function_sequence.js and function_parallel.js

Bug: 778674
Change-Id: I37b5d58f5f3b5d7cb2f30ada3e383c655ec69978
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1750464
Auto-Submit: Luciano Pacheco <lucmult@chromium.org>
Reviewed-by: default avatarAustin Tankiang <austinct@chromium.org>
Commit-Queue: Austin Tankiang <austinct@chromium.org>
Cr-Commit-Position: refs/heads/master@{#686328}
parent ad34509a
......@@ -3,17 +3,17 @@
// found in the LICENSE file.
/**
* @class FunctionSequence to invoke steps in sequence
*
* @class FunctionParallel to invoke steps in parallel.
*/
class FunctionParallel {
/**
* @param {string} name Name of the function.
* @param {Array<Function>} steps Array of functions to invoke in parallel.
* @param {MetadataParser} logger Logger object.
* @param {function()} callback Callback to invoke on success.
* @param {function(string)} failureCallback Callback to invoke on failure.
* @constructor
* @struct
*/
function FunctionParallel(name, steps, logger, callback, failureCallback) {
constructor(name, steps, logger, callback, failureCallback) {
// Private variables hidden in closure
this.currentStepIdx_ = -1;
this.failed_ = false;
......@@ -28,40 +28,40 @@ function FunctionParallel(name, steps, logger, callback, failureCallback) {
this.nextStep = this.nextStep_.bind(this);
this.onError = this.onError_.bind(this);
this.apply = this.start.bind(this);
}
}
/**
/**
* Error handling function, which fires error callback.
*
* @param {string} err Error message.
* @private
*/
FunctionParallel.prototype.onError_ = function(err) {
onError_(err) {
if (!this.failed_) {
this.failed_ = true;
this.failureCallback_(err);
}
};
}
/**
* Advances to next step. This method should not be used externally. In external
* cases should be used nextStep function, which is defined in closure and thus
* has access to internal variables of functionsequence.
/**
* Advances to next step. This method should not be used externally. In
* external cases should be used nextStep function, which is defined in
* closure and thus has access to internal variables of functionsequence.
*
* @private
*/
FunctionParallel.prototype.nextStep_ = function() {
nextStep_() {
if (--this.remaining == 0 && !this.failed_) {
this.callback_();
}
};
}
/**
* This function should be called only once on start, so start all the children
* at once
/**
* This function should be called only once on start, so start all the
* children at once
* @param {...} var_args Arguments to be passed to all the steps.
*/
FunctionParallel.prototype.start = function(var_args) {
start(var_args) {
this.logger.vlog(
'Starting [' + this.steps_.length + '] parallel tasks ' +
'with ' + arguments.length + ' argument(s)');
......@@ -71,11 +71,13 @@ FunctionParallel.prototype.start = function(var_args) {
}
}
for (let i = 0; i < this.steps_.length; i++) {
this.logger.vlog('Attempting to start step [' + this.steps_[i].name + ']');
this.logger.vlog(
'Attempting to start step [' + this.steps_[i].name + ']');
try {
this.steps_[i].apply(this, arguments);
} catch (e) {
this.onError(e.toString());
}
}
};
}
}
......@@ -3,16 +3,17 @@
// found in the LICENSE file.
/**
* @class FunctionSequence to invoke steps in sequence
*
* @class FunctionSequence to invoke steps in sequence.
*/
class FunctionSequence {
/**
* @param {string} name Name of the function.
* @param {Array} steps Array of functions to invoke in sequence.
* @param {MetadataParser} logger Logger object.
* @param {function()} callback Callback to invoke on success.
* @param {function(string)} failureCallback Callback to invoke on failure.
* @constructor
*/
function FunctionSequence(name, steps, logger, callback, failureCallback) {
constructor(name, steps, logger, callback, failureCallback) {
// Private variables hidden in closure
this.currentStepIdx_ = -1;
this.failed_ = false;
......@@ -21,71 +22,73 @@ function FunctionSequence(name, steps, logger, callback, failureCallback) {
this.failureCallback_ = failureCallback;
this.logger = logger;
this.name = name;
/** @public {boolean} */
this.started = false;
this.onError = this.onError_.bind(this);
this.finish = this.finish_.bind(this);
this.nextStep = this.nextStep_.bind(this);
this.apply = this.apply_.bind(this);
}
}
/**
/**
* Sets new callback
*
* @param {function()} callback New callback to call on succeed.
*/
FunctionSequence.prototype.setCallback = function(callback) {
setCallback(callback) {
this.callback_ = callback;
};
}
/**
/**
* Sets new error callback
*
* @param {function(string)} failureCallback New callback to call on failure.
*/
FunctionSequence.prototype.setFailureCallback = function(failureCallback) {
setFailureCallback(failureCallback) {
this.failureCallback_ = failureCallback;
};
}
/**
/**
* Error handling function, which traces current error step, stops sequence
* advancing and fires error callback.
*
* @param {string} err Error message.
* @private
*/
FunctionSequence.prototype.onError_ = function(err) {
onError_(err) {
this.logger.vlog(
'Failed step: ' + this.steps_[this.currentStepIdx_].name + ': ' + err);
if (!this.failed_) {
this.failed_ = true;
this.failureCallback_(err);
}
};
}
/**
/**
* Finishes sequence processing and jumps to the last step.
* This method should not be used externally. In external
* cases should be used finish function, which is defined in closure and thus
* has access to internal variables of functionsequence.
* @private
*/
FunctionSequence.prototype.finish_ = function() {
finish_() {
if (!this.failed_ && this.currentStepIdx_ < this.steps_.length) {
this.currentStepIdx_ = this.steps_.length;
this.callback_();
}
};
}
/**
/**
* Advances to next step.
* This method should not be used externally. In external
* cases should be used nextStep function, which is defined in closure and thus
* has access to internal variables of functionsequence.
* cases should be used nextStep function, which is defined in closure and
* thus has access to internal variables of functionsequence.
* @param {...} var_args Arguments to be passed to the next step.
* @private
*/
FunctionSequence.prototype.nextStep_ = function(var_args) {
nextStep_(var_args) {
if (this.failed_) {
return;
}
......@@ -95,37 +98,40 @@ FunctionSequence.prototype.nextStep_ = function(var_args) {
this.callback_.apply(this, arguments);
} else {
this.logger.vlog(
'Attempting to start step [' + this.steps_[this.currentStepIdx_].name +
']');
'Attempting to start step [' +
this.steps_[this.currentStepIdx_].name + ']');
try {
this.steps_[this.currentStepIdx_].apply(this, arguments);
} catch (e) {
this.onError(e.toString());
}
}
};
}
/**
* This function should be called only once on start, so start sequence pipeline
/**
* This function should be called only once on start, so start sequence
* pipeline
* @param {...} var_args Arguments to be passed to the first step.
*/
FunctionSequence.prototype.start = function(var_args) {
start(var_args) {
if (this.started) {
throw new Error('"Start" method of FunctionSequence was called twice');
}
this.logger.log('Starting sequence with ' + arguments.length + ' arguments');
this.logger.log(
'Starting sequence with ' + arguments.length + ' arguments');
this.started = true;
this.nextStep.apply(this, arguments);
};
}
/**
/**
* Add Function object mimics to FunctionSequence
* @private
* @param {*} obj Object.
* @param {Array} args Arguments.
*/
FunctionSequence.prototype.apply_ = function(obj, args) {
apply_(obj, args) {
this.start.apply(this, args);
};
}
}
......@@ -4,24 +4,23 @@
/**
* Cache of metadata for a FileEntry.
* @constructor
* @struct
*/
function MetadataCacheItem() {
class MetadataCacheItem {
constructor() {
/**
* Map of property name and MetadataCacheItemProperty.
* @private {!Object<!MetadataCacheItemProperty>}
* @const
*/
this.properties_ = {};
}
}
/**
/**
* Creates requested names that need to be loaded.
* @param {!Array<string>} names
* @return {!Array<string>} Property names that need to be loaded.
*/
MetadataCacheItem.prototype.createRequests = function(names) {
createRequests(names) {
const loadRequested = [];
for (let i = 0; i < names.length; i++) {
const name = names[i];
......@@ -35,14 +34,14 @@ MetadataCacheItem.prototype.createRequests = function(names) {
loadRequested.push(name);
}
return loadRequested;
};
}
/**
* Marks the given properies as loading.
/**
* Marks the given properties as loading.
* @param {number} requestId
* @param {!Array<string>} names
*/
MetadataCacheItem.prototype.startRequests = function(requestId, names) {
startRequests(requestId, names) {
for (let i = 0; i < names.length; i++) {
const name = names[i];
assert(!/Error$/.test(name));
......@@ -52,15 +51,15 @@ MetadataCacheItem.prototype.startRequests = function(requestId, names) {
this.properties_[name].requestId = requestId;
this.properties_[name].state = MetadataCacheItemPropertyState.LOADING;
}
};
}
/**
/**
* Feeds the result of startRequests.
* @param {number} requestId Request ID passed when calling startRequests.
* @param {!MetadataItem} typedObject Map of property name and value.
* @return {boolean} Whether at least one property is updated or not.
*/
MetadataCacheItem.prototype.storeProperties = function(requestId, typedObject) {
storeProperties(requestId, typedObject) {
let changed = false;
const object = /** @type {!Object} */ (typedObject);
for (let name in object) {
......@@ -87,29 +86,29 @@ MetadataCacheItem.prototype.storeProperties = function(requestId, typedObject) {
this.properties_[name].state = MetadataCacheItemPropertyState.FULFILLED;
}
return changed;
};
}
/**
/**
* Marks the caches of all properties in the item as invalidates and forces to
* reload at the next time of startRequests.
* @param {number} requestId Request ID of the invalidation request. This must
* be larger than other requets ID passed to the item before.
*/
MetadataCacheItem.prototype.invalidate = function(requestId) {
invalidate(requestId) {
for (const name in this.properties_) {
assert(this.properties_[name].requestId < requestId);
this.properties_[name].requestId = requestId;
this.properties_[name].state = MetadataCacheItemPropertyState.INVALIDATED;
}
};
}
/**
/**
* Obtains property for entries and names.
* Note that it returns invalidated properties also.
* @param {!Array<string>} names
* @return {!MetadataItem}
*/
MetadataCacheItem.prototype.get = function(names) {
get(names) {
const result = /** @type {!Object} */ (new MetadataItem());
for (let i = 0; i < names.length; i++) {
const name = names[i];
......@@ -120,13 +119,13 @@ MetadataCacheItem.prototype.get = function(names) {
}
}
return /** @type {!MetadataItem} */ (result);
};
}
/**
/**
* Creates deep copy of the item.
* @return {!MetadataCacheItem}
*/
MetadataCacheItem.prototype.clone = function() {
clone() {
const clonedItem = new MetadataCacheItem();
for (const name in this.properties_) {
const property = this.properties_[name];
......@@ -137,14 +136,14 @@ MetadataCacheItem.prototype.clone = function() {
clonedItem.properties_[name].state = property.state;
}
return clonedItem;
};
}
/**
/**
* Returns whether all the given properties are fulfilled.
* @param {!Array<string>} names Property names.
* @return {boolean}
*/
MetadataCacheItem.prototype.hasFreshCache = function(names) {
hasFreshCache(names) {
for (let i = 0; i < names.length; i++) {
if (!(this.properties_[names[i]] &&
this.properties_[names[i]].state ===
......@@ -153,7 +152,8 @@ MetadataCacheItem.prototype.hasFreshCache = function(names) {
}
}
return true;
};
}
}
/**
* @enum {string}
......@@ -166,10 +166,9 @@ const MetadataCacheItemPropertyState = {
/**
* Cache of metadata for a property.
* @constructor
* @struct
*/
function MetadataCacheItemProperty() {
class MetadataCacheItemProperty {
constructor() {
/**
* Cached value of property.
* @public {*}
......@@ -192,4 +191,5 @@ function MetadataCacheItemProperty() {
* @public {MetadataCacheItemPropertyState}
*/
this.state = MetadataCacheItemPropertyState.INVALIDATED;
}
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment