【发布时间】:2020-06-18 12:20:55
【问题描述】:
我正在尝试将删除时的外键引用从级联更改为 null,如下所示:
created_by = models.ForeignKey(CustomUser,on_delete=models.SET_NULL, null=True)
当我通过从 CustomUser 中删除记录来测试这一点时,我会在执行删除之前和之后获得 Games 表中对象的计数。
p = Games.objects.count()
print(p) #outputs 100
print(Games.objects.filter(created_by=2)) #outputs <QuerySet [<Games: 181 79 None>]>
cu = CustomUser.objects.get(pk=2)
cu.delete()
p = Games.objects.count()
print(p) #outputs 98
print(Games.objects.filter(created_by=2)) # outputs <QuerySet []>
我尝试使用其他值进行删除,但唯一不从数据库中删除行的值是保护。相反,它会引发保护错误
raise ProtectedError(
django.db.models.deletion.ProtectedError: ("Cannot delete some instances of model 'CustomUser' because they are referenced through a protected foreign key: 'Games.created_by'", <QuerySet [<Games: 181 79 None>]>)
CustomUser 和 Games 模型的代码
class CustomUser(AbstractBaseUser, PermissionsMixin):
id = models.BigAutoField(primary_key=True)
username = models.CharField(max_length=15, unique=True)
email = models.EmailField(max_length=128, unique=True)
password = models.CharField(max_length=254)
salt = models.CharField(max_length=128)
email_verified = models.BooleanField(default=False)
avatar = models.ImageField(blank=True, null=True)
date_joined = models.DateTimeField(default=timezone.now)
last_updated = models.DateTimeField(blank=True, null=True)
is_active = models.BooleanField(default=False)
is_staff = models.BooleanField(default=False)
USERNAME_FIELD = 'email'
objects = CustomUserManager()
def __str__(self):
return self.email
class Games(models.Model):
CATEGORY = (
('general knowledge','general knowledge'),
('science','science'),
('mythology','mythology'),
('sports','sports'),
('geography','geography'),
('history','history'),
('politics','politics'),
('art','art'),
('celebrities','celebrities'),
('animals','animals'),
('vehicles','vehicles'),
('entertainment','entertainment'),
('random','random')
)
id = models.BigAutoField(primary_key=True)
number_of_questions = models.SmallIntegerField()
number_of_players = models.SmallIntegerField()
start_time = models.DateTimeField(default=timezone.now)
category = models.CharField(max_length=18, choices=CATEGORY)
created_by = models.ForeignKey(CustomUser,on_delete=models.SET_NULL, null=True)
result_id = models.ForeignKey(Results, on_delete=models.CASCADE, null=True, blank=True)
sudden_death_id = models.ForeignKey(SuddenDeath, on_delete=models.CASCADE, null=True, blank=True)
objects = models.Manager()
def __str__(self):
return '%s %s %s' % (self.id, self.result_id, self.sudden_death_id)
【问题讨论】:
-
你的 Django 版本是多少?
-
@LucasWieloch 3.0.7
-
models.SET_NULL的外键参数是正确的。您确定您的迁移是最新的吗? -
@LucasWieloch 是的,我只是仔细检查了一下,我的迁移是最新的
-
好吧,我会提示您在删除之前通过将游戏 pks 连接到
cu来测试它,并在删除后执行Games.objects.filter(pk__in=game_pks)以确保记录仍然存在。除此之外,我建议您发布一个带有更大代码 sn-p 的示例,因为无论错误是什么,它都可能超出您问题中块的范围
标签: django django-models