Branching via CJuiDialog entry

Okay, can someone tell me where the render for the second view goes in the following example (and why)? I just want to do a simple branching based on a value entered; according to the log, everything is good, but I don’t see the redirect rendered as expected…

Any corrections to my thinking appreciated! :)

Controller:




    public function actionFirst() {

        $this->render('first');

        Yii::trace('Info returned: ['.print_r($_POST,true).']', 'info');

        if (isset($_POST['val']) && ($_POST['val'] === 'ABC')) {

            Yii::trace('Match...', 'info');

            $this->redirect(array('test/second'));

        } else {

            Yii::trace('No match...', 'info');

        }

    }

    public function actionSecond() {

        $this->render('second');

    }



View ‘first’:




<?php

    echo '<h2>First</h2>';

    echo CHtml::button('Go',

        array(

        'style'=>'cursor: pointer;',

        'onclick'=>"{jQuery('#dialogTest').dialog('open');}"));

?>

 

<?php

    $this->beginWidget('zii.widgets.jui.CJuiDialog', array(

        'id'=>'dialogTest',

        'options'=>array(

            'title'=>'Test',

            'autoOpen'=>false,

            'modal'=>true,

            'width'=>300,

            'height'=>100,

        ),

    ));

    echo CHtml::label('Enter value:', "val");

    echo CHtml::textField('val');

    $this->endWidget('zii.widgets.jui.CJuiDialog');

?>

 

<script type="text/javascript">

jQuery(document).ready(function() {

    jQuery("input").bind("keydown", function(e) {

        if ((e.which && e.which == 13) || (e.keyCode && e.keyCode == 13)) {

            e.preventDefault();

            <?php echo CHtml::ajax(array(

                'url'=>array('test/first'),

		'data'=>'js:{val: jQuery("#val").val()}',

                'type'=>'post',

                'dataType'=>'json',

            ))?>;

            jQuery('#dialogTest').dialog("close");

            return false;

        }

        return true;

    });

});

</script>



View ‘second’:




<h2>Second...</h2>

<p>Success!</p>



If you don’t have any sort of output buffering turned on then you cannot send headers (read redirect) after you have sent output (read render()).

You don’t want to do a render at the beginning of actionFirst if you’re going to be doing a redirect later.

Rewrite like this:


 public function actionFirst() {

        Yii::trace('Info returned: ['.print_r($_POST,true).']', 'info');

        if (isset($_POST['val']) && ($_POST['val'] === 'ABC')) {

            Yii::trace('Match...', 'info');

            $this->redirect(array('test/second'));

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

        } else {

            Yii::trace('No match...', 'info');

        }

        $this->render('first');

    }



Edit: You can omit the


            

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



line above, because it seems that Yii terminates the application by default on a redirect call. Which makes a lot of sense.

Thank you so much for the info and setting me back on track… :D

Still no joy. I corrected actionFirst to read as below, but the second page still doesn’t get presented. Am I still missing something?




    public function actionFirst() {

        Yii::trace('Info returned: ['.print_r($_POST,true).']', 'info');

	if (isset($_POST['val'])) {

            if ($_POST['val'] === 'ABC') {

                Yii::trace('Match...', 'info');

                $this->redirect(array('test/second'));

            } else {

                Yii::trace('No match...', 'info');

            }

        } else {

            $this->render('first');

        }

    }



You should probably try this out and see if it redirects correctly:




    public function actionFirst() {

        $this->redirect(array('test/second'));

    }



If this doesn’t work, it might be that you’re accidentally sending some whitespace out before you get to the redirect line. You could check the output for leading whitespace before the html generated by your controller.

To avoid leading whitespace, make sure all the pure php files you code start with <?php and contain no end tag.

http://framework.zend.com/manual/en/coding-standard.php-file-formatting.html

Hey zilles.

Yeah, that redirect works fine. In fact, for the regular case, I’m able to see that the render takes in all the info correctly and constructs good output, then calls echo. The only thing that doesn’t occur is the actual page update in the browser.

Sorry, this feels like a total newbie problem, but I’m at a loss… :-[

Yeah, I think I missed the important issue. Hopefully this will be more helpful:

If I’m reading your original code right, you’re calling this controller with an ajax call, so the redirect will get processed within the ajax call. So your server is returning the data from actionSecond, but the ajax is just throwing this data away.

You need to add either a ‘replace’, ‘update’, or ‘success’ option to your ajax call in order to do something with this output.

See the following documentation:

http://www.yiiframework.com/doc/api/1.1/CHtml#ajax-detail

http://api.jquery.com/jQuery.ajax/

Alternatively, move away from ajax and rewrite this as a form that simply submits an http post request. If you are planning on doing some server side processing and then redirecting the browser to another page there is no need to use ajax.

Thanks again zilles.

My intent was to capture some pieces of info via a CJuiDialog widget, then look at that info on the server side, process things accordingly, and redirect the user to an appropriate page. Not sure how I managed to mangle things up, but I think you’re right about ajax tossing out my page. After reading through the links you provided, I’m inclined to re-think my approach and move away from ajax, as you suggest, but I’ll tinker with it a bit to see if I can’t get a reasonable mechanism to work with the dialog thingy…

Cheers.