cordova-app-loader
Version:
Cordova App Loader - remote update your cordova app
139 lines (124 loc) • 4.28 kB
JavaScript
(function(){
// Retrieved and slightly modified from: https://github.com/typicode/pegasus
// --------------------------------------------------------------------------
//
// a url (naming it a, beacause it will be reused to store callbacks)
// xhr placeholder to avoid using var, not to be used
window.pegasus = function pegasus(a, xhr) {
xhr = new XMLHttpRequest();
// Open url
xhr.open('GET', a);
// Reuse a to store callbacks
a = [];
// onSuccess handler
// onError handler
// cb placeholder to avoid using var, should not be used
xhr.onreadystatechange = xhr.then = function(onSuccess, onError, cb, result) {
// Test if onSuccess is a function or a load event
if (onSuccess.call) a = [onSuccess, onError];
// Test if request is complete
if (xhr.readyState == 4) {
try {
if(xhr.status === 200 || xhr.status === 0){
result = JSON.parse(xhr.responseText);
cb = a[0];
} else {
result = new Error('Status: '+xhr.status);
cb = a[1];
}
} catch(e) {
result = e;
cb = a[1];
}
// Safari doesn't support xhr.responseType = 'json'
// so the response is parsed
if (cb) cb(result);
}
};
// Send
xhr.send();
// Return request
return xhr;
};
//------------------------------------------------------------------
// Step 2: After fetching manifest (localStorage or XHR), load it
function loadManifest(manifest,fromLocalStorage,timeout){
// Safety timeout. If BOOTSTRAP_OK is not defined,
// it will delete the 'localStorage' version and revert to factory settings.
if(fromLocalStorage){
setTimeout(function(){
if(!window.BOOTSTRAP_OK){
console.warn('BOOTSTRAP_OK !== true; Resetting to original manifest.json...');
localStorage.removeItem('manifest');
location.reload();
}
},timeout);
}
if(!manifest.load) {
console.error('Manifest has nothing to load (manifest.load is empty).',manifest);
return;
}
var el,
head = document.getElementsByTagName('head')[0],
scripts = manifest.load.concat(),
now = Date.now();
// Load Scripts
function loadScripts(){
scripts.forEach(function(src) {
if(!src) return;
// Ensure the 'src' has no '/' (it's in the root already)
if(src[0] === '/') src = src.substr(1);
src = manifest.root + src ;
// Load javascript
if(src.substr(-3) === ".js"){
el= document.createElement('script');
el.charset="UTF-8";
el.type= 'text/javascript';
el.src= src + '?' + now;
el.async = false;
// Load CSS
} else {
el= document.createElement('link');
el.rel = "stylesheet";
el.href = src + '?' + now;
el.type = "text/css";
}
head.appendChild(el);
});
}
//---------------------------------------------------
// Step 3: Ensure the 'root' end with a '/'
manifest.root = manifest.root || './';
if(manifest.root.length > 0 && manifest.root[manifest.root.length-1] !== '/')
manifest.root += '/';
// Step 4: Save manifest for next time
if(!fromLocalStorage)
localStorage.setItem('manifest',JSON.stringify(manifest));
// Step 5: Load Scripts
// If we're loading Cordova files, make sure Cordova is ready first!
if(typeof window.cordova !== 'undefined'){
document.addEventListener("deviceready", loadScripts, false);
} else {
loadScripts();
}
// Save to global scope
window.Manifest = manifest;
}
//---------------------------------------------------------------------
window.Manifest = {};
// Step 1: Load manifest from localStorage
var manifest = JSON.parse(localStorage.getItem('manifest'));
// grab manifest.json location from <script manifest="..."></script>
var s = document.querySelector('script[manifest]');
// Not in localStorage? Fetch it!
if(!manifest){
var url = (s? s.getAttribute('manifest'): null) || 'manifest.json';
// get manifest.json, then loadManifest.
pegasus(url).then(loadManifest,function(xhr){
console.error('Could not download '+url+': '+xhr.status);
});
// Manifest was in localStorage. Load it immediatly.
} else {
loadManifest(manifest,true,s.getAttribute('timeout') || 10000);
}
})();