HOWTO: Submit a Form with AHAH in Drupal 6

Dynamic form extension and validation with AHAH is quite easy in Drupal 6; form submission via AHAH on the other hand is less trivial. If you're familiar with AHAH Dynamic Form Extension then this article should fill in the missing details - this example deals with submitting a custom content type:

 

Step 1: Set up callbacks for button click and (optionally) form validation:

 

function MYMODULE_form_alter (&$form, $form_state, $form_id){
   switch ($form_id) {

   case 'MYFORM_node_form':


      $form['buttons']['submit']['#ahah'] = array(
         'event' => 'click',
         'path' => 'MYCALLBACK/submit',
         'wrapper' => 'submit-feedback');
         $form['#validate'][] = 'MYFORM_validation';
   break;
   }
}
 
Step 2: Set up menu callback and point it to MYMODULE_submit (described elsewhere).
 
Step 3: Handle form submission in MYMODULE_submit:
 
function MYMODULE_submit() {
   // include node definition
   module_load_include('inc', 'node', 'node.pages');
   // load form
   $form_state = array('storage' => NULL, 'submitted' => FALSE);
   $form_build_id = $_POST['form_build_id'];
   $form = form_get_cache($form_build_id, $form_state);
   $args = $form['#parameters'];
   $form_id = array_shift($args);
   $form_state['post'] = $form['#post'] = $_POST;
   $form['#programmed'] = $form['#redirect'] = FALSE;
   // Process the form with drupal_process_form(), which calls the submit handlers that put whatever was worthy of keeping in the $form_state
   drupal_process_form($form_id, $form, $form_state);
   if ($error = form_get_errors()){
      $output = implode($error);
      // since there were errors, drupal_process_form has done its job. No need to rebuild $form.
      // Session messages would get displayed at the next regular request, but we're in AHAH here, so that won't happen. Make them go away.
      unset($_SESSION['messages']);
   }
   else {
      $message = drupal_get_messages('status');
      $output = $message['status']['0']; // you might want more than one status message
      // everything has been submitted in drupal_process_form, so $form has to be rebuilt
      $form = drupal_rebuild_form($form_id, $form_state, $args, $form_build_id);
      unset($_SESSION['messages']); // same as above
   }
   drupal_json(array('status' => TRUE, 'data' => $output));
}
 

Step 4: Optionally handle validation in MYFORM_validation:

 

function MYFORM_validation(&$form, &$form_state) {
  if ($form_state['values']['SOMEFIELD'] == '') {
    form_set_error('', t('SOMEFIELD must not be empty.'));
  }
}
 

Now you have an AHAH enabled submit form which (as an added bonus) will degrade gracefully in presence of non-Javascript enabled browsers (they still exist?).

 

Alternatively you could use the AHAH Helper Module I've been told (haven't tried it out though). Or wait for the release of Drupal 7, where stuff like this ought to be easier.

Really helpful

I was strugling for 2 days to figure out how to give to a node submit button this exact ahah behavior.

It was really helpful, worked like a charm.

Thanx for this great post.