Moves closure sha384 into a new extension amp-crypto-polyfill for lazy load#7006
Moves closure sha384 into a new extension amp-crypto-polyfill for lazy load#7006lannka merged 6 commits intoampproject:masterfrom
Conversation
| dev().error(TAG, FALLBACK_MSG, e); | ||
| } | ||
| return this.loadPolyfill_() | ||
| .then(polyfill => polyfill.sha384(input)); |
There was a problem hiding this comment.
Can we call this.sha384(input) instead? The correct polyfill method is already codified above.
There was a problem hiding this comment.
that will not work. we need to call loadPolyfill here otherwise this.polyfillPromise_ is null forever
There was a problem hiding this comment.
Yah, but the then block doesn't need to know about polyfill#sha384.
return this.loadPolyfill_().then(this.sha384(input));| }); | ||
| } catch (e) { | ||
| dev().error(TAG, FALLBACK_MSG, e); | ||
| return this.loadPolyfill_().then(polyfill => polyfill.sha384(input)); |
| if (this.polyfillPromise_) { | ||
| return this.polyfillPromise_; | ||
| } | ||
| return this.polyfillPromise_ = extensionsFor(this.win_) |
There was a problem hiding this comment.
Need to add the polyfillPromise_ property in the constructor, regardless of subtle_.
| */ | ||
| sha384Base64(input) { | ||
| return this.sha384(input).then(buffer => { | ||
| return lib.base64(buffer); |
There was a problem hiding this comment.
Can we please drop the base64 stuff from the library?! 😋
There was a problem hiding this comment.
done. but no size change.
There was a problem hiding this comment.
Really? Does sha384 internally depend on it?
There was a problem hiding this comment.
Ohh, we might have to update https://github.com/ampproject/amphtml/blob/fa5c6cc7a9a78802bc816b6a986543420d90917f/third_party/closure-library/compile.sh, too.
There was a problem hiding this comment.
yep, i've updated it already. did you see anything else i can strip off?
There was a problem hiding this comment.
Oh perfect, not sure how I missed that.
| import * as lib from '../../../third_party/closure-library/sha384-generated'; | ||
|
|
||
| // Register doc-service factory. | ||
| AMP.registerServiceForDoc( |
There was a problem hiding this comment.
Should we just do window-singleton service instead? It really always window-scoped, right? Just as WebCrypto itself...
There was a problem hiding this comment.
Small correction:
installCryptoPolyfill(window);
->
installCryptoPolyfill(AMP.win);
| } | ||
| // polyfill is (being) loaded, | ||
| // means native Crypto API is not available or failed before. | ||
| if (this.polyfillPromise_) { |
There was a problem hiding this comment.
This var should be defined in the constructor.
| /** @private @const {?webCrypto.SubtleCrypto} */ | ||
| this.subtle_ = getSubtle(win); | ||
|
|
||
| /** @private {!Window} */ |
| @@ -28,6 +30,13 @@ export class Crypto { | |||
| constructor(win) { | |||
| import * as lib from '../../../third_party/closure-library/sha384-generated'; | ||
| import {fromClass} from '../../../src/service'; | ||
| import {dev} from '../../../src/log'; | ||
| import {getExistingServiceForWindow} from '../../../src/service'; |
There was a problem hiding this comment.
So, this module now just needs to go to the src/, right?
There was a problem hiding this comment.
@keithwrightbos has a pending PR to do that. Tests updated.
| } | ||
| try { | ||
| return this.subtle_.digest({name: 'SHA-384'}, | ||
| input instanceof Uint8Array ? input : stringToBytes(input)) |
There was a problem hiding this comment.
Should this be the other way: if (typeof input == 'string') ? stringToBytes(input) : input?
| try { | ||
| return this.subtle_.digest({name: 'SHA-384'}, | ||
| input instanceof Uint8Array ? input : stringToBytes(input)) | ||
| // [].slice.call(Unit8Array) is a shim for Array.from(Unit8Array) |
| } | ||
| return this.polyfillPromise_ = extensionsFor(this.win_) | ||
| .loadExtension('amp-crypto-polyfill') | ||
| .then(() => getExistingServiceForWindow(this.win_, 'crypto-polyfill')); |
There was a problem hiding this comment.
You already lookup window-scoped service, so it should definitely be window-scoped in the polyfill itself.
|
|
||
| /** | ||
| * Loads Crypto polyfill library. | ||
| * @returns {!Promise} |
There was a problem hiding this comment.
This should be !Promise<????> since you are using response of this promise everywhere.
There was a problem hiding this comment.
Not seeing changes here. Did you push?
Also, it should be @return (no "s")
There was a problem hiding this comment.
obviously i lied. done now.
lannka
left a comment
There was a problem hiding this comment.
Comments addressed. PTAL
| import * as lib from '../../../third_party/closure-library/sha384-generated'; | ||
| import {fromClass} from '../../../src/service'; | ||
| import {dev} from '../../../src/log'; | ||
| import {getExistingServiceForWindow} from '../../../src/service'; |
There was a problem hiding this comment.
@keithwrightbos has a pending PR to do that. Tests updated.
| @@ -28,6 +30,13 @@ export class Crypto { | |||
| constructor(win) { | |||
| /** @private @const {?webCrypto.SubtleCrypto} */ | ||
| this.subtle_ = getSubtle(win); | ||
|
|
||
| /** @private {!Window} */ |
| } | ||
| // polyfill is (being) loaded, | ||
| // means native Crypto API is not available or failed before. | ||
| if (this.polyfillPromise_) { |
| try { | ||
| return this.subtle_.digest({name: 'SHA-384'}, | ||
| input instanceof Uint8Array ? input : stringToBytes(input)) | ||
| // [].slice.call(Unit8Array) is a shim for Array.from(Unit8Array) |
|
|
||
| /** | ||
| * Loads Crypto polyfill library. | ||
| * @returns {!Promise} |
| if (this.polyfillPromise_) { | ||
| return this.polyfillPromise_; | ||
| } | ||
| return this.polyfillPromise_ = extensionsFor(this.win_) |
| } | ||
| return this.polyfillPromise_ = extensionsFor(this.win_) | ||
| .loadExtension('amp-crypto-polyfill') | ||
| .then(() => getExistingServiceForWindow(this.win_, 'crypto-polyfill')); |
| import * as lib from '../../../third_party/closure-library/sha384-generated'; | ||
|
|
||
| // Register doc-service factory. | ||
| AMP.registerServiceForDoc( |
| * Input string cannot contain chars out of range [0,255]. | ||
| * @param {string|!Uint8Array} input | ||
| * @returns {!Promise<!Array<number>>} | ||
| * @returns {!Promise<!Uint8Array>} |
| } catch (e) { | ||
| dev().error(TAG, FALLBACK_MSG, e); | ||
| } | ||
| if (!(input instanceof Uint8Array)) { |
There was a problem hiding this comment.
We are usually careful with instanceof b/c of different window contexts. E.g. window.UInt8Array vs embedWin.UInt8Array. Is this not a concern here?
/cc @jridgewell
There was a problem hiding this comment.
Friendly Frames are the only thing that can violate that, right? We can do a !input.buffer check instead.
There was a problem hiding this comment.
Correct. Only friendly iframes.
There was a problem hiding this comment.
hi gentlemen, what is this?
Uint8Array can be different across windows in same browser?
There was a problem hiding this comment.
Each window has its own instance of the generic classes, take String for instance. Now, when we create an iframe, it gets its own window and its own String. If we compare, they are not equivalent:
window.String === iframe.contentWindow.String; // => falseSince instanceof looks for object equality in the prototype chain, this also breaks across iframe boundaries:
iframe.contentWindow.uint8instance instanceof Uint8Array; // => false
uint8instance instanceof iframe.contentWindow.Uint8Array; // => falseThere was a problem hiding this comment.
wow. thanks!
will change to typeof input === "string"
|
@lannka Couple more comments, but otherwise LGTM. |
* master: (310 commits) Update csa.md to remove non-required parameters (ampproject#6902) Add notes about requesting ads ATF and link to demo (ampproject#7037) Remove whitelist for lightbox scrollable validator (ampproject#7034) Delegate submit events until amp-form is loaded (ampproject#6929) Moves closure sha384 into a new extension amp-crypto-polyfill for lazy load (ampproject#7006) Refactor observables in viewer-impl into a map object (ampproject#7004) resizing of margins (ampproject#6824) Use URL replacer from embed for pixel (ampproject#7029) adds support for Gemius analytics (ampproject#6558) Avoid duplicating server-layout (ampproject#7021) Laterpay validator config (ampproject#6974) Validator rollup (ampproject#7023) skeleton for amp-tabs (ampproject#7003) Upgrade post-css and related packages to latest (ampproject#7020) handle unload (ampproject#7001) viewer-integr.js -> amp-viewer-integration (ampproject#6989) dev().info()->dev().fine() (ampproject#7017) Turned on experiment flag (ampproject#6774) Unlaunch ios-embed-wrapper for iOS8 to avoid scroll freezing issues (ampproject#7018) Add some A4A ad request parameters (ampproject#6643) ...
…y load (ampproject#7006) * Moves closure sha384 into a new extension amp-crypto-polyfill for lazy load. * fix * Update tests. Remove base64 polyfill from lib. * Fix presubmit * Address comments * Fix test.
…y load (ampproject#7006) * Moves closure sha384 into a new extension amp-crypto-polyfill for lazy load. * fix * Update tests. Remove base64 polyfill from lib. * Fix presubmit * Address comments * Fix test.
This PR introduces our first "lib-like" extension
amp-crypto-polyfill.Part of #4898
/cc @keithwrightbos This should unblock your refactoring in #6837