VulpesOS/gaia/tv_apps/smart-system/js/net_error.js
OverSu b38dea0597 Publish Vulpes Preview 15 sources for desktop, Android and Tundra
Share Gaia assets and adapters, keep private profiles and development documents local, and update both public READMEs.
2026-09-30 23:13:03 +02:00

240 lines
6.9 KiB
JavaScript
Executable file

/* global KeyEvent */
/* global SimpleKeyNavigation */
(function(exports) {
'use strict';
/**
* Parse the neterror information that's sent to us as part of the documentURI
* and return an error object.
*
* The error object will contain the following attributes:
* e - Type of error (eg. 'netOffline').
* u - URL that generated the error.
* m - Manifest URI of the application that generated the error.
* c - Character set for default gecko error message (eg. 'UTF-8').
* d - Default gecko error message.
* f - The frame type ("regular", "browser", "app")
*/
function getErrorFromURI() {
var error = {},
uri = document.documentURI;
// Quick check to ensure it's the URI format we're expecting.
if (!uri.startsWith('about:neterror?')) {
// A blank error will generate the default error message (no network).
return error;
}
// Small hack to get the URL object to parse the URI correctly.
var url = new URL(uri.replace('about:', 'http://'));
// Set the error attributes.
['e', 'u', 'm', 'c', 'd', 'f'].forEach(
function(v) {
error[v] = url.searchParams.get(v);
}
);
switch (error.e) {
case 'connectionFailure':
case 'netInterrupt':
case 'netTimeout':
case 'netReset':
error.e = 'connectionFailed';
break;
case 'unknownSocketType':
case 'unknownProtocolFound':
case 'cspFrameAncestorBlocked':
error.e = 'invalidConnection';
break;
}
return error;
}
var ErrorView = function(error) {
this.error = error;
this.viewEl = null;
this.titleEl = null;
this.messageEl = null;
this.retryBtnEl = null;
this.closeBtnEl = null;
this.isFramed = this.isViewFramed(this.error);
this.init();
};
ErrorView.prototype = {
init: function ew_init() {
var template = document.getElementById('net-error-confirm-dialog');
window.LazyLoader.load(template, (function() {
this.viewEl = document.getElementById('net-error-confirm-dialog');
this.titleEl = document.getElementById('error-title');
this.messageEl = document.getElementById('error-message');
this.retryBtnEl = document.getElementById('retry-btn');
this.closeBtnEl = document.getElementById('close-btn');
this.applyStyle();
this.populateMessages();
this.addHandlers();
}).bind(this));
},
isViewFramed: function ew_isViewFramed(error) {
var manifestURL = error.m;
// frame type values (regular, browser, app)
var frameType = error.f;
switch (frameType) {
// if we are in a "regular" frame, we are indeed framed
case 'regular':
return true;
// if we are an "app" frame, we are not framed
case 'app':
return false;
// If we are in a "browser" frame, we are either in a browser tab/system
// bookmark, or mozbrowser iframe within in app. Since system
// bookmarks are considered unframed, we must perform a check here to
// distinguish between the two cases.
case 'browser':
return manifestURL !== window.SYSTEM_MANIFEST;
default:
throw new Error('about:netError: invalid frame type - ' + frameType);
}
},
applyStyle: function ew_applyStyle() {
this.viewEl.classList.add(this.error.e);
if (this.isFramed) {
this.viewEl.classList.add('net-error-dialog-framed');
}
},
populateMessages: function ew_populateMessages() {
var titleL10nId = '',
messageL10nId = '',
messageL10nOption = null;
switch(this.error.e){
case 'netOffline':
titleL10nId = 'net-error-net-off-line-title';
if (this.isFramed) {
messageL10nId = 'network-error-launching';
messageL10nOption = {name: this.error.u};
} else {
messageL10nId = 'net-error-net-off-line-message';
}
break;
case 'dnsNotFound':
titleL10nId = 'server-not-found';
messageL10nId = 'server-not-found-error';
messageL10nOption = {name: this.error.u};
break;
case 'connectionFailed':
titleL10nId = 'connection-failed';
messageL10nId = 'connection-failed-error';
break;
case 'invalidConnection':
titleL10nId = 'invalid-connection';
messageL10nId = 'invalid-connection-error';
break;
default:
titleL10nId = 'unable-to-connect';
messageL10nId = this.error.d;
}
navigator.mozL10n.setAttributes(this.titleEl, titleL10nId);
navigator.mozL10n.setAttributes(this.messageEl, messageL10nId,
messageL10nOption);
},
addHandlers: function ew_addHandlers() {
var navBtns = [],
keyNav = null;
document.addEventListener('keydown', this.handleKeydown.bind(this));
if (!this.isFramed) {
navBtns.push(this.closeBtnEl);
this.closeBtnEl.addEventListener('click', this.close);
this.closeBtnEl.addEventListener('keydown',
this.handleCloseButtonKeydown.bind(this));
}
navBtns.push(this.retryBtnEl);
this.retryBtnEl.addEventListener('click', this.reload);
this.retryBtnEl.addEventListener('keydown',
this.handleRetryButtonKeydown.bind(this));
keyNav = new SimpleKeyNavigation();
keyNav.start(navBtns, SimpleKeyNavigation.DIRECTION.HORIZONTAL);
keyNav.focusOn(this.retryBtnEl);
},
handleKeydown: function ew_handleKeydown(e) {
if (e.keyCode === KeyEvent.DOM_VK_ESCAPE ||
e.keyCode === KeyEvent.DOM_VK_BACK_SPACE) {
this.close();
}
},
handleCloseButtonKeydown: function ew_handleCloseButtonKeydown(e) {
if (e.keyCode === KeyEvent.DOM_VK_RETURN) {
this.close();
}
},
handleRetryButtonKeydown: function ew_handleRetryButtonKeydown(e) {
if (e.keyCode === KeyEvent.DOM_VK_RETURN) {
this.reload();
}
},
reload: function ew_reload() {
// When reloading a page with POSTDATA the user will be prompted to
// confirm if he wants to resend the data. If the user accepted to resend
// the data, during the reload function call the onbeforeunload event is
// fired, otherwise if the event is not triggered then the last url from
// the history is loaded.
var isReloading = false;
window.addEventListener('beforeunload', function onBeforeunload() {
isReloading = true;
});
window.location.reload(true);
if (!isReloading) {
history.back();
}
},
close: function ew_close() {
window.close();
},
};
var NetError = {
create: function create() {
var error = getErrorFromURI();
if (error) {
return new ErrorView(error);
}
}
};
navigator.mozL10n.ready(NetError.create);
exports.NetError = NetError;
})(window);