Filestorage: Replace the two server classes with a wrapper class

Simplifies both the filestorage.js code as well as the starter.js code
that uses these FileStorage classes.

Now, the ServerFileStorageWrapper decorates the other FileStorage
classes by loading from the server when the file is not available.

Moreover, the previous starter.js was incorrectly passing the `baseurl`
parameter (it was passing it when baseurl was not defined nor needed).
This commit is contained in:
Ernest Wong 2018-11-13 11:57:06 +13:00 committed by Fabian
parent 93d9f6923e
commit 83b283ebbe
2 changed files with 20 additions and 83 deletions

View file

@ -190,13 +190,14 @@ IndexedDBFileStorage.prototype.set = function(sha256sum, data)
/**
* @constructor
* @implements {FileStorageInterface}
* @param {FileStorageInterface} file_storage
* @param {string} baseurl
*/
function ServerMemoryFileStorage(baseurl)
function ServerFileStorageWrapper(file_storage, baseurl)
{
dbg_assert(baseurl, "ServerMemoryFileStorage: baseurl should not be empty");
this.empty_storage = new MemoryFileStorage();
this.storage = file_storage;
this.baseurl = baseurl;
}
@ -205,7 +206,7 @@ function ServerMemoryFileStorage(baseurl)
* @param {string} sha256sum
* @return {!Promise<Uint8Array>}
*/
ServerMemoryFileStorage.prototype.load_from_server = function(sha256sum)
ServerFileStorageWrapper.prototype.load_from_server = function(sha256sum)
{
return new Promise((resolve, reject) =>
{
@ -221,9 +222,9 @@ ServerMemoryFileStorage.prototype.load_from_server = function(sha256sum)
* @param {string} sha256sum
* @return {Uint8Array}
*/
ServerMemoryFileStorage.prototype.get = async function(sha256sum) // jshint ignore:line
ServerFileStorageWrapper.prototype.get = async function(sha256sum) // jshint ignore:line
{
const data = await this.empty_storage.get(sha256sum); // jshint ignore:line
const data = await this.storage.get(sha256sum); // jshint ignore:line
if(!data)
{
return await this.load_from_server(sha256sum); // jshint ignore:line
@ -235,75 +236,7 @@ ServerMemoryFileStorage.prototype.get = async function(sha256sum) // jshint igno
* @param {string} sha256sum
* @param {!Uint8Array} data
*/
ServerMemoryFileStorage.prototype.set = async function(sha256sum, data) // jshint ignore:line
ServerFileStorageWrapper.prototype.set = async function(sha256sum, data) // jshint ignore:line
{
await this.empty_storage.set(sha256sum, data); // jshint ignore:line
}; // jshint ignore:line
/**
* @constructor
* @implements {FileStorageInterface}
* @param {string} baseurl
*/
function ServerIndexedDBFileStorage(baseurl)
{
dbg_assert(baseurl, "ServerIndexedDBFileStorage: baseurl should not be empty");
this.empty_storage = new IndexedDBFileStorage();
this.baseurl = baseurl;
}
/**
* @param {string} baseurl
* @return {IndexedDBFileStorage}
*/
ServerIndexedDBFileStorage.try_create = async function(baseurl) // jshint ignore:line
{
if(typeof window === "undefined" || !window.indexedDB)
{
throw new Error("IndexedDB is not available");
}
const file_storage = new ServerIndexedDBFileStorage(baseurl);
await file_storage.empty_storage.init(); // jshint ignore:line
return file_storage;
}; // jshint ignore:line
/**
* @private
* @param {string} sha256sum
* @return {!Promise<Uint8Array>}
*/
ServerIndexedDBFileStorage.prototype.load_from_server = function(sha256sum)
{
return new Promise((resolve, reject) =>
{
v86util.load_file(this.baseurl + sha256sum, { done: buffer =>
{
const data = new Uint8Array(buffer);
this.set(sha256sum, data).then(() => resolve(data));
}});
});
};
/**
* @param {string} sha256sum
* @return {Uint8Array}
*/
ServerIndexedDBFileStorage.prototype.get = async function(sha256sum) // jshint ignore:line
{
const data = await this.empty_storage.get(sha256sum); // jshint ignore:line
if(!data)
{
return await this.load_from_server(sha256sum); // jshint ignore:line
}
return data;
}; // jshint ignore:line
/**
* @param {string} sha256sum
* @param {!Uint8Array} data
*/
ServerIndexedDBFileStorage.prototype.set = async function(sha256sum, data) // jshint ignore:line
{
await this.empty_storage.set(sha256sum, data); // jshint ignore:line
await this.storage.set(sha256sum, data); // jshint ignore:line
}; // jshint ignore:line

View file

@ -448,18 +448,20 @@ V86Starter.prototype.continue_init = async function(emulator, options) // jshint
var fs_url = options["filesystem"]["basefs"];
var base_url = options["filesystem"]["baseurl"];
const IdealFileStorage = base_url ? ServerIndexedDBFileStorage : IndexedDBFileStorage;
const FallbackFileStorage = base_url ? ServerMemoryFileStorage : MemoryFileStorage;
let file_storage;
try
{
file_storage = await IdealFileStorage.try_create(base_url); // jshint ignore:line
file_storage = await IndexedDBFileStorage.try_create(); // jshint ignore:line
}
catch(e)
{
dbg_log("Initializing IndexedDBFileStorage failed due to Error: " + e);
dbg_log("Falling back to MemoryFileStorage instead.");
file_storage = new FallbackFileStorage(base_url);
file_storage = new MemoryFileStorage();
}
if (base_url)
{
file_storage = new ServerFileStorageWrapper(file_storage, base_url);
}
settings.fs9p = this.fs9p = new FS(file_storage);
@ -1057,18 +1059,20 @@ V86Starter.prototype.serial0_send = function(data)
*/
V86Starter.prototype.mount_fs = async function(path, baseurl, basefs, callback) // jshint ignore:line
{
const IdealFileStorage = baseurl ? ServerIndexedDBFileStorage : IndexedDBFileStorage;
const FallbackFileStorage = baseurl ? ServerMemoryFileStorage : MemoryFileStorage;
let file_storage;
try
{
file_storage = await IdealFileStorage.try_create(baseurl); // jshint ignore:line
file_storage = await IndexedDBFileStorage.try_create(); // jshint ignore:line
}
catch(e)
{
dbg_log("Initializing IndexedDBFileStorage failed due to Error: " + e);
dbg_log("Falling back to MemoryFileStorage instead.");
file_storage = new FallbackFileStorage(baseurl);
file_storage = new MemoryFileStorage();
}
if(baseurl)
{
file_storage = new ServerFileStorageWrapper(file_storage, baseurl);
}
const newfs = new FS(file_storage, this.fs9p.qidcounter);
const mount = () =>