Django:如何增加存储在 models.py / 数据库中的计数器

Django: How to increment a counter stored in models.py / Database

我创建了一个小型计数器模型 class Counter 来存储完成小型调查应用程序的次数。

我想从 views.py

中的 def done() 方法中增加 models.py 中的 SurveyWizardOneCounter

谁能告诉我怎么做?

以前我为我的计数器使用全局变量,我发现它不能与网络应用程序一起正常工作。我正在尝试学习如何在我的数据库中创建和存储计数器。任何帮助表示赞赏。

models.py

class Counter(models.Model):                
    SurveyWizardOneCounter = models.SmallIntegerField()
    TotalMaxCounter = models.SmallIntegerField() 

views.py

from survey.models import Counter

def done(self, form_list, **kwargs):

    Counter.SurveyWizardOneCounter += 1  # This is where I am trying to increment the counter

    logger.debug('\n\n SurveyWizardOneCounter = %s', SurveyWizardOneCounter)

    for form in form_list:
        form.save()

    return render(self.request, 'Return_to_AMT.html', {
        'form_data': [form.cleaned_data for form in form_list],            
    })  

我假设您的 Counter 模型将只存储一条记录。

c = Counter.objects.get()
c.SurveyWizardOneCounter += 1
# Update another attributes if you need
c.save()

或者也许

from django.db.models import F

Counter.objects.filter().update(SurveyWizardOneCounter=F('SurveyWizardOneCounter')+1)

由于您有 9 个不同的调查计数器,并且您需要在提交调查时递增每个计数器,因此最好定义一个字段 survey_wizard_type,其可能值为 survey_wizard_onesurvey_wizard_twosurvey_wizard_nine 和一个具有默认值 0 的字段 survey_wizard_count,用于存储该特定调查向导的计数。那么 Counter 模型在你的数据库中会有 9 条记录。

models.py

SURVEY_WIZARD_TYPE_CHOICES = ['survey_wizard_one', 'survey_wizard_two', 'survey_wizard_three', 'survey_wizard_four', 'survey_wizard_five', 'survey_wizard_six', 'survey_wizard_seven', 'survey_wizard_eight', 'survey_wizard_nine']

class Counter(models.Model): 

    survey_wizard_type = models.CharField(choices=SURVEY_WIZARD_TYPE_CHOICES)
    survey_wizard_count = models.SmallIntegerField(default=0)
    total_max_counter = models.SmallIntegerField() 

然后在您的 views.py 中,您可以使用 get_or_create 方法查找具有给定 survey_wizard_typeCounter 对象,必要时创建一个。然后将 survey_wizard_count 递增 1 并将该对象保存到数据库中。

views.py

from django.db.models import F
from survey.models import Counter

def done(self, form_list, **kwargs):

    survey_counter = Counter.objects.get_or_create(survey_wizard_type= 'survey_wizard_x') # x can be any value from one to nine
    survey_counter.survey_wizard_count = F('survey_wizard_count') + 1 
    survey_counter.save()

    logger.debug('\n\n SurveyWizardOneCounter = %s', SurveyWizardOneCounter)

    for form in form_list:
        form.save()

    return render(self.request, 'Return_to_AMT.html', {
        'form_data': [form.cleaned_data for form in form_list],            
    })   

编辑

Rahul 提供了解决方案,但这是我最终使用的代码

models.py

class Counter(models.Model):

    SURVEY_WIZARD_TYPE_CHOICES = (
                              ('SURVEY_WIZARD_ONE', 'survey_wizard_one'),
                              ('SURVEY_WIZARD_TWO', 'survey_wizard_two'), 
                              ('SURVEY_WIZARD_THREE', 'survey_wizard_three'), 
                              ('SURVEY_WIZARD_FOUR', 'survey_wizard_four'), 
                              ('SURVEY_WIZARD_FIVE', 'survey_wizard_five'),
                              ('SURVEY_WIZARD_SIX', 'survey_wizard_six'), 
                              ('SURVEY_WIZARD_SEVEN', 'survey_wizard_seven'),
                              ('SURVEY_WIZARD_EIGHT', 'survey_wizard_eight'),
                              ('SURVEY_WIZARD_NINE', 'survey_wizard_nine'),
                              )   

    survey_wizard_type = models.CharField(max_length=1000, choices=SURVEY_WIZARD_TYPE_CHOICES)
    survey_wizard_count = models.SmallIntegerField(default=0)
    total_max_counter = models.SmallIntegerField(default=0) 

views.py

def done(self, form_list, **kwargs):

    survey_counter = Counter.objects.get_or_create(survey_wizard_type= 'survey_wizard_one')[0] # x can be any value from one to nine
    survey_counter.survey_wizard_count = F('survey_wizard_count') + 1 
    survey_counter.save()

    for form in form_list:
        form.save()

    return render(self.request, 'Return_to_AMT.html', {
        'form_data': [form.cleaned_data for form in form_list],            
    }) 

您应该确保使用原子方法更新字段,上面的一些答案可能在更新和保存之间存在竞争条件。 Django documentation建议使用以下方法:

from django.db.models import F
product = Product.objects.get(name='Venezuelan Beaver Cheese')
product.number_sold = F('number_sold') + 1
product.save()