Bug 1102477: pass HAWK request errors through to content. r=Standard8
--- a/browser/components/loop/MozLoopAPI.jsm
+++ b/browser/components/loop/MozLoopAPI.jsm
@@ -38,23 +38,33 @@ XPCOMUtils.defineLazyServiceGetter(this,
"nsIExternalProtocolService");
this.EXPORTED_SYMBOLS = ["injectLoopAPI"];
/**
* Trying to clone an Error object into a different container will yield an error.
* We can work around this by copying the properties we care about onto a regular
* object.
*
- * @param {Error} error Error object to copy
- * @param {nsIDOMWindow} targetWindow The content window to attach the API
+ * @param {Error|nsIException} error Error object to copy
+ * @param {nsIDOMWindow} targetWindow The content window to clone into
*/
const cloneErrorObject = function(error, targetWindow) {
let obj = new targetWindow.Error();
- for (let prop of Object.getOwnPropertyNames(error)) {
+ let props = Object.getOwnPropertyNames(error);
+ // nsIException properties are not enumerable, so we'll try to copy the most
+ // common and useful ones.
+ if (!props.length) {
+ props.push("message", "filename", "lineNumber", "columnNumber", "stack");
+ }
+ for (let prop of props) {
let value = error[prop];
+ // for nsIException objects, the property may not be defined.
+ if (typeof value == "undefined") {
+ continue;
+ }
if (typeof value != "string" && typeof value != "number") {
value = String(value);
}
Object.defineProperty(Cu.waiveXrays(obj), prop, {
configurable: false,
enumerable: true,
value: value,
@@ -73,26 +83,31 @@ const cloneErrorObject = function(error,
* @param {any} value Value or object to copy
* @param {nsIDOMWindow} targetWindow The content window to copy to
*/
const cloneValueInto = function(value, targetWindow) {
if (!value || typeof value != "object") {
return value;
}
+ // HAWK request errors contain an nsIException object inside `value`.
+ if (("error" in value) && (value.error instanceof Ci.nsIException)) {
+ value = value.error;
+ }
+
// Strip Function properties, since they can not be cloned across boundaries
// like this.
for (let prop of Object.getOwnPropertyNames(value)) {
if (typeof value[prop] == "function") {
delete value[prop];
}
}
// Inspect for an error this way, because the Error object is special.
- if (value.constructor.name == "Error") {
+ if (value.constructor.name == "Error" || value instanceof Ci.nsIException) {
return cloneErrorObject(value, targetWindow);
}
let clone;
try {
clone = Cu.cloneInto(value, targetWindow);
} catch (ex) {
MozLoopService.log.debug("Failed to clone value:", value);