CActiveForm seems to be submitting form twice

Here is my config:




<?php $form = $this->beginWidget('CActiveForm', array(

	'id'=>'booking-form',

	'enableAjaxValidation'=>false,

	'enableClientValidation'=>true,

	'clientOptions'=>array(

		'validateOnChange'=>false,

		'validateOnSubmit'=>true,

	),

)); ?>


<?php echo CHtml::imageButton('images/confirmed-button.png', array('name'=>'confirmed', 'id'=>'confirmed-button')); ?>



And I have this custom handler:


$('#booking-form #confirmed-button').click(function(){

	return confirm("Mark as Confirmed?");

});

The alert confirm message appears twice when validation is successful.

Try something like this




$('#booking-form #confirmed-button').click(function(){

        var c = confirm("Mark as Confirmed?");

if(c){

//submit form, or whatever you want to do...

}

else{

return false;

}

});



I think the reason is that CActiveForm uses the click event of the submit button in order to submit the form if it validates. So this seems to happen:

  1. You click on submit => your dialog shows up

  2. JS validates attributes => valid

  3. JS creates a new click event for the submit button to actually submit the form now => confirm dialog shows up again

Maybe you could use the clientChange attribute of your imageButton in your htmlOptions to solve that. It is worth a try


<?php echo CHtml::imageButton('images/confirmed-button.png', array('name'=>'confirmed', 'id'=>'confirmed-button','confirm'=>'Mark as confirmed?')); ?>

Of course you will have to remove your custom js code above

That seemed like a possible solution, but unfortunately it does the same thing.

I’m surprised it’s mimicking a click on the submit button in order to submit the form. Surely it can just use form.submit()?

the problem, most likely is because in your controller, when you perform the ajax validation, you don’t compare $_GET[‘ajax’] to the right form id(which by default is the model class name).

So hint, take a look at this part in your controller:




if(isset($_GET['ajax']) && $_GET['ajax']==='YourModelNameHere'){

   echo CActiveForm::validate($model);

   Yii::app()->end();

}



The form ID is correct on my controller.

why don’t you post the controller and model, do you want us to guess the content of those files ?

I have posted the necessary code in my original post. Everything is correct, this seems to be an issue with how CActiveForm works.

yeah sure. good luck with that!

Anyone got any idea how to fix this?

did you check what twisted1919 wrote in #5 ?

Hi mdomba - yes I did check this. The problem also occurs when:


'enableAjaxValidation'=>false,

'enableClientValidation'=>true,

Even as you have enableClientValidation set to false… you still have validateOnSubmit set to true… so at that time an ajax() call is made… so you still need the serverside ajax validation handling.

Are you sure about that? I checked Firebug console and there is no ajax call made when enableClientValidation is true and validateOnSubmit is true.

Actually you are right… I just checked it and if enableAjaxValidation is disabled then no ajax calls are made…

As hansel posted in the comment #3 … if the validateOnSubmit is enabled… then the "click" on the submit button is intercepted to first validate all the fields… and then again a click() is invoked so that is the reason for the alert firing twice.

I see. So I assume it is just doing a ‘virtual’ click of the submit button to submit the form - can it not be changed so that it instead triggers the submit() event of the form?

changing this would break possible existing code that could rely on click() to be made.

So what can u suggest as a workaround for me?

you can use the afterValidate option of clientOptions - http://www.yiiframework.com/doc/api/1.1/CActiveForm#clientOptions-detail

but it all depends on your needs…

Hi Brother, I have this problem many times, and searching the answer didnt find anything to solve this.

I got help in forum thousand times, but myself never helped to people in forum, I am doing it first time :)

The problem is here, not in CActiveForm scripts, it in Yii scripts, that called jquery.yii.js.

You should find the method

$.yii = {

version : '1.0',





submitForm : function (element, url, params) {


	var f = &#036;(element).parents('form')[0];


	if (&#33;f) {


		f = document.createElement('form');


		f.style.display = 'none';


		element.parentNode.appendChild(f);


		f.method = 'POST';


	}

Here as you see, the scripts trying to find parent form element, if it exists, it will submit that form, if not, it will create new form.

I have overwrite this function,

dont search the form

var f = $(element).parents(‘form’)[0]; remove this line.

Allways use this way

var f = document.createElement(‘form’);

f.style.display = ‘none’;

element.parentNode.appendChild(f);

f.method = ‘POST’;

And you will never have problems like that. Wish you well. Hope you will thank me. :)