Skip to main content

更新订单状态

在本节中,我们将介绍如何使用Django和Celery定时任务来自动更新订单表中的订单状态。我们将创建一个定时任务,每隔一定时间检查所有订单的状态是否过期,如果过期则将其更改为已关闭。

步骤

1. 创建任务函数

在我们的trade应用的tasks.py文件中,我们定义一个名为batch_check_expired_time_orders的任务函数。该函数将获取所有未支付的订单,并遍历每个订单调用另一个函数check_order_expired来检查订单是否过期。我们使用异步方法delay来调用检查订单过期函数。

dx_movie/trade/tasks.py
from datetime import timedelta

from django.utils import timezone
from celery import shared_task

from .models import Order


@shared_task
def batch_check_expired_orders():
orders = Order.objects.filter(pay_status='PAYING')
for order in orders:
check_order_expired.delay(order.id)

2. 检查订单过期函数

在我们的trade应用的tasks.py文件中,我们定义一个名为check_order_expired的函数,该函数将根据给定的订单ID来检查订单是否过期。我们使用订单的下单时间加上一个自定义的时间间隔来判断订单是否过期。如果订单过期,则将订单状态更改为已关闭,否则不做处理。

dx_movie/trade/tasks.py
from datetime import timedelta
from django.utils import timezone
from celery import shared_task
from .models import Order

@shared_task
def check_order_expired(order_id):
order = Order.objects.get(id=order_id)
expired_time = order.pay_time + timedelta(minutes=30)
if timezone.now() > expired_time:
order.pay_status = 'TRADE_CLOSED'
order.save()
return f'order {order.id} 过期,订单状态:close'
else:
return f'order {order.id}未过期,订单状态:paying'

@shared_task
def batch_check_expired_orders():
orders = Order.objects.filter(pay_status='PAYING')
for order in orders:
check_order_expired.delay(order.id)

3. 配置定时任务

在Django的后台管理页面中,我们选择"周期性任务"并点击"添加"按钮。如下图所示。 图87-添加检查订单任务

我们选择之前创建的batch_check_expired_time_orders任务,并设置适当的时间间隔(如每隔30秒执行一次)。 图88-设置周期时间

我们不需要为任务传递参数,所以在"参数"字段中留空。保存配置。

4. 启动任务

启动Celery以及Celery Beat服务,使定时任务生效。

图88-重启celery

图88-重启celery-beat

图88-重启flower

5. 检查订单状态

定时任务会每隔一定时间执行一次,检查订单的过期状态,并将过期的订单状态更改为已关闭。你可以在Celery Beat的界面上查看每次任务执行的时间点,以及任务的执行情况。

图88-订单状态发生变化

图88-订单页面状态变化

结论

通过以上步骤,我们成功地使用Django和Celery实现了定时任务来自动更新订单表中的订单状态。每隔一定时间,定时任务会检查订单的过期状态,并将过期的订单状态更改为已关闭,从而确保订单状态的准确性和及时性。

注意:以上代码仅为示例,具体实现根据项目需求进行调整和扩展。