CSRF Token in Ajax Request - Codeigniter 4 and Datatables

CSRF Token in Ajax Request - Codeigniter 4 and Datatables

schwaluckschwaluck Posts: 103Questions: 27Answers: 1

Hello all,

I have the following problem: I am currently using Codeigniter 4 as a web framework and have activated the CSRF function here. But now I don't manage to send the csrf token with in the ajax request, so the access is forbidden (403 forbidden) every time the ajax request is performed.

My current code:

View:

                                    <div class="container">
                                        <div class="container1">
                                            <div class="row">
                                                <div class="col">
                                                    <table cellpadding="0" cellspacing="0" border="0" class="table table-striped" id="master_data_personal_data_categories" data-ajaxurl="<?= site_url('Master_Data_Personal_Data_Categories_Controller/ajax_add_edit'); ?>" width="100%">
                                                        <thead>
                                                            <tr class="table-design-1">
                                                                <th>Name</th>
                                                                <th>Beschreibung</th>
                                                                <th>Beispiele</th>
                                                            </tr>
                                                        </thead>
                                                        <tfoot>
                                                            <tr class="table-design-1">
                                                                <th>Name</th>
                                                                <th>Beschreibung</th>
                                                                <th>Beispiele</th>
                                                            </tr>
                                                        </tfoot>
                                                    </table>
                                                </div>
                                            </div>
                                        </div>
                                    </div>

JS:

(function($){
$(document).ready(function() {
    
    var csrfName = '<?= csrf_token() ?>';
    var csrfHash = '<?= csrf_hash() ?>';
    
    
    var _thisDatatable = $('#master_data_personal_data_categories');
    var editor = new $.fn.dataTable.Editor( {
        //ajax: _thisDatatable.attr('data-ajaxurl'),
        ajax: {
            url: _thisDatatable.attr('data-ajaxurl'),
            data: function (d) {
                d.csrfName = csrfHash;
            }
        },

I have also already tried to include the token as a meta tag in the HTML head and then query it as described in this post: https://datatables.net/forums/discussion/28125/send-csrf-token-with-datatable-ajax. However, that didn't work either.

Can someone maybe help me with that and explain what my mistake is?

Best regards
schwaluck

This question has an accepted answers - jump to answer

Answers

  • colincolin Posts: 15,142Questions: 1Answers: 2,586

    Have you seen the manual page discussing CSRF tokens? It's worth looking at other threads too, such as here, here and here. That last one is also Codeigniter.

    If no joy with those, could you link to your page, please, so we can take a look,

    Colin

  • schwaluckschwaluck Posts: 103Questions: 27Answers: 1
    edited February 2021

    Hi Colin,

    thanks for the feedback. I had already seen the posts, but unfortunately I didn't get much further through them. I have also already seen the documentation from you, which is why I tried to pass the token via "data" and also "headers" in the ajax options.

    I have now added the token again as a meta tag in the head. Then I have addressed the tag via Javascript and stored the contents (name and content) in two variables. I could display these values on the console, but when I try to include them in the ajax request, it still does not work.

    Code JS - First version:

    (function($){
    $(document).ready(function() {
        
        var meta = document.getElementsByTagName("meta")[0];
        
        var tokenName = meta.name;
        var tokenHash = meta.content;
        
        console.log(tokenName, tokenHash);
        
        var _thisDatatable = $('#master_data_personal_data_categories');
        var editor = new $.fn.dataTable.Editor( {
            //ajax: _thisDatatable.attr('data-ajaxurl'),
            ajax: {
                url: _thisDatatable.attr('data-ajaxurl'),
                data: function (d) {
                    d.tokenName = tokenHash;
                }
            },
    

    Code JS - Second version:

    (function($){
    $(document).ready(function() {
        
        var meta = document.getElementsByTagName("meta")[0];
        
        var tokenName = meta.name;
        var tokenHash = meta.content;
        
        console.log(tokenName, tokenHash);
        
        var _thisDatatable = $('#master_data_personal_data_categories');
        var editor = new $.fn.dataTable.Editor( {
            //ajax: _thisDatatable.attr('data-ajaxurl'),
            ajax: {
                url: _thisDatatable.attr('data-ajaxurl'),
                headers: {
                    tokenName : tokenHash
                    //'tokenName' : tokenHash
                }
            },
    

    So I assume that my problem is in the Ajax request, but unfortunately I don't know what I did wrong.
    Can you help me here?

  • schwaluckschwaluck Posts: 103Questions: 27Answers: 1
    edited February 2021

    UPDATE/SOLVED:

    I have now got it working. For all of you who might have the same problem, the following might help:

    In Codeigniter 4 you can disable the regeneration of the CSRF token on every request under app/Config/Security.php (see: https://codeigniter4.github.io/userguide/libraries/security.html).

    In my JS code I made the following adjustment:

    Note: Both ajaxSetup and ajaxPrefilter work and I used <?= csrf_meta() ?> to place the Token as the first meta tag in my html head.

    (function($){
    $(document).ready(function() {
        
        var meta = document.getElementsByTagName("meta")[0];
        
        var tokenHash = meta.content;
        
        $.ajaxPrefilter(function(options,originalOptions,jqXHR) {
            jqXHR.setRequestHeader('X-CSRF-Token', tokenHash);
        });
        /*$.ajaxSetup({
            headers: {
                'X-CSRF-Token' : tokenHash
            }
        });*/
        
        var _thisDatatable = $('#master_data_personal_data_categories');
        var editor = new $.fn.dataTable.Editor( {
            ajax: _thisDatatable.attr('data-ajaxurl'),
    

    Best regards
    schwaluck

  • colincolin Posts: 15,142Questions: 1Answers: 2,586
    edited March 2022 Answer ✓

    Excellent, good find - thanks for reporting back,

    Colin

  • JrengGoJrengGo Posts: 1Questions: 0Answers: 0

    Bro.. I help to solve the problem above. it's easy just see my post in pastebin link bellow. just follow step by step of my method.
    there are two link show data and update data using csrf datatable update generate true setting random token

    https://pastebin.com/kupzmyx3

    https://pastebin.com/tHhztmwc

  • VBoisdonVBoisdon Posts: 1Questions: 0Answers: 0

    If you don't want to disable the regeneration of the CSRF token on every request in order not to weaken your security, you can reset it after each ajax request.

    In the controller that handles the ajax, you generate a new CSRF that you return with the response to the ajax, and in the request callback you set the new CSRF for all the ajax of the page with this $.ajaxSettings.data.csrf_token = "testcsrf".

    I hope this helps someone,
    Vincent

Sign In or Register to comment.