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
Allow variable substitutions in hidden fields. #6130
Conversation
for (let i = 0; i < varSubsFields.length; i++) { | ||
const variable = varSubsFields[i].getAttribute('default-value'); | ||
varSubPromises.push( | ||
this.urlReplacement_.expandAsync(variable).then(value => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Careful, UrlReplacements
isn't a generic variable substitution library. I added an assert that the "protocol" of the url remains the same (because they were all URLs before now), but that doesn't apply here. So if the default value had something like RANDOM:X:Y
, this would break because of the changing "protocol".
We should split UrlReplacements into a core class (VarSubstitutions
?), and leave the URL specific code out of it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah that makes sense.
I can get started in moving VarSubstitutions
to a separate service. My guess is for any call to that service directly (outside of url-replacement-impl.js
) shouldn't allow URL replacements then?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My guess is for any call to that service directly (outside of url-replacement-impl.js) shouldn't allow URL replacements then?
Hm?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I meant to say that we'd need a way to prevent direct calls to var-sub service with a URL to avoid circumventing the protocol assert.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We can presubmit and whitelist Forms and UrlReplacements.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sent a PR #6257
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done.
* @private | ||
*/ | ||
waitOnPromisesOrTimeout_(promises, timeout) { | ||
return Promise.race( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Timer#timeoutPromise
takes a second "race" promise.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That one rejects though when timeout happens, I guess I could call the same callback in both then
and catch
clauses, or is there a better way to do this?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ahh, this is fine then.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ack
this.renderTemplate_(error.responseJson || {}); | ||
rethrowAsync('Form submission failed:', error); | ||
// Wait until all variables have been substituted or 100ms timeout. | ||
return this.waitOnPromisesOrTimeout_(varSubPromises, 100).then(() => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This changes the method signature from void return. Consider returning null
in other cases and updating return type to ?Promise
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Dropped this return since we don't use it.
// Wait until all variables have been substituted or 100ms timeout. | ||
return this.waitOnPromisesOrTimeout_(varSubPromises, 100).then(() => { | ||
if (isHeadOrGet) { | ||
xhrUrl = addParamsToUrl(this.xhrAction_, this.getFormAsObject_()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit: This would be more readable if xhrUrl
was declared closer to its usage and the isHeadOrGet
conditional wasn't duped below for body
. E.g.
let xhrUrl, body;
if (isHeadOrGet) {
xhrUrl = addParamsToUrl(this.xhrAction_, this.getFormAsObject_());
body = new FormData(this.form_);
} else {
xhrUrl = this.xhrAction_;
}
return this.xhr_.fetchJson(xhrUrl, {
body: body,
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
@@ -91,6 +99,7 @@ describe('amp-form', () => { | |||
sandbox.restore(); | |||
}); | |||
|
|||
// asd |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Typo?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Dropped
PTAL 👀 |
@choumx @jridgewell this is ready for another 👀 |
@@ -201,47 +210,86 @@ export class AmpForm { | |||
return; | |||
} | |||
|
|||
const isVarSubExpOn = isExperimentOn(this.win_, 'amp-form-var-sub'); | |||
// Fields that support var substitutions. | |||
const varSubsFields = !isVarSubExpOn ? [] : this.form_.querySelectorAll( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Flip please.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
Fix #5654