Simple analysis of post requests implemented with yii helpers Html class and yii.js of yii2

Keywords: PHP JQuery JSON Attribute

Yii2 provides many helpful classes, such as Html, Url, Json, etc., which can easily implement some functions. Let's briefly talk about this Html. It's often used when you write a view with yii2, and it's used today when you rewrite a page. The advantage of it is that it not only generates a simple HTML tag, but also realizes a post request with yii2's own static resource file yii.js.

Yii2 encapsulates all these functions, as long as it calls its method in the right place. It can be said that yii2 is an out-of-the-box framework. You can use it to quickly implement a required function: for example, to place a delete button in the page, click the button to send a post request, and pop up the confirmation dialog box. If you don't have yii helpers Html classes and yii.js, then you need to write a lot of js/jquery to implement this function. If you use yii2, the following code can be implemented:

 1 // html Code
 2 <?= Html::a(
 3     'delete',
 4     [
 5         'delete',
 6         'id' => $id,
 7     ],
 8     [
 9         'data' => [
10             'confirm' => 'Are you sure you want to delete it?',
11             'method' => 'post',
12         ],
13     ]
14 )
15 ?>
16 // html Code

It generates the following html code in the page:

<a href="delete?id=1" data-confirm="Are you sure you want to quit?" data-method="post">delete</a>

Clicking this button will pop up a dialog box, confirming the deletion will send a post request. So how did the post request be sent? So far, a piece of js code has not been written.

The yii2 framework hides the details of technology implementation, and the post request is implemented in yii.js. In yii.js, the window.yii object is defined and the initModule method of window.yii object is initialized:

window.yii = (function ($) {
    var pub = {
        // Defines how to handle events, such as the following:
        confirm: function (message, ok, cancel) {
            if (window.confirm(message)) {
                !ok || ok();
            } else {
                !cancel || cancel();
            }
        },

        handleAction: function ($e, event) {
            var $form = $e.attr('data-form') ? $('#' + $e.attr('data-form')) : $e.closest('form'),
            method = !$e.data('method') && $form ? $form.attr('method') : $e.data('method'),

            // Other omissions

        },

        // Other omissions

    };
    // Initialization module
    initModule: function (module) {
        if (module.isActive !== undefined && !module.isActive) {
            return;
        }
        if ($.isFunction(module.init)) {
            module.init();
        }
        $.each(module, function () {
            if ($.isPlainObject(this)) {
                pub.initModule(this);
            }
        });
    },

    // Initialization method
    init: function () {
        initCsrfHandler();
        initRedirectHandler();
        initAssetFilters();
        initDataMethods();
    },

    return pub;
})(window.jQuery);

window.jQuery(function () {
    window.yii.initModule(window.yii);
});

The initDataMethods() above calls the pub.handleAction method:

    function initDataMethods() {
        var handler = function (event) {
            var $this = $(this),
                method = $this.data('method'),
                message = $this.data('confirm'),
                form = $this.data('form');

            if (method === undefined && message === undefined && form === undefined) {
                return true;
            }

            if (message !== undefined) {
                $.proxy(pub.confirm, this)(message, function () {
                    pub.handleAction($this, event);
                });
            } else {
                pub.handleAction($this, event);
            }
            event.stopImmediatePropagation();
            return false;
        };

        // handle data-confirm and data-method for clickable and changeable elements
        $(document).on('click.yii', pub.clickableSelector, handler)
            .on('change.yii', pub.changeableSelector, handler);
    }

You can see that this method takes the data attribute value of the tag a generated above and handles it to handlerAction. Handler Action handles various requests by dynamically generating a form, and finally submits them by triggering submit events.

// Other omissions

$form = $('<form/>', {method: method, action: action});
var target = $e.attr('target');
if (target) {
    $form.attr('target', target);
}
if (!/(get|post)/i.test(method)) {
    $form.append($('<input/>', {name: '_method', value: method, type: 'hidden'}));
    method = 'post';
    $form.attr('method', method);
}
if (/post/i.test(method)) {
    var csrfParam = pub.getCsrfParam();
    if (csrfParam) {
        $form.append($('<input/>', {name: csrfParam, value: pub.getCsrfToken(), type: 'hidden'}));
    }
}
$form.hide().appendTo('body');

// Other omissions

 

PS: It's very convenient to use the framework for projects, but it's easy to forget the basic technology after using the framework for a long time. Still need to lay a good foundation, so no matter what framework is used, it will not be used in the clouds.

 

finish

Posted by eojlin on Wed, 26 Dec 2018 10:21:06 -0800