-
Notifications
You must be signed in to change notification settings - Fork 0
[TP-179336] Use postmessage instead of storage event for embedded case #2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -38,6 +38,7 @@ var ServicesMixin = Mixin.create({ | |
let service = this; | ||
let lastRemote = this.remote; | ||
let storageToriiEventHandler; | ||
let messageToriiEventHandler; | ||
|
||
return new EmberPromise(function (resolve, reject) { | ||
if (lastRemote) { | ||
|
@@ -55,7 +56,34 @@ var ServicesMixin = Mixin.create({ | |
}); | ||
} | ||
}; | ||
|
||
// Using postMessage as an alternative to localStorage/storageEvent | ||
// for case of web site embedded in iframe | ||
messageToriiEventHandler = function (messageEvent) { | ||
if (messageEvent.data === 'getPendingRequestKey') { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. suggestion: this fix should be merged alongside the first commit. Also, the commit about feature flags is confusing here, but that only makes sense in the context of the SCF application (not here in Torii fork land). |
||
messageEvent.source.postMessage( | ||
JSON.stringify({ pendingRequestKey: service.pendingRequestKey }), | ||
window.location.origin | ||
); | ||
} else { | ||
const msg = JSON.parse(messageEvent.data); | ||
const key = Object.keys(msg)[0]; | ||
var remoteIdFromEvent = PopupIdSerializer.deserialize( | ||
decodeURIComponent(key) | ||
); | ||
if (remoteId === remoteIdFromEvent) { | ||
var data = parseMessage(msg[key], keys); | ||
localStorage.removeItem(key); | ||
run(function () { | ||
resolve(data); | ||
}); | ||
} | ||
} | ||
}; | ||
window.addEventListener('message', messageToriiEventHandler); | ||
|
||
var pendingRequestKey = PopupIdSerializer.serialize(remoteId); | ||
service.pendingRequestKey = pendingRequestKey; | ||
localStorage.setItem(CURRENT_REQUEST_KEY, pendingRequestKey); | ||
localStorage.removeItem(WARNING_KEY); | ||
|
||
|
@@ -115,6 +143,7 @@ var ServicesMixin = Mixin.create({ | |
}).finally(function () { | ||
// didClose will reject this same promise, but it has already resolved. | ||
service.close(); | ||
window.removeEventListener('message', messageToriiEventHandler); | ||
window.removeEventListener('storage', storageToriiEventHandler); | ||
}); | ||
}, | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,6 @@ | ||
{ | ||
"name": "torii", | ||
"version": "1.0.0-beta.2", | ||
"version": "1.0.0-beta.3", | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. suggestion: the version bump should be the last commit - also, do we need to bump the version up again? |
||
"description": "A set of clean abstractions for authentication in Ember.js", | ||
"keywords": [ | ||
"authentication", | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,129 @@ | ||
/* eslint-disable ember/no-mixins, ember/no-new-mixins, ember/no-classic-classes */ | ||
|
||
import EmberObject from '@ember/object'; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. suggestion: let's add the test to the first commit. thought: I need some help walking through the test code - I'll schedule something for this afternoon. Update: tests seem to be failing - can reschedule the group review we rescheduled if you need more time. |
||
import Evented from '@ember/object/evented'; | ||
import UiServiceMixin, { | ||
CURRENT_REQUEST_KEY, | ||
} from 'torii/mixins/ui-service-mixin'; | ||
import PopupIdSerializer from 'torii/lib/popup-id-serializer'; | ||
import { module, test } from 'qunit'; | ||
|
||
module('Unit | Mixin | ui-service-mixin', function (hooks) { | ||
const originalWindowOpen = window.open; | ||
|
||
const popupId = '09123-asdf'; | ||
const expectedUrl = 'http://authServer'; | ||
const expectedRedirectUrl = 'http://localserver?code=fr'; | ||
const expectedMessage = 'getPendingRequestKey'; | ||
|
||
const mockWindowListener = (event) => { | ||
let msg; | ||
try { | ||
msg = JSON.parse(event.data); | ||
} catch { | ||
// allow | ||
} | ||
if (msg && Object.keys(msg)[0] === 'pendingRequestKey') { | ||
const obj = {}; | ||
const key = PopupIdSerializer.serialize(encodeURIComponent(popupId)); | ||
obj[key] = `${expectedUrl}?redirect_url=${expectedRedirectUrl}`; | ||
window.dispatchEvent( | ||
new MessageEvent('message', { | ||
data: JSON.stringify(obj), | ||
source: window, | ||
}) | ||
); | ||
} | ||
}; | ||
|
||
const buildMockWindow = function (windowName) { | ||
windowName = windowName || ''; | ||
window.addEventListener('message', mockWindowListener); | ||
return { | ||
name: windowName, | ||
focus() {}, | ||
close() {}, | ||
open() { | ||
this.postMessage(expectedMessage); | ||
}, | ||
postMessage(msg) { | ||
window.dispatchEvent( | ||
new MessageEvent('message', { data: msg, source: window }) | ||
); | ||
}, | ||
}; | ||
}; | ||
|
||
const buildPopupIdGenerator = function (popupId) { | ||
return { | ||
generate() { | ||
return popupId; | ||
}, | ||
}; | ||
}; | ||
|
||
let Popup = EmberObject.extend(Evented, UiServiceMixin, { | ||
// Open a popup window. | ||
openRemote(_url, pendingRequestKey) { | ||
this.remote = buildMockWindow(pendingRequestKey); | ||
this.remote.open(); | ||
}, | ||
|
||
closeRemote() { | ||
this.remote.closed = true; | ||
}, | ||
|
||
pollRemote() { | ||
if (!this.remote) { | ||
return; | ||
} | ||
}, | ||
}); | ||
|
||
let popup; | ||
|
||
hooks.beforeEach(function () { | ||
popup = Popup.create({ remoteIdGenerator: buildPopupIdGenerator(popupId) }); | ||
localStorage.removeItem(CURRENT_REQUEST_KEY); | ||
}); | ||
|
||
hooks.afterEach(async function () { | ||
localStorage.removeItem(CURRENT_REQUEST_KEY); | ||
window.open = originalWindowOpen; | ||
window.removeEventListener('message', mockWindowListener); | ||
popup.destroy(); | ||
}); | ||
|
||
test('requests pending request key', function (assert) { | ||
assert.expect(1); | ||
|
||
let resultMessage; | ||
const resultMessageListener = (event) => { | ||
resultMessage = event.data; | ||
}; | ||
try { | ||
window.addEventListener('message', resultMessageListener); | ||
|
||
popup.openRemote(expectedUrl, CURRENT_REQUEST_KEY); | ||
|
||
assert.strictEqual( | ||
resultMessage, | ||
expectedMessage, | ||
'requests pendingRequestKey' | ||
); | ||
} finally { | ||
window.removeEventListener('message', resultMessageListener); | ||
} | ||
}); | ||
|
||
test('returns data after receiving key', async function (assert) { | ||
const keys = ['redirect_url']; | ||
const result = await popup.open(expectedUrl, keys); | ||
|
||
assert.strictEqual( | ||
result.redirect_url, | ||
expectedRedirectUrl, | ||
'returns data successfully' | ||
); | ||
}); | ||
}); |
Uh oh!
There was an error while loading. Please reload this page.