Clarification regarding ajax.reload(null,false)

Clarification regarding ajax.reload(null,false)

TomBajzekTomBajzek Posts: 163Questions: 36Answers: 1

I have a case where I'm calling ajax.reload(null,false) in a submitSuccess handler. When the field that is the sort-column is changed, the screen gets updated to the new value and the table is then re-sorted so that the edited row moves, possibly off the page. I had thought this was not supposed to happen when the second parameter to ajax.reload() is false. The code segment in question is:

        ticketEditor.on( 'submitSuccess', function (e,json,data,action) {
            if (data.status === 'closed') {
                ticketTable.row( { selected: true } ).deselect();
        var truth = true;   // This is to get a breakpoint inside the if
            }
        ticketTable.ajax.reload(null,false);        // Update the row on screen
            
        // Make the noteTable follow the ticketTable updates
        ticketTable.rows().every(function() {
        if (this.child.isShown()) {
            updateChild(this);
        }
        } );
        } );

Strangely, I have an earlier version of this code (running in production) where ajax.reload() is not called at all in this location, yet the value of the changed field is updated on the screen, and the table is not re-sorted. This is the effect I want. This code segment is as follows:

        ticketEditor.on( 'submitSuccess', function (e,json,data,action) {
            noteTable.ajax.reload();
            if (data.status === 'closed') {
                ticketTable.row( { selected: true } ).deselect();
//              ticketTable.ajax.reload(null,true);
                var truth = true;   // This is to get a breakpoint inside the if
            } else {
//              ticketTable.ajax.reload(null,false);                
            }
        } );

The earlier version is using DataTables-1.10.10. The newer version with the problem is using DataTables-1.10.19. The new version's behavior does not change if I use it with DataTables-1.10.10.

I think I'm not understanding ajax.reload(null, false) correctly. Can someone shed some light on this?

This question has an accepted answers - jump to answer

Answers

  • colincolin Posts: 15,112Questions: 1Answers: 2,583

    Hi @TomBajzek ,

    Whether the ajax.reload() is called or not, the row would move to it's new position in the sorting order. For example, change "Airi" to "Biri" in this example and it will move as the name field is being sorted. I'm not sure how you saw this not happening, but it's definitely what I would expect,

    Cheers,

    Colin

  • TomBajzekTomBajzek Posts: 163Questions: 36Answers: 1

    Colin,

    What you describe is my original understanding of how this should work. However, in the production system, the row does not move when you change the data in the sort column. This is why I asked for clarification.

    My client prefers this non-moving behavior. Since this is results from my adding the other features they want, it looks like they will lose this behavior that they prefer, which is unfortunate.

    I'm not sure how I should proceed with this.

    Tom

  • kthorngrenkthorngren Posts: 20,142Questions: 26Answers: 4,736

    If you simply need to display the updated row you might be able to accomplish this with the row().show() plugin. However if you want to keep the other rows around the updated the same then that would require something else. Not sure what that would be :smile:

    Kevin

  • colincolin Posts: 15,112Questions: 1Answers: 2,583

    Hi @TomBajzek ,

    Could you link to that page that shows the problem, please. Or if that's not possible, could you modify this test case here so that it demonstrates that behaviour.

    Cheers,

    Colin

  • TomBajzekTomBajzek Posts: 163Questions: 36Answers: 1

    Kevin and Colin,

    I think I should try the plugin as Kevin suggested, as that may do what I need.

    As for Colin's suggestion, I think the pertinent case is the one that is in use on the production system, not the one I'm developing. The version on the production system seems to be the exception to expected behavior, but it is preferred by the client. I could send you a screen movie of its behavior, but it's running on a private intranet server having restricted access, so I can't let you experience it directly. I can send you the code if you wish.

    I appreciate your responses. Let me try the plugin first, as I may be able to make that do what is desired. I'll report what happens.

    Thanks much,
    Tom

  • TomBajzekTomBajzek Posts: 163Questions: 36Answers: 1

    Kevin,

    It seems that I don't understand how to apply the row().show() plugin to the existing code. I've tried this:

            ticketEditor.on( 'submitSuccess', function (e,json,data,action) {
                if (data.status === 'closed') {
                    ticketTable.row( { selected: true } ).deselect();
                    var truth = true;   // This is to get a breakpoint inside the if
                }
                ticketTable.row( {selected: true} ).show();
                
                // Make the noteTable follow the ticketTable updates
                ticketTable.rows().every(function() {
                    if (this.child.isShown()) {
                        updateChild(this);
                    }
                } );
            } );
    
    

    With a breakpoint at line 6, I've noticed that ticketTable.row( {selected: true} ) is sometimes an array of _Api[ [ ] ], while on alternate executions it as an array containing an array of _Api[ [178 ] ], but inspection of the latter reveals no further information. I think something elsewhere must be the cause of this, but in any case, I don't know the right way to apply the plugin call to this.

    What should I expect to find in _Api at that point? I feel that something elsewhere is wrong causing this to fail.

    I'm not sure how to proceed.

    Tom

  • kthorngrenkthorngren Posts: 20,142Questions: 26Answers: 4,736
    edited May 2019

    Not sure about what you should expect to see in the break point output but you are missing the .draw(false) after .show(). Without the draw(false) the Datatable won't update the display, ie, jump to the page desired. Here is an example that, after clicking the button, selects a row and uses ticketTable.row( {selected: true} ).show().draw(false); to jump to the page.
    http://live.datatables.net/zelevoce/1/edit

    Kevin

  • TomBajzekTomBajzek Posts: 163Questions: 36Answers: 1

    Hi Kevin,

    Your answer to my other question has enabled me to get all of the data issues straightened out, and the selection, deselection, and editing work as desired. However, the line

    ticketTable.row( {selected: true} ).show().draw(false);
    

    still does not display the page where the edited row ends up. When I tried to debug this, I found that the parameters passed into the submitSuccess event do not make sense. In particular, the data parameter does not contain the data for the row just edited. In particular, data refers to some row in the table other than the row being edited. This must be why the page with the edited row is not displayed at the end of the process.

    In the process of trying to debug this, I also found that there is a series of events after the submitSuccess event before the process finishes: select, deselect, and select. I do not understand why these events occur.

    The event handers in question are here:

            ticketTable.on( 'select', function (e, dt, type, indexes) {
                var row = dt.row(indexes);
    
                // Set classes to customize UI actions
                // If this select is from a click in the id-field, change class to canEdit
                ticketTable.cells(row,2).nodes().to$().removeClass('canSelect')
                ticketTable.cells(row,2).nodes().to$().addClass('canEdit')
                
                // Now display childRow and set this row as selectedRow
                createChild(row);
                selectedRow = row;
    
                // Show edit button if needed
                $('.nBtn').show();
                if (showEditBtn) {
                    $('.buttons-edit').show();
    
                } else {
                    $('.buttons-edit').hide();              
                }
            } );
    
            ticketTable.on( 'deselect', function (e, dt, type, indexes) {
                $('.buttons-edit').hide();              
                $('.nBtn').hide();
                var row = dt.row(indexes);
                selectedRow = '';
                destroyChild(row);
                ticketTable.cells(row,2).nodes().to$().removeClass('canEdit');
                ticketTable.cells(row,2).nodes().to$().addClass('canSelect');
            } );
    
            ticketEditor.on( 'submitSuccess', function (e,json,data,action) {
                if (data.status === 'closed') {
                    ticketTable.row( { selected: true } ).deselect();
                    var truth = true;   // This is to get a breakpoint inside the if
                }
                ticketTable.ajax.reload(null,false);        // Update the row on screen
                ticketTable.row( {selected: true} ).show().draw(false);
                
                truth = true;
    
                // Make the noteTable follow the ticketTable updates
                ticketTable.rows().every(function() {
                    if (this.child.isShown()) {
                        updateChild(this);
                    }
                } );
            } );
    
    

    To clarify, selection is done by the select-checkbox in the first column, or be clicking the third column (id) when it has the class canSelect, which is how it is initialized. When the row is selected, editing can be invoked by an Edit button, or by clicking on the third column when it has the class canEdit.

    I'm suspicious of the select and deselect events at the end, and of the fact that the data parameter does not match the row edited, but I don't know what to do about it.

    Can you see what is wrong, or tell me what is happening beyond what I can see?

    Thanks,
    Tom

  • colincolin Posts: 15,112Questions: 1Answers: 2,583
    edited June 2019

    Hi @TomBajzek ,

    When I tried to debug this, I found that the parameters passed into the submitSuccess event do not make sense. In particular, the data parameter does not contain the data for the row just edited.

    That definitely shouldn't be the case - see here.

    There's a lot going on in this thread that makes it hard to follow - I know you said before this is a production system so you can't link to it, but would you be able to modify my test case to demonstrate the problem? That would help us to follow your code.

    Cheers,

    Colin

  • TomBajzekTomBajzek Posts: 163Questions: 36Answers: 1
    edited June 2019

    Colin,

    The issue I'm dealing with now occurs on my development system. I can give you credentials to access that system, if you wish. I'll also send you a couple of sentences to explain how to see the problem.

    Please let me know how to send you the credentials privately.

    Thanks,
    Tom

  • colincolin Posts: 15,112Questions: 1Answers: 2,583
    Answer ✓

    Hi @TomBajzek ,

    You can either send as a DM here, or please email to colin@datatables.net,

    Cheers,

    Colin

  • colincolin Posts: 15,112Questions: 1Answers: 2,583

    Mailed Tom directly, but putting solution here so others can see what was needed. Kevin's replies got it close. Here's what I mailed:

    ... got a couple of things that will hopefully do the trick.

    rowId :
    One problem is because the DataTables hasn't been told what the unique Id field is, after the Ajax reload, it can't keep track of what was selected before. If you add

    rowId: 'id'
    

    into the top level of the DataTables initialisation, then that will help.

    ajax.reload()

    These lines here would cause a problem,

    ticketTable.ajax.reload(null,false);        // Update the row on screen
    ticketTable.row( {selected: true} ).show().draw(false);
    

    because of the nature of asychronous ajax call the second line would be called before the ajax had completed. It's best to do the code within the ajax.reload() callback function. That said, we did find a bug, some timing issue, so it still seems to need a tiny sleep to make the row().show() work - see our test case here.

    If you do the same, move the code into the callback, something like this, hopefully that'll do the trick:

    ticketTable.ajax.reload(function() {
       setTimeout( function () {
     
                ticketTable.row( {selected: true} ).show().draw(false);
                  
                truth = true;
      
                // Make the noteTable follow the ticketTable updates
                ticketTable.rows().every(function() {
                    if (this.child.isShown()) {
                        updateChild(this);
                    }
                } );
        }, 10 );
     
    },false);      
    
This discussion has been closed.