Asp.Net Mvc Html.BeginFormSubmit ajax 发送两次请求(一个的类型xhr 另一个的文档)

Asp.Net Mvc Html.BeginFormSubmit ajax sends twice request (one's type xhr the other's document)

我正在使用 Asp.Net MVC 开发调查应用程序。我有一个名为 Index.cshtml 的页面,其中有一个问题 table 和一个 'Add New' button.Once 按钮被点击,一个弹出窗口被打开 jQuery。我正在从控制器调用一个视图来填充名为 AddOrEdit.cshtml(子页面)的 jQuery 对话框。我正在添加新的问题和选项。问题是一个文本字段,它的选项添加在 editable table 中。单击提交按钮后,将触发提交表单事件(保存或更新)。但是 ajax 发送了两次请求。其中一个请求发送空对象,另一个发送完整对象。我哪里出错了?

根据我的研究,导致这个问题的原因是不引人注目的验证器被放置在 2 个不同的页面上。但对我来说情况并非如此。

当我在 f12 中使用 chrome 进行调试时,2 个请求之一的发起者 'jquery' 另一个请求的发起者 'other' 这 2 个请求之一的类型 post 请求显示为 'XHR' 而另一个请求的类型是 'document'.

Index.cshtml

@{
ViewBag.Title = "Soru Listesi";
}

<h2>Soru Oluşturma</h2>
<a class="btn btn-success" style="margin-bottom: 10px" 
onclick="PopupForm('@Url.Action("AddOrEdit","Question")')"><i class="fa fa-plus"></i> Yeni Soru Oluştur</a><table id="questionTable" class="table table-striped table-bordered accent-blue" style="width: 100%">
<thead>
    <tr>
        <th>Soru No</th>
        <th>Soru Adı</th>
        <th>Oluşturma Tarihi</th>
        <th>Güncelleme Tarihi</th>
        <th>Güncelle/Sil</th>
    </tr>
</thead>
</table>
<link 
href="https://cdn.datatables.net/1.10.20/css/dataTables.bootstrap4.min.css" rel="stylesheet" />
<link href="https://stackpath.bootstrapcdn.com/font-awesome/4.7.0/css/font-awesome.min.css" 
rel="stylesheet" />



 @section Scripts{
<script src="https://cdn.datatables.net/1.10.20/js/jquery.dataTables.min.js"></script>
<script src="https://cdn.datatables.net/1.10.20/js/dataTables.bootstrap4.min.js"></script>

<script>


    var Popup, dataTable;
    $(document).ready(function() {

        dataTable = $("#questionTable").DataTable({
            "ajax": {
                "url": "/Question/GetData",
                "type": "GET",
                "datatype": "json"
            },
            "columnDefs": [
                { targets: 2 }
            ],
            "scrollX": true,
            "scrollY": "auto",
            "columns": [
                { "data": "QuestionId" },
                { "data": "QuestionName" },
                {
                    "data": "CreatedDate",
                    "render": function(data) { return getDateString(data); }
                },
                {
                    "data": "UpdatedDate",
                    "render": function(data) { return getDateString(data); }
                },
                {
                    "data": "QuestionId",
                    "render": function(data) {
                        return "<a class='btn btn-primary btn-sm' onclick=PopupForm('@Url.Action("AddOrEdit", "Question")/" +
                            data +
                            "')><i class='fa fa-pencil'></i> Güncelle</a><a class='btn btn-danger btn-sm' style='margin-left:5px' onclick=Delete(" +
                            data +
                            ")><i class='fa fa-trash'></i> Sil</a>";
                    },
                    "orderable": false,
                    "searchable": false,
                    "width": "150px"
                }
            ],
            "language": {
                "emptyTable":
                    "Soru bulunamadı, lütfen <b>Yeni Soru Oluştur</b> butonuna tıklayarak yeni soru oluşturunuz. "
            }
        });
    });


    function getDateString(date) {
        var dateObj = new Date(parseInt(date.substr(6)));
        let year = dateObj.getFullYear();
        let month = (1 + dateObj.getMonth()).toString().padStart(2, '0');
        let day = dateObj.getDate().toString().padStart(2, '0');
        return day + '/' + month + '/' + year;
    };


    function PopupForm(url) {
        var formDiv = $('<div/>');
        $.get(url)
            .done(function(response) {
                formDiv.html(response);
                Popup = formDiv.dialog({
                    autoOpen: true,
                    resizable: true,
                    title: 'Soru Detay',
                    modal: true,
                    height: 'auto',
                    width: '700',
                    close: function() {
                        Popup.dialog('destroy').remove();
                    }

                });
            });
    }

    function SubmitForm(form) {
        debugger;
        if (form.checkValidity() === false) {
            debugger;
            event.preventDefault();
            event.stopPropagation();
        }
        form.classList.add('was-validated');
        if ($(form).valid()) {
            var question = {};
            question.questionId = 1111;
            var options = new Array();
            $("#questionForm TBODY TR").each(function() {
                var row = $(this);
                var option = {};
                option.OptionId = row.find("TD").eq(0).html();
                option.OptionName = row.find("TD").eq(1).html();
                options.push(option);
            });
            question.options = options;
            question.responses = new Array();
            $.ajax({
                type: "POST",
                url: form.action,
                data: JSON.stringify(question),
                success: function(data) {
                    if (data.success) {
                        debugger;
                        Popup.dialog('close');
                        dataTable.ajax.reload();
                        $.notify(data.message,
                            {
                                globalPosition: "top center",
                                className: "success",
                                showAnimation: "slideDown",
                                gap: 1000
                            });
                    }
                },
                error: function(req, err) {
                    debugger;
                    alert('req : ' + req + ' err : ' + err.data);
                },
                complete: function(data) {
                    alert('complete : ' + data.status);
                }
            });
        }
    }


    function ResetForm(form) {
        Popup.dialog('close');
        return false;
    }

    function Delete(id) {
        if (confirm('Bu soruyu silmek istediğinizden emin misiniz?')) {
            $.ajax({
                type: "POST",
                url: '@Url.Action("Delete", "Question")/' + id,
                success: function(data) {
                    if (data.success) {
                        dataTable.ajax.reload();
                        $.notify(data.message,
                            {
                                className: "success",
                                globalPosition: "top center",
                                title: "BAŞARILI"
                            })
                    }
                }

            });
        }
    }

</script>
}

AddOrEdit.cshtml

@using MerinosSurvey.Models
@model Questions
@{
Layout = null;
}

@using (Html.BeginForm("AddOrEdit", "Question", FormMethod.Post, new { @class = "needs-validation", 
novalidate = "true", onsubmit = "return SubmitForm(this)", onreset = "return ResetForm(this)", id = 
"questionForm" }))
{
<div class="form-group row">
    @Html.Label("QuestionId", "Soru No", new { @class = "col-form-label col-md-3" })
    <div class="col-md-9">
        @Html.TextBoxFor(model => model.QuestionId, new { @readonly = "readonly", @class = "form-control" })

    </div>
</div>
<div class="form-group row">
    @Html.Label("QuestionName", "Soru Adı", new { @class = "col-form-label col-md-3" })
    <div class="col-md-9">
        @Html.EditorFor(model => model.QuestionName, new { htmlAttributes = new { @class = "form-control", required = "true" } })
        <div class="valid-feedback"><i class="fa fa-check">Süpersin</i></div>
        <div class="invalid-feedback "><i class="fa fa-times"></i></div>
    </div>
</div>


@*<div class="form-group row">
        @Html.LabelFor(model => model.CreatedDate, new { @class = "form-control-label col-md-3"})
        <div class="col-md-9">
            @Html.EditorFor(model => model.CreatedDate, "{0:yyyy-MM-dd}", new { htmlAttributes = new { @class = "form-control", type = "date", @readonly = "readonly",required="false" } })

        </div>
    </div>*@


<div class="table-wrapper form-group table-responsive-md">
    <div class="table-title">
        <div class="form-group row">
            <div class="col-md-9">Seçenekler</div>
            <div class="col-md-3">
                <a class="btn btn-success add-new" style="margin-bottom: 10px"><i class="fa fa-plus"></i>Seçenek Ekle</a>
            </div>
        </div>
    </div>
    <table class="table optionTable">
        <thead>
            <tr>
                <th scope="col">Seçenek Id</th>
                <th scope="col">Seçenek Adı</th>
                <th scope="col">Güncelle/Sil</th>
            </tr>

        </thead>
        <tbody>
            @*@foreach (Options options in Model.Options)
                {
                    <tr>
                        <td>@options.OptionId</td>
                        <td>@options.OptionName</td>
                        <td>
                            <a class="add btn btn-primary btn-sm" title="Add" data-toggle="tooltip"> 
<i class="fa fa-check">Onayla</i></a>
                            <a class="edit btn btn-secondary btn-sm" title="Edit" data-toggle="tooltip"><i class="fa fa-pencil">Güncelle</i></a>
                            <a class="delete btn-danger btn-sm" title="Delete" data-toggle="tooltip"><i class="fa fa-trash">Sil</i></a>
                        </td>
                    </tr>
                }*@
        </tbody>
    </table>
</div>


<div class="form-group row">
    <input type="submit" value="Submit" class="btn btn-primary" id="btnSubmit" />
    <input type="reset" value="Reset" class="btn btn-secondary" />
</div>
}
<script>
 $(document).ready(function () {
     $('[data-toggle="tooltip"]').tooltip();
     //var actions = $("table.optionTable td:last-child").html();

     var actions =' <a class="add btn btn-primary btn-sm" title="Add" data-toggle="tooltip"><i 
    class="fa fa-check">Onayla</i></a>' + '<a class="edit btn btn-secondary btn-sm" title="Edit" data toggle="tooltip"><i class="fa fa-pencil">Güncelle</i></a>' +'<a class="delete btn-danger btn-sm" title="Delete" data-toggle="tooltip"><i class="fa fa-trash">Sil</i></a>';

    // Append table with add row form on add new button click
    $(".add-new").click(function () {
        $(this).attr("disabled", "disabled");
        var index = $("table.optionTable tbody tr:last-child").index();
        var row = '<tr>' +
            '<td><input type="text" class="form-control" name="optionId" id="optionId"></td>' +
            '<td><input type="text" class="form-control" name="optionId" id="optionName"></td>' +
            '<td>' + actions + '</td>' +
        '</tr>';
        $("table.optionTable").append(row);
        $("table.optionTable tbody tr").eq(index + 1).find(".add, .edit").toggle();
        $('[data-toggle="tooltip"]').tooltip();
    });



    // Add row on add button click
    $(document).on("click", ".add", function () {
        var empty = false;
        var input = $(this).parents("tr").find('input[type="text"]');
        input.each(function () {
            if (!$(this).val()) {
                $(this).addClass("error");
                empty = true;
            } else {
                $(this).removeClass("error");
            }
        });
        $(this).parents("tr").find(".error").first().focus();
        if (!empty) {
            input.each(function () {
                $(this).parent("td").html($(this).val());
            });
            $(this).parents("tr").find(".add, .edit").toggle();
            $(".add-new").removeAttr("disabled");
        }
    });

    // Edit row on edit button click
    $(document).on("click", ".edit", function () {

        $(this).parents("tr").find("td:not(:last-child)").each(function () {
            $(this).html('<input type="text" class="form-control" value="' + $(this).text() + '">');
        });
        $(this).parents("tr").find(".add, .edit").toggle();
        $(".add-new").attr("disabled", "disabled");
    });



    // Delete row on delete button click
    $(document).on("click", ".delete", function () {
        debugger;
        $(this).parents("tr").remove();
        $(".add-new").removeAttr("disabled");
    });
});

event.preventDefault();移动此行并将其紧跟在 function SubmitForm (form){

之后

如下所示:

function SubmitForm(form) { 
    debugger; 
event.preventDefault(); 
if (form.checkValidity() === false) { 
debugger; 

event.stopPropagation(); 
} 
form.classList.add('was-validated'); 
if ($(form).valid()) { 
var question = {}; 
question.questionId = 1111; 
var options = new Array(); 
$("#questionForm TBODY TR").each(function() { 
var row = $(this); 
var option = {}; 
option.OptionId = row.find("TD").eq(0).html(); 
option.OptionName = row.find("TD").eq(1).html(); 
options.push(option); 
}); 
question.options = options; 
question.responses = new Array(); 
$.ajax({ 
type: "POST", 
url: form.action, 
data: JSON.stringify(question), 
success: function(data) { 
if (data.success) { 
debugger; 
Popup.dialog('close'); 
dataTable.ajax.reload(); 
$.notify(data.message, 
{ 
globalPosition: "top center", 
className: "success", 
showAnimation: "slideDown", 
gap: 1000 
}); 
} 
}, 
error: function(req, err) { 
debugger; 
alert('req : ' + req + ' err : ' + err.data); 
}, 
complete: function(data) { 
alert('complete : ' + data.status); 
} 
}); 
} 
}