WIP frameRequest refactor (iframe, window.open)
This commit is contained in:
parent
458649d073
commit
d6e29cd0fa
|
@ -251,7 +251,7 @@
|
|||
).then(function (params) {
|
||||
// discWin.child.close()
|
||||
// TODO params should have response_type indicating json, binary, etc
|
||||
var directives = JSON.parse(OAUTH3.utils.atob(OAUTH3.utils.urlSafeBase64ToBase64(params.result || params.directives)));
|
||||
var directives = JSON.parse(OAUTH3.utils.atob(OAUTH3.utils._urlSafeBase64ToBase64(params.result || params.directives)));
|
||||
return OAUTH3.hooks.directives.set(providerUri, directives);
|
||||
});
|
||||
}
|
||||
|
@ -310,7 +310,6 @@
|
|||
xhr = new XMLHttpRequest();
|
||||
}
|
||||
xhr.onreadystatechange = function () {
|
||||
console.error('state change');
|
||||
var data;
|
||||
if (xhr.readyState !== XMLHttpRequest.DONE) {
|
||||
// nothing to do here
|
||||
|
@ -365,7 +364,10 @@
|
|||
);
|
||||
|
||||
// TODO ability to reuse iframe instead of closing
|
||||
return OAUTH3._browser._iframe.insert(discObj.url, discObj.state, opts).then(function (params) {
|
||||
opts._windowType = opts.windowType;
|
||||
opts.windowType = opts.windowType || 'background';
|
||||
return OAUTH3._browser.frameRequest(discObj.url, discObj.state, opts).then(function (params) {
|
||||
opts.windowType = opts._windowType;
|
||||
OAUTH3._browser.closeFrame(discObj.state, { debug: opts.debug || params.debug });
|
||||
if (params.error) {
|
||||
return OAUTH3.utils._formatError(providerUri, params.error);
|
||||
|
@ -378,47 +380,67 @@
|
|||
});
|
||||
}
|
||||
, frameRequest: function (url, state, opts) {
|
||||
opts = opts || {};
|
||||
var previousFrame = OAUTH3._browser._frames[state];
|
||||
|
||||
if (!opts.windowType) {
|
||||
opts.windowType = 'popup';
|
||||
var windowType = opts.windowType;
|
||||
if (!windowType) {
|
||||
windowType = 'popup';
|
||||
}
|
||||
|
||||
opts = opts || {};
|
||||
var timeout = opts.timeout;
|
||||
if (opts.debug) {
|
||||
opts.timeout = opts.timeout || 15 * 60 * 1000;
|
||||
timeout = timeout || 3 * 60 * 1000;
|
||||
}
|
||||
else {
|
||||
timeout = timeout || ('background' === windowType ? 15 * 1000 : 3 * 60 * 1000);
|
||||
}
|
||||
|
||||
return new OAUTH3.PromiseA(function (resolve, reject) {
|
||||
// TODO periodically garbage collect expired handlers from window object
|
||||
var tok;
|
||||
|
||||
function cleanup() {
|
||||
delete window['--oauth3-callback-' + state];
|
||||
clearTimeout(tok);
|
||||
tok = null;
|
||||
// the actual close is done later (by the caller) so that the window/frame
|
||||
// can be reused or self-closes synchronously itself / by parent
|
||||
// (probably won't ever happen, but that's a negotiable implementation detail)
|
||||
}
|
||||
|
||||
|
||||
console.log('[oauth3.implicit.js] callbackName', '--oauth3-callback-' + state);
|
||||
window['--oauth3-callback-' + state] = function (params) {
|
||||
resolve(params);
|
||||
cleanup();
|
||||
};
|
||||
|
||||
tok = setTimeout(function () {
|
||||
var err = new Error("the iframe request did not complete within 15 seconds");
|
||||
var err = new Error(
|
||||
"the '" + windowType + "' request did not complete within " + Math.round(timeout / 1000) + "s"
|
||||
);
|
||||
err.code = "E_TIMEOUT";
|
||||
reject(err);
|
||||
cleanup();
|
||||
}, opts.timeout || 15 * 1000);
|
||||
}, timeout);
|
||||
|
||||
if ('background' === opts.windowType) {
|
||||
setTimeout(function () {
|
||||
if (!OAUTH3._browser._frames[state]) {
|
||||
reject(new Error("TODO: open the iframe first and discover oauth3 directives before popup"));
|
||||
cleanup();
|
||||
}
|
||||
}, 0);
|
||||
|
||||
if ('background' === windowType) {
|
||||
if (previousFrame) {
|
||||
previousFrame.location = url;
|
||||
//promise = previousFrame.promise;
|
||||
}
|
||||
else {
|
||||
OAUTH3._browser._iframe.insert(url, state, opts);
|
||||
OAUTH3._browser._frames[state] = OAUTH3._browser.iframe(url, state, opts);
|
||||
}
|
||||
} else if ('popup' === opts.windowType) {
|
||||
} else if ('popup' === windowType) {
|
||||
if (previousFrame) {
|
||||
previousFrame.location = url;
|
||||
if (opts.debug) {
|
||||
|
@ -426,9 +448,9 @@
|
|||
}
|
||||
}
|
||||
else {
|
||||
OAUTH3._browser.frame.open(url, state, opts);
|
||||
OAUTH3._browser._frames[state] = OAUTH3._browser.frame(url, state, opts);
|
||||
}
|
||||
} else if ('inline' === opts.windowType) {
|
||||
} else if ('inline' === windowType) {
|
||||
// callback function will never execute and would need to redirect back to current page
|
||||
// rather than the callback.html
|
||||
url += '&original_url=' + OAUTH3._browser.window.location.href;
|
||||
|
@ -478,72 +500,32 @@
|
|||
}
|
||||
}
|
||||
, _frames: {}
|
||||
, iframe: {
|
||||
insert: function (url, state, opts) {
|
||||
// TODO hidden / non-hidden (via directive even)
|
||||
var framesrc = '<iframe class="js-oauth3-iframe" src="' + url + '" ';
|
||||
if (opts.debug) {
|
||||
framesrc += ' width="800px" height="800px" style="opacity: 0.8;" frameborder="1"';
|
||||
}
|
||||
else {
|
||||
framesrc += ' width="1px" height="1px" frameborder="0"';
|
||||
}
|
||||
framesrc += '></iframe>';
|
||||
|
||||
var frame = OAUTH3._browser._frames[state] = OAUTH3._browser.window.document.createElement('div');
|
||||
OAUTH3._browser._frames[state].innerHTML = framesrc;
|
||||
OAUTH3._browser.window.document.body.appendChild(OAUTH3._browser._frames[state]);
|
||||
|
||||
return frame;
|
||||
, iframe: function (url, state, opts) {
|
||||
var framesrc = '<iframe class="js-oauth3-iframe" src="' + url + '" ';
|
||||
if (opts.debug) {
|
||||
framesrc += ' width="' + (opts.height || 600) + 'px"'
|
||||
+ ' height="' + (opts.width || 720) + 'px"'
|
||||
+ ' style="opacity: 0.8;" frameborder="1"';
|
||||
}
|
||||
else {
|
||||
framesrc += ' width="1px" height="1px" frameborder="0"';
|
||||
}
|
||||
framesrc += '></iframe>';
|
||||
|
||||
var frame = OAUTH3._browser.window.document.createElement('div');
|
||||
frame.innerHTML = framesrc;
|
||||
OAUTH3._browser.window.document.body.appendChild(frame);
|
||||
|
||||
return frame;
|
||||
}
|
||||
, frame: {
|
||||
open: function (url, state, opts) {
|
||||
if (opts.debug) {
|
||||
opts.timeout = opts.timeout || 15 * 60 * 1000;
|
||||
}
|
||||
, frame: function (url, state, opts) {
|
||||
|
||||
var promise = new OAUTH3.PromiseA(function (resolve, reject) {
|
||||
var tok;
|
||||
|
||||
function cleanup() {
|
||||
clearTimeout(tok);
|
||||
tok = null;
|
||||
delete window['--oauth3-callback-' + state];
|
||||
// close is done later in case the window is reused or self-closes synchronously itself / by parent
|
||||
// (probably won't ever happen, but that's a negotiable implementation detail)
|
||||
}
|
||||
|
||||
window['--oauth3-callback-' + state] = function (params) {
|
||||
console.log('YOLO!!');
|
||||
resolve(params);
|
||||
cleanup();
|
||||
};
|
||||
|
||||
tok = setTimeout(function () {
|
||||
var err = new Error("the windowed request did not complete within 3 minutes");
|
||||
err.code = "E_TIMEOUT";
|
||||
reject(err);
|
||||
cleanup();
|
||||
}, opts.timeout || 3 * 60 * 1000);
|
||||
|
||||
setTimeout(function () {
|
||||
if (!promise.child) {
|
||||
reject("TODO: open the iframe first and discover oauth3 directives before popup");
|
||||
cleanup();
|
||||
}
|
||||
}, 0);
|
||||
});
|
||||
|
||||
// TODO allow size changes (via directive even)
|
||||
OAUTH3._browser._frames[state] = window.open(
|
||||
url
|
||||
, 'oauth3-login-' + (opts.reuseWindow || state)
|
||||
, 'height=' + (opts.height || 720) + ',width=' + (opts.width || 620)
|
||||
);
|
||||
// TODO periodically garbage collect expired handlers from window object
|
||||
return promise;
|
||||
}
|
||||
// TODO allow size changes (via directive even)
|
||||
return window.open(
|
||||
url
|
||||
, 'oauth3-login-' + (opts.reuseWindow || state)
|
||||
, 'height=' + (opts.height || 720) + ',width=' + (opts.width || 620)
|
||||
);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue