创建模型对象时触发IntegrityError:Evaluation_data_id非空约束违规
解决IntegrityError:"列'Evaluation_data_id'存在空值,违反非空约束"的问题
你遇到的核心问题是创建EvaluatorModel时没有正确关联对应的EvaluationModel实例,导致evaluation_data这个主键字段为空,触发了数据库的非空约束。咱们一步步来修复:
1. 修正EvaluatorModel的字段设计
你现在用CharField存储evaluee、evaluator的方式不太合理——既然这些是关联User模型的,应该用ForeignKey和EvaluationModel保持一致,这样能保证数据一致性,也方便后续的关联查询。另外evaluation_data作为OneToOneField且是主键,不需要设置default=""(这对关联字段无效),也不需要db_constraint=False(除非你有特殊业务需求,否则保留数据库约束更安全)。
修改后的EvaluatorModel代码:
class EvaluatorModel(models.Model): evaluation_data = models.OneToOneField( EvaluationModel, on_delete=models.CASCADE, primary_key=True, related_name="evaluationdata", verbose_name="关联评估数据" ) # 改为关联User模型,和EvaluationModel保持一致 evaluee = models.ForeignKey( get_user_model(), on_delete=models.CASCADE, related_name='+', verbose_name='Evaluee', ) evaluator = models.ForeignKey( get_user_model(), on_delete=models.CASCADE, related_name='+', verbose_name='Evaluator', ) dgl = models.ForeignKey( get_user_model(), on_delete=models.CASCADE, related_name='+', verbose_name='DGL', ) currentrole = models.CharField(max_length=100) # 保留你原有字段,可根据实际调整长度 tenure = models.CharField(max_length=50) # 同理 def __str__(self): # 用用户的用户名显示,比纯字符拼接更友好 return f"{self.evaluee.username} - {self.evaluator.username}"
2. 修复EvaluationModel的save方法
原来的save方法创建EvaluatorModel时,没有传入evaluation_data字段,这就是导致空值错误的直接原因。你需要把当前保存的EvaluationModel实例传给这个字段:
修改后的EvaluationModel代码:
class EvaluationModel(models.Model): evaluee = models.ForeignKey( get_user_model(), on_delete=models.CASCADE, related_name='+', verbose_name='Evaluee', ) evaluator = models.ForeignKey( get_user_model(), on_delete=models.CASCADE, related_name='+', verbose_name='Evaluator', ) dgl = models.ForeignKey( get_user_model(), on_delete=models.CASCADE, related_name='+', verbose_name='DGL', ) currentrole = models.CharField(max_length=100) # 保留你的其他业务字段 tenure = models.CharField(max_length=50) def save(self, *args, **kwargs): created = not self.pk super().save(*args,**kwargs) if created: # 关键:添加evaluation_data=self,关联当前的EvaluationModel实例 EvaluatorModel.objects.create( evaluation_data=self, evaluee=self.evaluee, evaluator=self.evaluator, dgl=self.dgl, currentrole=self.currentrole, tenure=self.tenure )
3. 同步数据库结构
修改完模型后,别忘了生成并应用迁移,让数据库结构同步更新:
python manage.py makemigrations python manage.py migrate
报错原因复盘
- 你把
evaluation_data设为了EvaluatorModel的主键,主键默认是非空且唯一的,但创建EvaluatorModel时没有给这个字段赋值,数据库就会抛出IntegrityError。 - 原来用
CharField存储用户关联,不仅没法利用ORM的关联查询优势,还可能出现数据不一致(比如用户用户名修改后,这里的字段不会自动更新)。
这样修改后,每次创建EvaluationModel时,都会自动创建关联的EvaluatorModel,并且正确填充所有字段,应该就能解决你遇到的空值约束问题了。
内容的提问来源于stack exchange,提问作者marchibello
相关产品推荐
相关产品推荐

