Queuing changes in Editor not working when Serverside is true

Queuing changes in Editor not working when Serverside is true

Khalid TeliKhalid Teli Posts: 251Questions: 71Answers: 0
edited October 2020 in Free community support

I ma using the example given in https://datatables.net/blog/2017-10-24#Multi-row-editing.
Everything works as expected when "serverSide": false and doesn't work when "serverSide": true

My code looks like this:

var editorOpts = {
    "table": "#mssr_list",
    "fields": [ {
        "label": "Product Code:",
        "name": "product_code_fk"
      } ,

      {
        "label": "Name:",
        "name": "m_1"
      } 
 ]
  } ;

   var changedRows = [];
  var localEditor = new $.fn.dataTable.Editor( editorOpts );

localEditor.on('postEdit', function (e, json, data) {
    changedRows.push( '#'+data.DT_RowId );

    tableone.buttons([3,4]).enable();
    console.log(changedRows);

});

    var ajaxEditor = new $.fn.dataTable.Editor( $.extend( true, {
         ajax: '../../controllers/xxx_fetch.php'
    }, editorOpts ) );


    var tableone = $('#mssr_list').DataTable( {

        "processing": true,
        "serverSide": true,
         "scrollY":"800px",
          "scrollX":"100%",
          "scrollCollapse": true,
          "ordering": [],
          "stateSave": false,
           "info":   true,
        "dom": 'lBrtip',
        "ajax":"../../controllers/xxx_fetch.php",

        "columns": [

      { data: "product_code_fk" },
      { data: "m_1"}

        ],

     select: true,
    buttons: [
            { extend: "create", editor: ajaxEditor },
            { extend: "edit", editor: localEditor },
            { extend: "remove", editor: ajaxEditor },
            {
                text: 'Save changes',
                init: function () {
                    this.disable();
                },
                action: function () {
                    ajaxEditor
                        .edit( changedRows, false )
                        .submit();

                    changedRows.length = 0;
                    tableone.buttons([3,4]).disable();
                }
            },
            {
                text: 'Discard changes',
                init: function () {
                    this.disable();
                },
                action: function () {
                    this.ajax.reload();

                    changedRows.length = 0;
                    tableone.buttons([3,4]).disable();
                }
            }
        ]

});

This question has an accepted answers - jump to answer

Answers

  • kthorngrenkthorngren Posts: 21,341Questions: 26Answers: 4,954
    edited October 2020

    Everything works as expected when "serverSide": false and doesn't work when "serverSide": true

    Please be more specific about the problem description.

    Kevin

  • Khalid TeliKhalid Teli Posts: 251Questions: 71Answers: 0
    edited October 2020

    @kthorngren
    sorry, if my question was not framed right.

    What I am saying is that, when I use the code given in the example above it works fine when working on client side, that is when in the datatales initialisation I make Server side: False
    .

    But as soon as I shift to server side processing by changing serverside:true the code doesn’t work.

  • kthorngrenkthorngren Posts: 21,341Questions: 26Answers: 4,954

    Saying it doesn't work doesn't give us any information to start helping.

    Do you get alert messages or errors in the browser's console?

    What are you using for your server side script?

    Does the problem happen when you click the "Save" button?

    Using the browser's network inspector tool what is sent to the server and what is the response?

    Or please post a link to your page or a running test case showing the issue so we can help debug.
    https://datatables.net/manual/tech-notes/10#How-to-provide-a-test-case

    Kevin

  • Khalid TeliKhalid Teli Posts: 251Questions: 71Answers: 0
    edited October 2020

    @kthorngren

    1)
    In the scenario 1 , where I use serverside:false. when is click the edit button , window pops up up and then I enter the fields and on clicking the update button inputted data gets displayed in table. And upon clicking the save button , the updated data gets send to the server which I confirmed using developer tool > network tab. Finally, the updated data gets saved in database and displayed in table

      Following Form data gets sent to server:  
        data[row_31][product_code_fk]: 17194
        data[row_31][m_1]: werrdf
        data[row_31][m_2]: 0
        data[row_31][m_3]: y
       ......
        data[row_31][m_12]: 1
        data[row_31][total_score]: 1
        data[row_31][execution]: 1
        action: edit
    

    2)** in the scenario 2: ** when I use serverside:true. when I click the edit button , window pops up up and then I enter the data in fields and on clicking the update button The form data that gets sent is shown below and the response is the data which was there before edit which then gets displayed in table:

        draw: 2
        columns[0][data]: product_code_fk
        columns[0][name]: 
        columns[0][searchable]: true
        columns[0][orderable]: true
        columns[0][search][value]: 
        columns[0][search][regex]: false
       ...........
        columns[16][data]: no_of_stock
        columns[16][name]: 
        columns[16][searchable]: true
        columns[16][orderable]: true
        columns[16][search][value]: 
        columns[16][search][regex]: false
        columns[17][data]: execution
        columns[17][name]: 
        columns[17][searchable]: true
        columns[17][orderable]: true
        columns[17][search][value]: 
        columns[17][search][regex]: false
        order[0][column]: 0
        order[0][dir]: asc
        start: 0
        length: 10
        search[value]: 
        search[regex]: false
    

    Both times it doesn't show any error in console window.

    My client side code looks like this:

    <?php
    session_start();
    // $_SESSION["username"] = "member" ;
      //$_SESSION["username"] = "supplier" ;
    $_SESSION["username"] = "crg" ;
    
    include('filter_sql.php');
    include('plugins.php');
    ?>
    
    <!DOCTYPE html>
    <html>
    <head>
      <title>Promotion Forms</title>
    <link rel="stylesheet" href="style.css">
    
    </head>
    
    <body >
    
    <br>
    
    </div>
    </div>
      <div class="input-daterange input-group" id="report-date-filter">
           <input id="start_date" type="text" class="input-sm form-control" placeholder="Start Date" name="start_date" autocomplete="off">
           <span class="input-group-addon btn btn-info" type="button" name="search" id="search" value="Search"  > SEARCH</span>
           <input id="end_date" type="text" class="input-sm form-control" placeholder="End Date" name="end_date" autocomplete="off">
    
         </div>
      </div>  
    
    
    
    
          <table id="mssr_list"  class="table-bordered display nowrap cell-border compact  mytables " cellspacing="0" style="width:100%">
          <thead>
    
          <tr>
    
        <th class="rotate"><div><span>Product Code</span></div></th>
           ......
         .........
             <th class="rotate"><div><span>12</span></div></th>
              <th class="rotate"><div><span>13</span></div></th>
              <th class="rotate"><div><span>Execution</span></div></th>
    
            </tr>
    
            </thead>
    
                        </table>
      </div>    
    </body>
    </html>
    
    <script type="text/javascript" language="javascript">
    
    var editorOpts
    
    $(document).ready(function() {
    
    
    
     var editorOpts = {
        "table": "#mssr_list",
        "fields": [ {
            "label": "Product Code:",
            "name": "product_code_fk"
          } ,
    
          {
            "label": "1:",
            "name": "m_1"
          } 
               ,
            ......
    ....
    .....
              {
                "label": "12:",
                "name": "m_12"
          } ,
          {
            "label": "Total Score:",
            "name": "total_score"
          } ,
    
          {
            "label": "Execution:",
            "name": "execution"
          } 
    
        ]
      } ;
    
      var changedRows = [];
      var localEditor = new $.fn.dataTable.Editor( editorOpts );
    
    localEditor.on('postEdit', function (e, json, data) {
        changedRows.push( '#'+data.DT_RowId );
    
        tableone.buttons([3,4]).enable();
        console.log(changedRows);
    
    });
    
        var ajaxEditor = new $.fn.dataTable.Editor( $.extend( true, {
             ajax: '../../controllers/crg_promotions_mssr_fetch.php'
        }, editorOpts ) );
    
    
    $('.input-daterange').datepicker({
         todayBtn:'linked',
         format: "yyyy-mm-dd",
         viewMode: "months",
         minViewMode: "months",
         autoclose: true
        });
    
    
      var tableone = $('#mssr_list').DataTable( {
    
            "processing": true,
            "serverSide": true,
             "scrollY":"800px",
              "scrollX":"100%",
              "scrollCollapse": true,
    
          "ordering": [],
          "stateSave": false,
            "info":   true,
        "dom": 'lBrtip',
        "ajax":"../../controllers/crg_promotions_mssr_fetch.php",
    
        "columns": [
    
          { data: "product_code_fk" },
        { data: "product_name"},
        { data: "pack_size" },
          { data: "total_score" },
          { data: "m_1"},
        .....
    

    ................
    { data: "m_12"},
    { data: "no_of_stock"},

          { data: "execution" }
        ],
    
         select: true,
        buttons: [
                { extend: "create", editor: ajaxEditor },
                { extend: "edit", editor: localEditor },
                { extend: "remove", editor: ajaxEditor },
                {
                    text: 'Save changes',
                    init: function () {
                        this.disable();
                    },
                    action: function () {
                        ajaxEditor
                            .edit( changedRows, false )
                            .submit();
    
                        changedRows.length = 0;
                        tableone.buttons([3,4]).disable();
                    }
                },
                {
                    text: 'Discard changes',
                    init: function () {
                        this.disable();
                    },
                    action: function () {
                        this.ajax.reload();
    
                        changedRows.length = 0;
                        tableone.buttons([3,4]).disable();
                    }
                }
            ]
    
    });
    
      $("#search").click(function () {
         var start_date = $('#start_date').val();
              var end_date = $('#end_date').val();
    
            if(start_date != '' && end_date !=''){
                   tabletwo.draw();
               }
              else
      {
       alert("Both Date is Required");
      }
     });
    
    });
    
    
    </script>
    

    my server side code looks like:

    <?php
    session_start();
    
    
    
    // DataTables PHP library
    include( "../lib/DataTables.php" );
    
    // Alias Editor classes so they are easy to use
    use
        DataTables\Editor,
    

    ......
    .......
    DataTables\Editor\Validate,
    DataTables\Editor\ValidateOptions;

    $editor = Editor::inst( $db, 'mssr_list', 'promotion_id' )
        ->fields(
             Field::inst( 'mssr_list.promotion_id' ,'promotion_id'),
                Field::inst( 'mssr_list.product_code_fk' ,'product_code_fk'),
            Field::inst( 'mssr_list.promotion_id' ,'promotion_id'),
                 Field::inst( 'products.product_code','product_code' ),
            Field::inst( 'products.product_name','product_name' ),
            Field::inst( 'products.pack_size','pack_size' ),
                     Field::inst( 'mssr_list.total_score','total_score' ),
                  Field::inst( 'mssr_list.m_1','m_1' ),
    
              ....
    ..............
                Field::inst( 'mssr_list.m_12','m_12' ),
                Field::inst( 'mssr_list.no_of_stock','no_of_stock' ),
                Field::inst( 'mssr_list.execution','execution' )
    
            );
    
    //  if (( $_SESSION['username'] === 'member') || ($_SESSION['username'] === 'supplier')) {
    //      $editor->fields(Field::inst( 'mssr_list.product_code_fk' ,'product_code_fk' )->set(false)
    //      ->getFormatter( function ( $val, $data, $opts ) { return null;}));
    //    } 
    
    
    $editor
    
        ->leftJoin( 'products', 'products.product_code', '=', 'mssr_list.product_code_fk' )
    
    
        ->process( $_POST )
        ->json();
    
  • kthorngrenkthorngren Posts: 21,341Questions: 26Answers: 4,954

    The form data that gets sent is shown below and the response is the data which was there before edit which then gets displayed in table:

    draw: 2
    columns[0][data]: product_code_fk

    That request to the server looks like the request sent for the table draw after editing. Is there a request sent when you click the save button? What is in that request?

    What is the output of this console.log?

    localEditor.on('postEdit', function (e, json, data) {
        changedRows.push( '#'+data.DT_RowId );
     
        tableone.buttons([3,4]).enable();
        console.log(changedRows);
     
    });
    

    Kevin

  • Khalid TeliKhalid Teli Posts: 251Questions: 71Answers: 0

    That request to the server looks like the request sent for the table draw after editing. Is there a request sent when you click the save button? What is in that request?

    And when I click save button ,at same time** two requests** get sent
    a) Form data with old inputs (data before edit)

    data[row_31][product_code_fk]: 17194
    data[row_31][m_1]: a
    data[row_31][m_2]: 0
    data[row_31][m_3]: y
    data[row_31][m_4]: y
    data[row_31][m_5]: y
    data[row_31][m_6]: y
    data[row_31][m_7]: y
    data[row_31][m_8]: 1
    data[row_31][m_9]: 1
    data[row_31][m_10]: 1
    data[row_31][m_11]: 1
    data[row_31][m_12]: 1
    data[row_31][total_score]: 1
    data[row_31][execution]: 1
    action: edit
    

    b)

                 draw: 3
                    columns[0][data]: product_code_fk
                    columns[0][name]: 
                    columns[0][searchable]: true
                    columns[0][orderable]: true
                    columns[0][search][value]: 
                    columns[0][search][regex]: false
                    columns[1][data]: product_name
                    columns[1][name]: 
                    columns[1][searchable]: true
                .....
    

    What is the output of this console.log?

    output of console.log(changedRows); is ["#row_31"]

  • allanallan Posts: 63,516Questions: 1Answers: 10,472 Site admin
    Answer ✓

    Server-side processing and the queuing changes example are mutually exclusive. They fundamentally cannot work together because of how each operates.

    The queuing changes uses DataTables as a data store - the information in the table is held in the table, so that when ready to submit to the server the table data can be read and submitted.

    With server-side processing, the data shown in the table is basically readonly. Any change to the data needs a re-read from the server. This is why you can't use things like row().data() as a setter with server-side processing - the next draw would just wipe it, since the server hasn't been told about the change.

    I'm sorry to say, I don't see a way how the two can be used together.

    Allan

  • kthorngrenkthorngren Posts: 21,341Questions: 26Answers: 4,954
    edited October 2020

    @allan Please update the blog entry to note that server side processing is not supported. I scanned through the doc for this before trying to help and did not see anything about server side processing.

    Kevin

  • colincolin Posts: 15,240Questions: 1Answers: 2,599

    Yep, @kthorngren, that's a good suggestion. I'm updating it now, and it'll be pushed on the next site build,

    Colin

  • Khalid TeliKhalid Teli Posts: 251Questions: 71Answers: 0

    Thank you . I will look for a different strategy :)

This discussion has been closed.