首页 > 解决方案 > Django Rest Framework如何在models.CharField上设置error_messages

问题描述

你好!

总结问题

我有一个 Django Rest Framework 后端,我想做一件简单的事情:更改默认验证消息

'max_length': _('Ensure this field has no more than {max_length} characters.'),

对于像这样的自定义

'max_length': 'I am happy to see you {max_length}.'

失败的方法在这篇文章的底部

最小的例子:

您可以从git repo中提取一个最小示例,并通过调用此文件来运行测试。

from django.contrib.auth.models import (
AbstractBaseUser,
PermissionsMixin,
)
from django.db import models
from rest_framework import serializers


class User(AbstractBaseUser, PermissionsMixin):
    name = models.CharField("Name", max_length=42, null=True, 
        error_messages={'max_length':"I am happy to see you {max_length}."})

class UserSerializer(serializers.ModelSerializer):

    class Meta:
        model = User
        fields = ["name"]
        extra_kwargs = {
            "name": {"required": True, "allow_blank": False, "allow_null": False},
    }

class TestUserSerializer:
    def test_name() -> None:
        data = {
            "name": "A" * 43,
            }
        serializer = UserSerializer(data=data)
        assert serializer.is_valid() is False
        assert str(serializer.errors["name"][0]) == "I am happy to see you 42."

错误消息似乎被忽略了。

什么失败了:

标签: pythondjangodjango-rest-framework

解决方案


随意git am。提交消息中的解释。

还修复了值的显示并添加了一个测试以确保覆盖在模型级别工作。

From b5e0b90d8aea9348ef0de7624ad1460c06a2c44e Mon Sep 17 00:00:00 2001
From: Melvyn <melvyn@stackexchange.site>
Date: Sat, 20 Mar 2021 00:30:29 +0100
Subject: [PATCH] fix(main): Add error_messages to serializer

Apparently the ModelSerializer doesn't copy the error_messages attribute
from the model field, so we have to do that by hand.
---
 stack_example/tests/test_user.py  | 9 +++++++++
 stack_example/user/models.py      | 2 +-
 stack_example/user/serializers.py | 5 ++---
 3 files changed, 12 insertions(+), 4 deletions(-)

diff --git a/stack_example/tests/test_user.py b/stack_example/tests/test_user.py
index 5aeba74..8493dc1 100644
--- a/stack_example/tests/test_user.py
+++ b/stack_example/tests/test_user.py
@@ -1,5 +1,14 @@
 import pytest
 from user.serializers import UserSerializer
+from user.models import User
+from django.core.exceptions import ValidationError
+
+def test_model():
+    user = User(name="A" * 43)
+    try:
+        user.clean_fields()
+    except ValidationError as e:
+        assert e.message_dict['name'][0] == "I am happy to see you 42."
 
 class TestUserSerializer():
     def test_name(self) -> None:
diff --git a/stack_example/user/models.py b/stack_example/user/models.py
index 2d03e7a..7d92470 100644
--- a/stack_example/user/models.py
+++ b/stack_example/user/models.py
@@ -8,4 +8,4 @@ from django.contrib.auth.models import (
 
 class User(AbstractBaseUser, PermissionsMixin):
     name = models.CharField("Name", max_length=42, null=True, 
-        error_messages={'max_length':"I am happy to see you {max_length}."})
+        error_messages={'max_length':"I am happy to see you %(limit_value)s."})
diff --git a/stack_example/user/serializers.py b/stack_example/user/serializers.py
index ddd86ce..704f844 100644
--- a/stack_example/user/serializers.py
+++ b/stack_example/user/serializers.py
@@ -2,10 +2,9 @@ from rest_framework import serializers
 from user.models import User 
 
 class UserSerializer(serializers.ModelSerializer):
-
     class Meta:
         model = User
         fields = ["name"]
         extra_kwargs = {
-            "name": {"required": True, "allow_blank": False, "allow_null": False},
-    }
+            "name": {"required": True, "allow_blank": False, "allow_null": False, "error_messages": User._meta.get_field('name').error_messages},
+        }
-- 
2.20.1 (Apple Git-117)

解决方案可以在github上浏览


推荐阅读