Author Topic: AJAX Call on master fails when I have a detailModel included.  (Read 3440 times)

stevejacobsen

  • Pro Enterprise
  • Newbie
  • *
  • Posts: 46
    • View Profile
AJAX Call on master fails when I have a detailModel included.
« on: September 21, 2016, 04:17:18 am »
I have a grid with a master/detail relationship. When I include the link to the detail grid the AJAX call hangs. It never makes the AJAX call.

Quote
var colM = [
        {title: "", minWidth: 25, width: 27, type: "detail", resizable: false, editable: false},
        {title: "ID", width: 75, dataIndx: "id", align: "center", editable: false},
        {title: "Date", width: 125, dataIndx: "service_date", align: "center",
            editor: {
                type: 'textbox',
                init: dateEditor
            },
            validations: [
                {type: 'regexp', value: '^[0-9]{4}-[0-9]{2}-[0-9]{2}$', msg: 'Not in yyyy-mm-dd format'}
            ]
        },
        {title: "Location", width: 300, dataIndx: "location", align: "center"},
        {title: "Leader", width: 225, dataIndx: "leader", align: "center"},
        {title: "", editable: false, minWidth: 165, sortable: false,
            render: function (ui) {
                return "<button type='button' class='edit_btn'>Edit</button>\
                                <button type='button' class='delete_btn'>Delete</button>";
            },
            postRender: function (ui) {
                var rowIndx = ui.rowIndx,
                        grid = this,
                        $cell = grid.getCell(ui);

                //delete button
                $cell.find(".delete_btn").button({icons: {primary: 'ui-icon-close'}})
                        .bind("click", function (evt) {
                            deleteRow(rowIndx, grid);
                        });

                //edit button
                $cell.find(".edit_btn").button({icons: {primary: 'ui-icon-pencil'}})
                        .bind("click", function (evt) {
                            if (isEditing(grid)) {
                                return false;
                            }
                            editRow(rowIndx, grid, true);
                        });

                //if it has edit class, then edit the row.
                if (grid.hasClass({rowData: ui.rowData, cls: 'pq-row-edit'})) {
                    editRow(rowIndx, grid);
                }
            }
        }
    ];
    var dataModel = {
        location: "remote",
        dataType: "JSON",
        method: "GET",
        recIndx: "id",
        url: "utilities/ajax_get_services_data_JSON.php",
        getData: function (dataJSON) {
            var data = dataJSON.data;
            if (data && data.length) {
                data[0]['pq_detail'] = {'show': true};
            }
            return {curPage: dataJSON.curPage, totalRecords: dataJSON.totalRecords, data: data};
        }
    };
    var grid = $("#services_grid").pqGrid({
        postRenderInterval: 200,
        width: 1100,
        height: 815,
        resizeable: true,
        dataModel: dataModel,
        colModel: colM,
        wrap: false,
        hwrap: false,
        editable: true,
        numberCell: {show: false},
        flex: {one: true},
        title: "Praise Song Organizer - Services List",
        virtualX: true, virtualY: false,
        hoverMode: null,
        trackModel: {on: true},
        editor: {type: 'textbox', select: true, style: 'outline:none;'},
        validation: {icon: 'ui-icon-info'},
        selectionModel: {type: 'cell'},
        pageModel: {type: 'local', rPP: 20},
        scrollModel: {flexContent: true},
        //make rows editable based upon the class.
        editable: function (ui) {
            return this.hasClass({rowIndx: ui.rowIndx, cls: 'pq-row-edit'});
        },
                create: function (evt, ui) {
                    this.widget().pqTooltip();
                },
        detailModel: {
            cache: true,
            collapseIcon: "ui-icon-plus",
            expandIcon: "ui-icon-minus",
            init: function (ui) {
                var rowData = ui.rowData,
                        detailobj = gridDetailModel($(this).pqGrid('instance'), rowData),
                        $grid = $("<div></div>").pqGrid(detailobj);
                return $grid;
            }
        },
        toolbar: {
            items: [
                {
                    type: 'button',
                    icon: 'ui-icon-print',
                    label: 'PowerPoint',
                    listener: function () {

                    }
                },
                {
                    type: 'button',
                    icon: 'ui-icon-print',
                    label: 'Chordsheets',
                    listener: function () {

                    }
                },
                {
                    type: 'button',
                    icon: 'ui-icon-print',
                    label: 'Capo Chordsheets',
                    listener: function () {

                    }
                },
                {
                    type: 'button',
                    icon: 'ui-icon-plus',
                    label: 'Add Service',
                    listener: function () {

                    }
                },
                {
                    type: 'select',
                    icon: 'ui-icon-select',
                    label: 'Add Song',
                    listener: function () {

                    }
                }
            ]
        }
    });

    var gridDetailModel = function (gridMain, rowData) {
        return {
            postRenderInterval: 200,
            width: 750,
            height: 'flex',
            pageModel: {type: "local", rPP: 5, strRpp: ""},
            showTop: false,
            showBottom: false,
            editable: true,
            dataModel: {
                location: "remote",
                dataType: "json",
                method: "GET",
                error: function () {
                    //gridMain.rowInvalidate({rowData: rowData});
                },
                url: "/utilities/ajax_get_services_song_detail.php?serviceid=" + rowData.id
            },
            colModel: [
                {title: "Order", width: 85, dataIndx: "song_order", dataType: "integer"

                },
                {title: "Title", width: 85, dataIndx: "title",
                    validations: [
                        {type: 'minLen', value: 1, msg: "Required"},
                        {type: 'maxLen', value: 20, msg: "length should be <= 20"}
                    ]
                },
                {title: "Description", width: 95, dataIndx: "description"},
                {title: "Key", width: 150, dataIndx: "key"},
                {title: "Time Signature", width: "100", align: "right", dataIndx: "time_signature"},
                {title: "", editable: false, minWidth: 250, sortable: false,
                    render: function (ui) {
                        return "<button type='button' class='edit_btn'>Edit</button>\
                                <button type='button' class='delete_btn'>Delete</button>";
                    },
                    postRender: function (ui) {
                        var rowIndx = ui.rowIndx,
                                grid = this,
                                $cell = grid.getCell(ui);

                        //delete button
                        $cell.find(".delete_btn").button({icons: {primary: 'ui-icon-close'}})
                                .bind("click", function (evt) {
                                    deleteRow(rowIndx, grid);
                                });

                        //edit button
                        $cell.find(".edit_btn").button({icons: {primary: 'ui-icon-pencil'}})
                                .bind("click", function (evt) {
                                    if (isEditing(grid)) {
                                        return false;
                                    }
                                    editRow(rowIndx, grid, true);
                                });

                        //if it has edit class, then edit the row.
                        if (grid.hasClass({rowData: ui.rowData, cls: 'pq-row-edit'})) {
                            editRow(rowIndx, grid);
                        }
                    }
                }
            ],
            refresh: function (evt, ui) {
                if (ui.source != "flex") {
                    this.flex();
                }
            },
            numberCell: {show: false},
            title: "Song Selections"
        };
    };

paramvir

  • Administrator
  • Hero Member
  • *****
  • Posts: 6265
    • View Profile
Re: AJAX Call on master fails when I have a detailModel included.
« Reply #1 on: September 21, 2016, 08:24:07 pm »
You need to look out for errors in detailModel ajax call, common cause is incorrect url.

Code: [Select]
dataModel: {
                location: "remote",
                dataType: "json",
                method: "GET",
                error: function ( jqXHR, textStatus, errorThrown) {
                    alert( 'check browser console for errors' );
                    console.log( "error: ", textStatus, errorThrown );
                    //gridMain.rowInvalidate({rowData: rowData});
                },
                url: "/utilities/ajax_get_services_song_detail.php?serviceid=" + rowData.id
            },
« Last Edit: September 21, 2016, 08:31:47 pm by paramquery »

stevejacobsen

  • Pro Enterprise
  • Newbie
  • *
  • Posts: 46
    • View Profile
Re: AJAX Call on master fails when I have a detailModel included.
« Reply #2 on: September 21, 2016, 09:09:06 pm »
Sorry, I left out the function that was failing. The detail records come up fine. It's when I click update on the master record that it fails.

In the code below, the "console.log(url);" echos the correct URL to the console but the AJAX code following doesn't fire at all. The browser becomes unresponsive.

Quote

//called by update button.
    function update(rowIndx, grid) {

        if (grid.saveEditCell() == false) {
            console.log('saveeditcell');
            return false;
        }

        if (!grid.isValid({rowIndx: rowIndx, focusInvalid: true}).valid) {
            console.log('isvalid');
            return false;
        }
        console.log('update');
        if (grid.isDirty()) {
            console.log('dirty');
            var url,
                    rowData = grid.getRowData({rowIndx: rowIndx}),
                    recIndx = grid.option("dataModel.recIndx"),
                    type;
            console.log(rowData);
            grid.removeClass({rowIndx: rowIndx, cls: 'pq-row-edit'});

            if (rowData[recIndx] == null) {
                //add record.
                type = 'add';
                url = "/utilities/ajax_edit_services.php?pq_add=1";
            } else {
                //update record.
                type = 'update';
                url = "/utilities/ajax_edit_services.php?pq_update=1";
            }
            console.log(url);
            $.ajax($.extend({}, ajaxObj, {
                context: grid,
                url: url,
                data: rowData,
                success: function (response) {
                    if (type === 'add') {
                        rowData[recIndx] = response.recId;
                    }
                    //debugger;
                    grid.commit({type: type, rows: [rowData]});
                    grid.refreshRow({rowIndx: rowIndx});
                }
            }));

        } else {
            grid.quitEditMode();
            grid.removeClass({rowIndx: rowIndx, cls: 'pq-row-edit'});
            grid.refreshRow({rowIndx: rowIndx});
        }
    }

paramvir

  • Administrator
  • Hero Member
  • *****
  • Posts: 6265
    • View Profile
Re: AJAX Call on master fails when I have a detailModel included.
« Reply #3 on: September 21, 2016, 10:34:45 pm »
Please try this: create a copy of rowData and remove the pq_detail property.

Code: [Select]
var row = $.extend( {}, rowData );
delete row.pq_detail;

 $.ajax($.extend({}, ajaxObj, {
                context: grid,
                url: url,
                //data: rowData,
                data: row,
                success: function (response) {
                    if (type === 'add') {
                        rowData[recIndx] = response.recId;
                    }
                    //debugger;
                    grid.commit({type: type, rows: [row]});
                    grid.refreshRow({rowIndx: rowIndx});
                }
            }));
« Last Edit: September 21, 2016, 10:41:40 pm by paramquery »

stevejacobsen

  • Pro Enterprise
  • Newbie
  • *
  • Posts: 46
    • View Profile
Re: AJAX Call on master fails when I have a detailModel included.
« Reply #4 on: September 22, 2016, 06:20:16 am »
That fixed it! Thanks!