2010-02-02 4 views
2

J'ai un formulaire qui est ajouté via le nodeapi affiché uniquement en mode d'affichage. Les utilisateurs peuvent sélectionner un élément dans un menu de sélection et leur choix sera automatiquement enregistré dans la base de données avec un rappel hook_menu en cas de modification. Si l'utilisateur a javascript désactivé, il va normalement soumettre avec le formulaire api. Tout cela fonctionne très bien, mais maintenant, pour des raisons de sécurité, je veux aussi soumettre la version ajax via le formulaire api. Mon form_name_submit est simple comme:Aide avec le rappel ajax et drupal_process_form

function mymodule_test_form_submit($form, &$form_state) { 
    global $user; 
    db_query("INSERT INTO {mymodule} (nid, uid, status, created) VALUES (%d, %d, %d, " . time() . ")", $form['#parameters'][2], $user->uid, $form_state['values']['mymodule_status']); 
} 

Mon ajax:

$('.mysubmit').css('display', 'none'); 
$('.myclass').change(function() { 
    $.ajax({ 
    type: 'POST', 
    url: Drupal.settings.basePath + 'mymodule/set/' + $nid + '/' + $('.myclass').val(), 
    dataType: 'json', 
    data: { 'ajax' : true, 'form_build_id' : $('#mymodule-form input[name=form_build_id]').val() } 
    }); 
}); 

Et ma fonction de rappel:

function mymodule_set($nid, $status) { 
    $form_build_id = $_POST['form_build_id']; 
    $form_state = array('storage' => NULL, 'submitted' => FALSE); 
    $form = form_get_cache($form_build_id, $form_state); 
    $args = $form['#parameters']; 
    $form_id = array_shift($args); 
    $form['#post'] = $_POST; 
    $form['#redirect'] = FALSE; 
    $form['#programmed'] = FALSE; 
    $form_state['post'] = $_POST; 
    drupal_process_form($form_id, $form, $form_state); 
} 

origine ma fonction de rappel était à peu près la même chose que ma fonction d'envoi, mais maintenant J'essaie d'utiliser la fonction submit avec ajax aussi. Est-ce la bonne façon d'utiliser drupal_process_form? Le formulaire est saisi à partir du cache, il est validé et soumis si aucune erreur? J'utilise du code de ce tutoriel pour m'appliquer à ma situation: http://drupal.org/node/331941 Il ne semble y avoir aucun exemple de ce que j'essaie de faire. J'ai aussi $ form ['# cache'] = TRUE; dans ma fonction de forme.

Comment drupal_process_form compare les valeurs soumises avec le formulaire d'origine pour vérifier l'intégrité? Suis-je censé ajouter mes valeurs à l'état form_state puisque l'état du formulaire sera vide avec ajax. Été bloqué sur cela pendant quelques jours, j'espère que quelqu'un a de l'expérience avec cela.

Merci.

Répondre

1

Je devais faire quelque chose similaire à vous dans le passé et lire le même tutoriel que vous avez posté, malheureusement il n'y a pas beaucoup d'informations disponibles à ce sujet et j'ai eu mal à la tête pour le faire fonctionner. Je ne me souviens pas bien les détails, mais je prenais un coup d'œil au code que j'ai écrit et voici quelques suggestions qui peuvent travailler pour vous:

Si vous faites cela sous une forme de nœud, en ajoutant la propriété #ahah sous une forme Je ne me souviens pas avoir vu un problème à ce sujet qui n'a pas été résolu à ce moment-là. Si tel est le cas, utilisez ce code pour attacher la liaison ahah, vous n'aurez pas besoin de "efect", "method" ou "progress" puisque vous voulez simplement soumettre le formulaire, ne rien changer:

function YOURMODULE_form_alter(&$form, $form_state, $form_id) { 
    if ('YOURCONTENTTYPE_node_form' == $form_id) { 
    //the only way I could make it work for exisiting fields is adding the binding "manually" 
    $ahah_binding = array(
     'url' => url('YOURCALLBACKPATH'), 
     'event' => 'change', 
     'wrapper' => 'FIELD-wrapper', 
     'selector' => '#FIELD', 
     'effect' => 'fade', 
     'method' => 'replace', 
     'progress' => array('type' => 'throbber'), 
    ); 

    drupal_add_js('misc/jquery.form.js'); 
    drupal_add_js('misc/ahah.js'); 
    drupal_add_js(array('ahah' => array('FIELDd' => $ahah_binding)), 'setting'); 

    //force the form to be cached 
    $form['#cache'] = TRUE; 
    } 
} 
  • Voici ma fonction de rappel, notez qu'il a quelques modifications du tutoriel que vous avez posté:

    function YOURMODULE_js() { 
    
        // The form is generated in an include file which we need to include manually. 
        include_once 'modules/node/node.pages.inc'; 
        // We're starting in step #3, preparing for #4. 
        //I have to add the 'rebuild' element, if not an empty node was created 
        $form_state = array('storage' => NULL, 'submitted' => FALSE, 'rebuild' => TRUE); 
        $form_build_id = $_POST['form_build_id']; 
        // Step #4. 
        $form = form_get_cache($form_build_id, $form_state); 
    
        // Preparing for #5. 
        $args = $form['#parameters']; 
        $form_id = array_shift($args); 
        $form_state['post'] = $form['#post'] = $_POST; 
        $form['#programmed'] = $form['#redirect'] = FALSE; 
    
        // if you want to do any modification to the form values, this is the place 
    
        // Step #5. 
        drupal_process_form($form_id, $form, $form_state); 
        // Step #6 and #7 and #8. 
        $form = drupal_rebuild_form($form_id, $form_state, $args, $form_build_id); 
    
    
        // Final rendering callback. 
        drupal_json(array('status' => TRUE, 'data' => $output)); 
    } 
    

Comme je l'ai dit il y a des détails que je l'ai oublié l'mais peut-être cette volonté T'aider.

Bonne chance.

+0

Merci d'avoir posté. Le formulaire est ajouté par nodeapi car je veux seulement que le formulaire apparaisse sur la vue du nœud. Je n'ai jamais fait d'AHAH auparavant, alors est-ce que j'utiliserais le même code de form_alter que vous avez posté? Je vais essayer de jouer avec ça maintenant ... – Wade

+0

Si le formulaire est un formulaire de noeud, alors le code que j'ai posté devrait fonctionner avec quelques petites modifications, la seule chose que je ne suis pas sûr à 100% est que drupal_process_form appellera la fonction submit automatiquement. – Flupkear

+0

Hmm, je ne vois aucune différence d'avant. Comment Drupal sait-elle réellement quelles sont les valeurs à comparer? Ou avez-vous besoin de les ajouter à l'état du formulaire? Si vous ne faites pas cela, l'état du formulaire ne sera pas vide, mais j'ai déjà essayé d'ajouter un tableau de valeurs à form_state, mais pas de différence. – Wade