There is a problem with form_example_tutorial_8, the multistep example.

This form does not seem to remember page 2 values when you hit the Back button.

I looked at the back handler (snippet below) and it is definitely trying to record the values, but when I dump the $form_state['values'] there is no reference to any form elements other than the submit buttons...

function form_example_tutorial_8_page_two_back($form, &$form_state) {
  $form_state['page_values'][2] = $form_state['values'];
  ...

I don't know if this a bug in D7, could be I guess. So marking this major for review.

Comments

rfay’s picture

When you do a back button any more, you have to either use #limit_validation_errors() or validate the data in the form before going back. If I remember right in this case we throw away the data. That said, thanks for the bug report and I'll look at it more closely later.

sime’s picture

Priority: Major » Normal

Thanks for your response Randy. When you say "we throw away the data", are you referring to the example form or to drupal core? I don't see where it would be happening in the example form and I don't see how Drupal knows the difference between the back/next/submit buttons.

FWIW, I played around with lots of variations based on your advice but was no successful.

I note that the values are in there in $form_state['input']. I've been trying to google for documentation about 'limit', but with no luck. I am considering just copying over these values into $form_state['page_values'][2] to make my own form work but I assume this is somewhat of a hack.

sime’s picture

Category: bug » task
Status: Active » Needs review

Ok, I worked it out.

The reason I was confused is that in form_example_tutorial_8_next_submit() the page 2 values are stored as if they will be retained. But storing these values is completely redundant for the reasons you say. Maybe add some comments like this?

<?php
function form_example_tutorial_8_next_submit($form, &$form_state) {
...
  // This won't actually work for any fields that have #limit_validation_errors set
  // because Drupal has destroyed the $form_state values that haven't been validated.
  // To make page 2 remember "color" setting after going Back, remove #limit_validation_errors
  // and remove '#required' => TRUE, on the color element.
  if (!empty($form_state['page_values'][2])) {
    $form_state['values'] = $form_state['page_values'][2];
  }
...
}
?>

For other people reading this, the related Drupal core code is in form.inc drupal_validate_form():

<?php
  // If validation errors are limited then remove any non validated form values,
  // so that only values that passed validation are left for submit callbacks.
  if (isset($form_state['triggering_element']['#limit_validation_errors']) && $form_state['triggering_element']['#limit_validation_errors'] !== FALSE) {
  ...
?>
rfay’s picture

Status: Needs review » Active

Thanks for your participation here, @sime.

Just FYI, you put an issue in "Needs review" when you have a patch attached.

Do you want to submit a patch that expresses what you want to fix?

rfay’s picture

Status: Active » Needs review
StatusFileSize
new1.43 KB

In #3 I think you showed changes that you intended to put in form_example_tutorial_8_back_submit() in form_example_tutorial_8_page_two_back().

The final reality in the D7 FAPI is that form values have to be either validated or they have to be discarded (which is what happens with #limit_validation_errors = array()). So in the case of a simple back button, discarding is probably the best option, as shown here.

Note that the form_example_wizard.inc goes into a much more extensive discussion of how to do this. Would appreciate your review of that as well.

Here's my patch based on your suggestions.

sime’s picture

Status: Needs review » Reviewed & tested by the community

Hi rfay, I think those changes would be great, and would help avoid confusion for future trekkers.

(Sorry, I didn't know about the "needs review" being for patches only.)

sime’s picture

Regarding the Needs Review, it's a bit confusing to be honest. There is no other way to suggest a maintainer should consider a solution! Needs Review is used for non-patch solutions in the, for example, the Webmaster queue all the time.

ilo’s picture

Title: multistep Back button missing form_state['values'] » Form tutorial back button discards step 2 values.
Status: Reviewed & tested by the community » Fixed

Thank you both! Committed as: http://drupal.org/cvs?commit=469696

Does this need to be back ported?

rfay’s picture

I don't believe this needs a backport, as the change here was caused by the very-D7 #limit_validation_errors = array().

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.