Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(93)

Side by Side Diff: third_party/WebKit/Source/core/html/HTMLFormElement.cpp

Issue 2340213002: submit() in submit event handler should not contains a value of a submit button. (Closed)
Patch Set: Created 4 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) 2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
3 * (C) 1999 Antti Koivisto (koivisto@kde.org) 3 * (C) 1999 Antti Koivisto (koivisto@kde.org)
4 * (C) 2001 Dirk Mueller (mueller@kde.org) 4 * (C) 2001 Dirk Mueller (mueller@kde.org)
5 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009 Apple Inc. All rights reserv ed. 5 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009 Apple Inc. All rights reserv ed.
6 * (C) 2006 Alexey Proskuryakov (ap@nypop.com) 6 * (C) 2006 Alexey Proskuryakov (ap@nypop.com)
7 * 7 *
8 * This library is free software; you can redistribute it and/or 8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Library General Public 9 * modify it under the terms of the GNU Library General Public
10 * License as published by the Free Software Foundation; either 10 * License as published by the Free Software Foundation; either
(...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after
228 } 228 }
229 if (fromImplicitSubmissionTrigger) { 229 if (fromImplicitSubmissionTrigger) {
230 // Default (submit) button is not activated; no implicit submiss ion. 230 // Default (submit) button is not activated; no implicit submiss ion.
231 return; 231 return;
232 } 232 }
233 } else if (control->canTriggerImplicitSubmission()) { 233 } else if (control->canTriggerImplicitSubmission()) {
234 ++submissionTriggerCount; 234 ++submissionTriggerCount;
235 } 235 }
236 } 236 }
237 if (fromImplicitSubmissionTrigger && submissionTriggerCount == 1) 237 if (fromImplicitSubmissionTrigger && submissionTriggerCount == 1)
238 prepareForSubmission(event); 238 prepareForSubmission(event, nullptr);
239 }
240
241 // FIXME: Consolidate this and similar code in FormSubmission.cpp.
242 static inline HTMLFormControlElement* submitElementFromEvent(const Event* event)
243 {
244 for (Node* node = event->target()->toNode(); node; node = node->parentOrShad owHostNode()) {
245 if (node->isElementNode() && toElement(node)->isFormControlElement())
246 return toHTMLFormControlElement(node);
247 }
248 return 0;
249 } 239 }
250 240
251 bool HTMLFormElement::validateInteractively() 241 bool HTMLFormElement::validateInteractively()
252 { 242 {
253 UseCounter::count(document(), UseCounter::FormValidationStarted); 243 UseCounter::count(document(), UseCounter::FormValidationStarted);
254 const FormAssociatedElement::List& elements = associatedElements(); 244 const FormAssociatedElement::List& elements = associatedElements();
255 for (unsigned i = 0; i < elements.size(); ++i) { 245 for (unsigned i = 0; i < elements.size(); ++i) {
256 if (elements[i]->isFormControlElement()) 246 if (elements[i]->isFormControlElement())
257 toHTMLFormControlElement(elements[i])->hideVisibleValidationMessage( ); 247 toHTMLFormControlElement(elements[i])->hideVisibleValidationMessage( );
258 } 248 }
(...skipping 25 matching lines...) Expand all
284 if (unhandled->isFocusable()) 274 if (unhandled->isFocusable())
285 continue; 275 continue;
286 String message("An invalid form control with name='%name' is not foc usable."); 276 String message("An invalid form control with name='%name' is not foc usable.");
287 message.replace("%name", unhandled->name()); 277 message.replace("%name", unhandled->name());
288 document().addConsoleMessage(ConsoleMessage::create(RenderingMessage Source, ErrorMessageLevel, message)); 278 document().addConsoleMessage(ConsoleMessage::create(RenderingMessage Source, ErrorMessageLevel, message));
289 } 279 }
290 } 280 }
291 return false; 281 return false;
292 } 282 }
293 283
294 void HTMLFormElement::prepareForSubmission(Event* event) 284 void HTMLFormElement::prepareForSubmission(Event* event, HTMLFormControlElement* submitButton)
295 { 285 {
296 LocalFrame* frame = document().frame(); 286 LocalFrame* frame = document().frame();
297 if (!frame || m_isSubmitting || m_inUserJSSubmitEvent) 287 if (!frame || m_isSubmitting || m_inUserJSSubmitEvent)
298 return; 288 return;
299 289
300 if (document().isSandboxed(SandboxForms)) { 290 if (document().isSandboxed(SandboxForms)) {
301 document().addConsoleMessage(ConsoleMessage::create(SecurityMessageSourc e, ErrorMessageLevel, "Blocked form submission to '" + m_attributes.action() + " ' because the form's frame is sandboxed and the 'allow-forms' permission is not set.")); 291 document().addConsoleMessage(ConsoleMessage::create(SecurityMessageSourc e, ErrorMessageLevel, "Blocked form submission to '" + m_attributes.action() + " ' because the form's frame is sandboxed and the 'allow-forms' permission is not set."));
302 return; 292 return;
303 } 293 }
304 294
305 bool skipValidation = !document().page() || noValidate(); 295 bool skipValidation = !document().page() || noValidate();
306 DCHECK(event); 296 DCHECK(event);
307 HTMLFormControlElement* submitElement = submitElementFromEvent(event); 297 if (submitButton && submitButton->formNoValidate())
308 if (submitElement && submitElement->formNoValidate())
309 skipValidation = true; 298 skipValidation = true;
310 299
311 UseCounter::count(document(), UseCounter::FormSubmissionStarted); 300 UseCounter::count(document(), UseCounter::FormSubmissionStarted);
312 // Interactive validation must be done before dispatching the submit event. 301 // Interactive validation must be done before dispatching the submit event.
313 if (!skipValidation && !validateInteractively()) 302 if (!skipValidation && !validateInteractively())
314 return; 303 return;
315 304
316 bool shouldSubmit; 305 bool shouldSubmit;
317 { 306 {
318 AutoReset<bool> submitEventHandlerScope(&m_inUserJSSubmitEvent, true); 307 AutoReset<bool> submitEventHandlerScope(&m_inUserJSSubmitEvent, true);
319 frame->loader().client()->dispatchWillSendSubmitEvent(this); 308 frame->loader().client()->dispatchWillSendSubmitEvent(this);
320 shouldSubmit = dispatchEvent(Event::createCancelableBubble(EventTypeName s::submit)) == DispatchEventResult::NotCanceled; 309 shouldSubmit = dispatchEvent(Event::createCancelableBubble(EventTypeName s::submit)) == DispatchEventResult::NotCanceled;
321 } 310 }
322 if (shouldSubmit) { 311 if (shouldSubmit) {
323 m_plannedNavigation = nullptr; 312 m_plannedNavigation = nullptr;
324 submit(event, true); 313 submit(event, submitButton);
325 } 314 }
326 if (!m_plannedNavigation) 315 if (!m_plannedNavigation)
327 return; 316 return;
328 AutoReset<bool> submitScope(&m_isSubmitting, true); 317 AutoReset<bool> submitScope(&m_isSubmitting, true);
329 scheduleFormSubmission(m_plannedNavigation); 318 scheduleFormSubmission(m_plannedNavigation);
330 m_plannedNavigation = nullptr; 319 m_plannedNavigation = nullptr;
331 } 320 }
332 321
333 void HTMLFormElement::submitFromJavaScript() 322 void HTMLFormElement::submitFromJavaScript()
334 { 323 {
335 submit(0, false); 324 submit(nullptr, nullptr);
336 } 325 }
337 326
338 void HTMLFormElement::submitDialog(FormSubmission* formSubmission) 327 void HTMLFormElement::submitDialog(FormSubmission* formSubmission)
339 { 328 {
340 for (Node* node = this; node; node = node->parentOrShadowHostNode()) { 329 for (Node* node = this; node; node = node->parentOrShadowHostNode()) {
341 if (isHTMLDialogElement(*node)) { 330 if (isHTMLDialogElement(*node)) {
342 toHTMLDialogElement(*node).closeDialog(formSubmission->result()); 331 toHTMLDialogElement(*node).closeDialog(formSubmission->result());
343 return; 332 return;
344 } 333 }
345 } 334 }
346 } 335 }
347 336
348 void HTMLFormElement::submit(Event* event, bool activateSubmitButton) 337 void HTMLFormElement::submit(Event* event, HTMLFormControlElement* submitButton)
349 { 338 {
350 FrameView* view = document().view(); 339 FrameView* view = document().view();
351 LocalFrame* frame = document().frame(); 340 LocalFrame* frame = document().frame();
352 if (!view || !frame || !frame->page()) 341 if (!view || !frame || !frame->page())
353 return; 342 return;
354 343
355 // https://html.spec.whatwg.org/multipage/forms.html#form-submission-algorit hm 344 // https://html.spec.whatwg.org/multipage/forms.html#form-submission-algorit hm
356 // 2. If form document is not connected, has no associated browsing context, 345 // 2. If form document is not connected, has no associated browsing context,
357 // or its active sandboxing flag set has its sandboxed forms browsing 346 // or its active sandboxing flag set has its sandboxed forms browsing
358 // context flag set, then abort these steps without doing anything. 347 // context flag set, then abort these steps without doing anything.
359 if (!isConnected()) 348 if (!isConnected())
360 return; 349 return;
361 350
362 if (m_isSubmitting) 351 if (m_isSubmitting)
363 return; 352 return;
364 353
365 // Delay dispatching 'close' to dialog until done submitting. 354 // Delay dispatching 'close' to dialog until done submitting.
366 EventQueueScope scopeForDialogClose; 355 EventQueueScope scopeForDialogClose;
367 AutoReset<bool> submitScope(&m_isSubmitting, true); 356 AutoReset<bool> submitScope(&m_isSubmitting, true);
368 357
369 HTMLFormControlElement* firstSuccessfulSubmitButton = nullptr; 358 if (event && !submitButton) {
370 bool needButtonActivation = activateSubmitButton; // do we need to activate a submit button? 359 // In a case of implicit submission without a submit button, 'submit'
371 360 // event handler might add a submit button. We search for a submit
372 const FormAssociatedElement::List& elements = associatedElements(); 361 // button again.
373 for (unsigned i = 0; i < elements.size(); ++i) { 362 // TODO(tkent): Do we really need to activate such submit button?
374 FormAssociatedElement* associatedElement = elements[i]; 363 for (const auto& associatedElement : associatedElements()) {
375 if (!associatedElement->isFormControlElement()) 364 if (!associatedElement->isFormControlElement())
376 continue; 365 continue;
377 if (needButtonActivation) {
378 HTMLFormControlElement* control = toHTMLFormControlElement(associate dElement); 366 HTMLFormControlElement* control = toHTMLFormControlElement(associate dElement);
379 if (control->isActivatedSubmit()) 367 DCHECK(!control->isActivatedSubmit());
380 needButtonActivation = false; 368 if (control->isSuccessfulSubmitButton()) {
381 else if (firstSuccessfulSubmitButton == 0 && control->isSuccessfulSu bmitButton()) 369 submitButton = control;
382 firstSuccessfulSubmitButton = control; 370 break;
371 }
383 } 372 }
384 } 373 }
385 374
386 if (needButtonActivation && firstSuccessfulSubmitButton) 375 FormSubmission* formSubmission = FormSubmission::create(this, m_attributes, event, submitButton);
387 firstSuccessfulSubmitButton->setActivatedSubmit(true);
388
389 FormSubmission* formSubmission = FormSubmission::create(this, m_attributes, event);
390 if (formSubmission->method() == FormSubmission::DialogMethod) { 376 if (formSubmission->method() == FormSubmission::DialogMethod) {
391 submitDialog(formSubmission); 377 submitDialog(formSubmission);
392 } else if (m_inUserJSSubmitEvent) { 378 } else if (m_inUserJSSubmitEvent) {
393 // Need to postpone the submission in order to make this cancelable by 379 // Need to postpone the submission in order to make this cancelable by
394 // another submission request. 380 // another submission request.
395 m_plannedNavigation = formSubmission; 381 m_plannedNavigation = formSubmission;
396 } else { 382 } else {
397 // This runs JavaScript code if action attribute value is javascript: 383 // This runs JavaScript code if action attribute value is javascript:
398 // protocol. 384 // protocol.
399 scheduleFormSubmission(formSubmission); 385 scheduleFormSubmission(formSubmission);
400 } 386 }
401
402 if (needButtonActivation && firstSuccessfulSubmitButton)
403 firstSuccessfulSubmitButton->setActivatedSubmit(false);
404 } 387 }
405 388
406 void HTMLFormElement::scheduleFormSubmission(FormSubmission* submission) 389 void HTMLFormElement::scheduleFormSubmission(FormSubmission* submission)
407 { 390 {
408 DCHECK(submission->method() == FormSubmission::PostMethod || submission->met hod() == FormSubmission::GetMethod); 391 DCHECK(submission->method() == FormSubmission::PostMethod || submission->met hod() == FormSubmission::GetMethod);
409 DCHECK(submission->data()); 392 DCHECK(submission->data());
410 DCHECK(submission->form()); 393 DCHECK(submission->form());
411 if (submission->action().isEmpty()) 394 if (submission->action().isEmpty())
412 return; 395 return;
413 if (document().isSandboxed(SandboxForms)) { 396 if (document().isSandboxed(SandboxForms)) {
(...skipping 386 matching lines...) Expand 10 before | Expand all | Expand 10 after
800 { 783 {
801 for (const auto& control : associatedElements()) { 784 for (const auto& control : associatedElements()) {
802 if (!control->isFormControlElement()) 785 if (!control->isFormControlElement())
803 continue; 786 continue;
804 if (toHTMLFormControlElement(control)->canBeSuccessfulSubmitButton()) 787 if (toHTMLFormControlElement(control)->canBeSuccessfulSubmitButton())
805 toHTMLFormControlElement(control)->pseudoStateChanged(CSSSelector::P seudoDefault); 788 toHTMLFormControlElement(control)->pseudoStateChanged(CSSSelector::P seudoDefault);
806 } 789 }
807 } 790 }
808 791
809 } // namespace blink 792 } // namespace blink
OLDNEW
« no previous file with comments | « third_party/WebKit/Source/core/html/HTMLFormElement.h ('k') | third_party/WebKit/Source/core/html/forms/ImageInputType.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698