Python Django-将复选框输入保存到数据库并更新页面

Python Django-将复选框输入保存到数据库并更新页面,python,django,ajax,Python,Django,Ajax,我的问题是,我有一个“分配”对象列表,所有这些对象都有一个名为“状态”的字段。状态为true或false,用户可以通过单击特定分配的复选框来选择更改值 我目前的解决方案是: 课程详情。html: {% for assignment in assignments %} <tr> <td scope="row" style="text-align: center"> <form> {% csrf_to

我的问题是,我有一个“分配”对象列表,所有这些对象都有一个名为“状态”的字段。状态为true或false,用户可以通过单击特定分配的复选框来选择更改值

我目前的解决方案是:

课程详情。html:

{% for assignment in assignments %}

<tr>
  <td scope="row" style="text-align: center">
    <form>
    {% csrf_token %}
      {% if assignment.status %}
        <input type="checkbox" checked onclick='assignmentFinish("False","{{assignment.id}}")'>
      {% else %}
        <input type="checkbox" onclick='assignmentFinish("True","{{assignment.id}}")'>
      {% endif %}
    </form>
  </td>

  <td><h5><span class="badge badge-{{assignment.module.colour}}">{{assignment.module}}</span></td>

  <td><a href="{{ assignment.assigmentFile.url }}">{{assignment.title}}</a></td>
  
  <td>{{assignment.deadline}}</td>
  ...
</tr>
{% endfor %}
function assignmentFinish(value,assignment) {
    link = "{% url 'uni:finish-assignment' %}";
    $.ajax({
      type:'POST',
      url: link,
      data:{
        status: value,
        assignmentID: assignment,
        csrfmiddlewaretoken:$('input[name=csrfmiddlewaretoken]').val()
      },
      success: function(){
      }
    });
}

  
def finishAssignment(request):
    # Get the product that user has wished for
    assignmentID = request.POST['assignmentID']
    status = request.POST['status']
    assignment = Assignment.objects.get(pk=assignmentID)

    print(status)
    if status == 'True':
        print("saving to true")
        assignment.status = True
    else:
        print("saving to false")
        assignment.status = False

    assignment.save()
    return HttpResponse('')
enter code here
视图。py:

{% for assignment in assignments %}

<tr>
  <td scope="row" style="text-align: center">
    <form>
    {% csrf_token %}
      {% if assignment.status %}
        <input type="checkbox" checked onclick='assignmentFinish("False","{{assignment.id}}")'>
      {% else %}
        <input type="checkbox" onclick='assignmentFinish("True","{{assignment.id}}")'>
      {% endif %}
    </form>
  </td>

  <td><h5><span class="badge badge-{{assignment.module.colour}}">{{assignment.module}}</span></td>

  <td><a href="{{ assignment.assigmentFile.url }}">{{assignment.title}}</a></td>
  
  <td>{{assignment.deadline}}</td>
  ...
</tr>
{% endfor %}
function assignmentFinish(value,assignment) {
    link = "{% url 'uni:finish-assignment' %}";
    $.ajax({
      type:'POST',
      url: link,
      data:{
        status: value,
        assignmentID: assignment,
        csrfmiddlewaretoken:$('input[name=csrfmiddlewaretoken]').val()
      },
      success: function(){
      }
    });
}

  
def finishAssignment(request):
    # Get the product that user has wished for
    assignmentID = request.POST['assignmentID']
    status = request.POST['status']
    assignment = Assignment.objects.get(pk=assignmentID)

    print(status)
    if status == 'True':
        print("saving to true")
        assignment.status = True
    else:
        print("saving to false")
        assignment.status = False

    assignment.save()
    return HttpResponse('')
enter code here
型号.py

class Assignment(models.Model):
    owner = models.ForeignKey(User, on_delete=models.CASCADE)
    title = models.CharField(max_length=100)
    course = models.ForeignKey(Course, on_delete=models.CASCADE, default=None)
    module = models.ForeignKey(Module, on_delete=models.CASCADE)
    deadline = models.DateField()
    assignmentFile = models.FileField(default=None)
    status = models.BooleanField()
此解决方案将工作一次,但一旦用户再次单击复选框,它将不会将信息保存在数据库中。例如,如果用户反复单击最初未选中的复选框,则打印语句如下:

True
saving to true
[15/Jul/2020 16:11:51] "POST /uni/finishAssignment HTTP/1.1" 200 0
True
saving to true
[15/Jul/2020 16:11:52] "POST /uni/finishAssignment HTTP/1.1" 200 0
True
saving to true

它显示正在调用ajax请求,但是print语句应该在true和false之间交替。这可能是因为在第一次将新值保存到数据库中后,显示复选框的页面上的信息没有更新。如何修复此问题?

问题在于您是如何构建此问题的。我会就正在发生的事情和解决方案向您提供建设性的反馈

你提到

一,

例如,如果用户反复单击最初未选中的复选框,则打印语句如下:

True
saving to true
[15/Jul/2020 16:11:51] "POST /uni/finishAssignment HTTP/1.1" 200 0
True
saving to true
[15/Jul/2020 16:11:52] "POST /uni/finishAssignment HTTP/1.1" 200 0
True
saving to true
这是
True
,因为此
将调用值为
True
ajax
请求。在
views.py
中,它将执行以下块

if status == 'True':
   print("saving to true")
   assignment.status = True
因此,上面显示的打印行为是完全正常的,因为该块将被重复执行

二,

但是打印的语句应该是真假交替的。原因可能是显示复选框的页面上的信息未更新

这是正确的,因为您不会在任何地方更新复选框的值,并且您总是假定值最终为
true
false

解决方案: 要解决这个问题,您需要修改
js
函数,使其将
元素作为第一个参数,将
assignment.id
作为第二个参数。在此范围内,您需要使用属性直接获取复选框的值来更新
状态
参数

  <td scope="row" style="text-align: center">
    <form>
    {% csrf_token %}
      {% if assignment.status %}
        <input type="checkbox" checked onclick='assignmentFinish(this,"{{assignment.id}}")'>
      {% else %}
        <input type="checkbox" onclick='assignmentFinish(this,"{{assignment.id}}")'>
      {% endif %}
    </form>
  </td>

现在,您将传递复选框的实际值,它的行为应符合您的预期。

问题在于您是如何构建此复选框的。我会就正在发生的事情和解决方案向您提供建设性的反馈

你提到

一,

例如,如果用户反复单击最初未选中的复选框,则打印语句如下:

True
saving to true
[15/Jul/2020 16:11:51] "POST /uni/finishAssignment HTTP/1.1" 200 0
True
saving to true
[15/Jul/2020 16:11:52] "POST /uni/finishAssignment HTTP/1.1" 200 0
True
saving to true
这是
True
,因为此
将调用值为
True
ajax
请求。在
views.py
中,它将执行以下块

if status == 'True':
   print("saving to true")
   assignment.status = True
因此,上面显示的打印行为是完全正常的,因为该块将被重复执行

二,

但是打印的语句应该是真假交替的。原因可能是显示复选框的页面上的信息未更新

这是正确的,因为您不会在任何地方更新复选框的值,并且您总是假定值最终为
true
false

解决方案: 要解决这个问题,您需要修改
js
函数,使其将
元素作为第一个参数,将
assignment.id
作为第二个参数。在此范围内,您需要使用属性直接获取复选框的值来更新
状态
参数

  <td scope="row" style="text-align: center">
    <form>
    {% csrf_token %}
      {% if assignment.status %}
        <input type="checkbox" checked onclick='assignmentFinish(this,"{{assignment.id}}")'>
      {% else %}
        <input type="checkbox" onclick='assignmentFinish(this,"{{assignment.id}}")'>
      {% endif %}
    </form>
  </td>
现在,您将传递复选框的实际值,它的行为应符合您的预期