Django AJAX 表单提交始终无效

Django AJAX Form submission is always invalid

提问人:Floris Kruger 提问时间:8/31/2023 更新时间:8/31/2023 访问量:38

问:

我有一个 Django 项目,其视图包含两个表单,我想通过两个单独的 ajax 请求提交这些表单。第一个 ajax 请求实际上应该填写第二个表单的一个值,这成功了。此外,第二个表单有一些初始值,我稍后计划将其隐藏,以便用户在提交第一个表单后只能看到要填写的必要字段。

在我的视野中检查了“”和“”之后,我传入了一个“”关键字,以确定ajax类型是第一个ajax请求还是第二个ajax请求。我的第二个 ajax 请求使用了一个模型表单,该表单应该在验证时创建我的模型的新实例。ajax_typerequest.is_ajax()request.method == 'POST

我的观点:

def canadaTaxEntries(request):

    newest_record = LAWCHG.objects.aggregate(Max('control_number'))
    newest_control_number = newest_record["control_number__max"]
    print(newest_control_number)

    today = date.today().strftime("1%y%m%d")
    current_time = time.strftime("%H%M%S")
    #print(today)
    #print(current_time)

    initial_data = {
        'control_number': (newest_control_number + 1),
        'item_number': None,
        'vendor_tax_code': None,
        'expiration_flag': 1,
        'charge_category': None,
        'charge_desc_code': None,
        'country': 'US',
        'state': None,
        'city': None,
        'county': None,
        'charge_amount': None,
        'charge_uom': 'CA',
        'charge_percentage': 0.0,
        'apply_flag': 1,
        'beg_del_date': None,
        'end_del_date': None,
        'rev_date': today,
        'rev_time': current_time,
        'est_date': today,
        'est_time': current_time,
        'program_id': 'BI008',
        'operator_id': 'FKRUGER',
    }

    canada_tax_form = CanadaTaxForm(request.POST or None, initial=initial_data)

    if request.is_ajax():
        if request.method == 'POST':
            canada_tax_form = CanadaTaxForm(request.POST or None, initial=initial_data)

            data = json.load(request)
            #item_number = request.POST.get('itm', False)
            ajax_type = data.get("ajax_type")

            if ajax_type == "screen_item":
                print('1st request')
                num = data.get("item")
                itmnum = int(num)
                return screen_item_ajax(itmnum)
            
            elif ajax_type == "tax_entry":
                print("2nd request")

                if canada_tax_form.is_valid():
                    print("VALID")
                    canada_tax_form.save()
                else:
                    print("NOT VALID")
                    print(canada_tax_form.errors)

                controlnum = data.get("control_num")
                itemnum = data.get("item")
                ventaxnum = data.get("vend_tax")
                return canada_tax_entries_ajax(request, controlnum, itemnum, ventaxnum)


    context = {
        "canada_tax_form":canada_tax_form,
    }

    return render(request, "html/canadaTaxEntries.html", context)

我的ajax请求:

$(document).on('submit', '#item_num_form', function (e) {
    let item_number = document.getElementById("item_number").value

    console.log(item_number)
    e.preventDefault()
    $.ajax({
        url: "http://127.0.0.1:8000/canada/",
        type: 'POST',
        dataType: "json",
        data: JSON.stringify({
            ajax_type: "screen_item",
            item: item_number,
        }),
        headers: {
            "X-Requested-With": "XMLHttpRequest",
            "X-CSRFToken": getCookie("csrftoken"),
        },
        success: function (data) {
            console.log(data)
            console.log("AJAX Worked!")

            let description = data.item_info[0].item_description;
            document.getElementById("description").innerHTML = "Item Description: " + description;

            let upc_num = data.item_info[0].upc_14_long;
            document.getElementById("upc_num").innerHTML = " UPC Number: " + upc_num;

            document.getElementById("id_item_number").value = item_number;

            function getTH() {
                const column = table_headers;
                const head = document.querySelector('thead');
                let tags = "<tr>";
                for (i = 0; i < column.length; i++){
                    tags += `<th>${column[i]}</th>`;
                }
                tags += "</tr>"
                head.innerHTML = tags;

                getTD();
            }

            function getTD() {
                const body = document.querySelector('tbody');
                let tags = "";

                data.existing_tax_records.map(d => {
                    tags += `<tr>
                    <td>${d.beg_del_date}</td>
                    <td>${d.end_del_date}</td>
                    <td>${d.charge_amount}</td>
                    <td>${d.charge_uom}</td>
                    <td>${d.apply_flag}</td>
                    <td>${d.charge_category_id}</td>
                    <td>${d.charge_desc_code_id}</td>
                    <td>${d.vendor_tax_code}</td>
                    <td>${d.control_number}</td>
                    </tr>`
                })
                body.innerHTML = tags;
            }
            getTH()
        }
    })
})


$(document).on('submit', '#tax_form', function (e) {
    let control_number = document.getElementById("id_control_number").value
    let item_number = document.getElementById("id_item_number").value
    let vendor_tax_code = document.getElementById("id_vendor_tax_code").value

    console.log(control_number)
    e.preventDefault()
    $.ajax({
        url: "http://127.0.0.1:8000/canada/",
        type: 'POST',
        dataType: "json",
        data: JSON.stringify({
            ajax_type: "tax_entry",
            control_num: control_number,
            item: item_number,
            vend_tax: vendor_tax_code,
        }),
        headers: {
            "X-Requested-With": "XMLHttpRequest",
            "X-CSRFToken": getCookie("csrftoken"),
        },
        success: function (data) {
            console.log(data)
            console.log("2nd AJAX Worked!")
            console.log("Is form valid???")
        },
        error: function (error) {
            console.log(error)
            console.log("2nd AJAX Failed")
        }
    })
})

我的两个 ajax 请求都返回了成功消息,因此命中了提交第二个表单的触发器。我认为问题与我的表单在提交之前被擦除有关,即使我在点击第二个表单的提交按钮时填写了所有输入字段。我不确定我是否错误地初始化了我的表单,但我对为什么我的表单从未通过验证检查感到困惑。

最后,在验证检查后用“”打印到控制台,打印出以下内容,这让我相信我的表单正在被擦除。我怎样才能避免这种情况?print(canada_tax_form.errors)

NOT VALID
<ul class="errorlist"><li>control_number<ul class="errorlist"><li>This field is required.</li></ul></li><li>item_number<ul class="errorlist"><li>This field is required.</li></ul></li><li>vendor_tax_code<ul class="errorlist"><li>This field is required.</li></ul></li><li>expiration_flag<ul class="errorlist"><li>This field is required.</li></ul></li><li>charge_category<ul class="errorlist"><li>This field is required.</li></ul></li><li>charge_desc_code<ul class="errorlist"><li>This field is required.</li></ul></li><li>country<ul class="errorlist"><li>This field is required.</li></ul></li><li>state<ul class="errorlist"><li>This field is required.</li></ul></li><li>charge_amount<ul class="errorlist"><li>This field is required.</li></ul></li><li>charge_uom<ul class="errorlist"><li>This field is required.</li></ul></li><li>charge_percentage<ul class="errorlist"><li>This field is required.</li></ul></li><li>apply_flag<ul class="errorlist"><li>This field is required.</li></ul></li><li>beg_del_date<ul class="errorlist"><li>This field is required.</li></ul></li><li>end_del_date<ul class="errorlist"><li>This field is required.</li></ul></li><li>rev_date<ul class="errorlist"><li>This field is required.</li></ul></li><li>rev_time<ul class="errorlist"><li>This field is required.</li></ul></li><li>est_date<ul class="errorlist"><li>This field is required.</li></ul></li><li>est_time<ul class="errorlist"><li>This field is required.</li></ul></li><li>program_id<ul class="errorlist"><li>This field is required.</li></ul></li><li>operator_id<ul class="errorlist"><li>This field is required.</li></ul></li></ul>
javascript jquery django ajax 表单

评论

0赞 imvain2 8/31/2023
我敢肯定这不是问题,但是您不需要通过ajax发送的对象。您可以传递对象本身。JSON.stringify
0赞 Floris Kruger 8/31/2023
好的,谢谢,但是是的,这无助于为什么我的表格总是无效......关于为什么会这样有什么想法吗?

答:

0赞 SamSparx 8/31/2023 #1

在 ajax 中,您将发送以下内容:

    data: JSON.stringify({
        ajax_type: "tax_entry",
        control_num: control_number,
        item: item_number,
        vend_tax: vendor_tax_code,
    }),

但是,您的表格将令人期待

1)数据值的键与表单定义中的字段同名。为了通过错误来判断,它们的命名方式不同,例如,control_number而不是control_num,因此在请求的表单设置过程中不会分配它们。发布

2)CanadaTaxForm的所有必填字段需要填写。由于您正在发送 POST 数据,因此不会读取您的初始字段,这可能会使情况更加复杂。正如文档所说:这些值仅针对未绑定的表单显示,如果未提供特定值,则不会将其用作回退值。

若要解决此问题,还可以在 tax_records 表中写入隐藏字段以保存 CanadaTaxForm 所需的任何其他数据,并在为 ajax 提交执行新值时将这些值捕获为“数据”。或者,如果用户无法真正更改其他数据,则可以减少 CanadaTaForm,仅将提交的数据作为字段,在创建新对象时添加任何其他内容(如果不看到表单或模板,很难具体说明最佳课程)