Django - Вызов функции в ListView или модели для изменения состояния bolean модели

Я хочу вызвать функцию - из модели или из Listview, которая будет изменять состояние Order.isDone - TRUE или FALSE после нажатия на кнопку в шаблоне.

Model.py:

class Order(models.Model):
    isDone = models.BooleanField(default=False, verbose_name='Zrealizowane')
 

views.py:

class OrderListView (ListView):
  model = Order
  template_name = 'orders/orders_list.html'
  ordering = ['-orderDate']

urls.py:

urlpatterns = [
    path('', views.home, name='page-home'),
    path('orders_list/', OrderListView.as_view(), name='page-orders-list'),
    path('completed_orders_list/', OrderCompletedListView.as_view(), name='page-completed-orders-list'),
    path('orders/order_create/', OrderCreateView.as_view(), name='page-order-create'),
    path('orders/<int:pk>/delete/', OrderDeleteView.as_view(), name='page-order-delete'),
]

template:

      <tbody>
        {% for order in object_list %}
          {% if order.isDone == False %}
          <tr>
            <td>
              <button type="button" class="btn btn-secondary" data-toggle="modal" data-target="#exampleModalCenter">Szczegóły</button>
              <form action="{% url 'page-orders-list' order.id %}" method="post">
                {% csrf_token %}
                <button class="btn btn-info btn-sm">Finish order</button>
              <form>
              <a class="btn btn-danger adminButton" href="{% url 'page-order-delete' order.id %}">Usuń</a>
            </td>
          </tr>
          {% endif %}
        {% endfor %}
      </tbody>
    </table>
  </div>

{% endblock %}

Какой самый простой способ сделать это?

Я предлагаю использовать для этого другое представление. Вы можете использовать метод get в представлении для изменения статуса заказа. В вашем HTML вам нужно будет использовать только ссылку вместо формы.

То есть что-то вроде этого:

views.py

class OrderFinishView(RedirectView):
  success_url = None  # After finishing the order, where do you want to redirect the user?
  
  def get(self, request, *args, **kwargs):
     order_id = self.kwargs['pk_order']  # pk_order must be in your URL
     order = get_object_or_404(Order, pk=order_id)

     order.is_done = True
     order.save()

     return super().get(request, *args, **kwargs)

urls.py

urlpatterns = [
    path('', views.home, name='page-home'),
    path('orders_list/', OrderListView.as_view(), name='page-orders-list'),
    path('completed_orders_list/', OrderCompletedListView.as_view(), name='page-completed-orders-list'),
    path('orders/order_create/', OrderCreateView.as_view(), name='page-order-create'),
    path('orders/<int:pk>/delete/', OrderDeleteView.as_view(), name='page-order-delete'),
    path('orders/<int:pk_order>/finish', OrderFinishView.as_view(), name='page-order-finish'),
]

шаблон

      <tbody>
        {% for order in object_list %}
          {% if order.isDone == False %}
          <tr>
            <td>
                <a href={% url 'page-order-finish' order.id %}>Finish</a>
            </td>
          </tr>
          {% endif %}
        {% endfor %}
      </tbody>
    </table>
  </div>

{% endblock %}

Другая идея - использовать UpdateView для обновления заказа с помощью PartialOrderForm, которая будет содержать только поле is_done.

Я использую решение @vinkomlacic solutionhave, но изменил функцию get:

  def get(self, request, *args, **kwargs):
      order_id = self.kwargs['pk_order']  # pk_order must be in your URL
      order = get_object_or_404(Order, pk=order_id)
      order.isDone = True
      order.save()
      return redirect(self.success_url)

Похоже, теперь все работает правильно после установки success_url в классе

Вернуться на верх