summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAdam Zapletal <adamzap@gmail.com>2024-11-09 21:20:22 -0600
committerSarah Boyce <42296566+sarahboyce@users.noreply.github.com>2024-11-12 13:23:14 +0100
commitb9aa3239ab1328c915684d89b87a49459cabd30b (patch)
treed655dde080a41114bf747ec194694f2d16655a99
parentc12bc980e5b2bb25e447cd8dee550cad767f1ad2 (diff)
Refs #21286 -- Fixed YAML serialization of TimeField primary key.
Handling for PyYAML not being able to serialize `datetime.time` values is moved from `handle_field` to `_value_from_field` as only non-primary key, non-relation fields are passed into `handle_field`.
-rw-r--r--django/core/serializers/pyyaml.py12
-rw-r--r--tests/serializers/models/data.py5
-rw-r--r--tests/serializers/test_data.py3
3 files changed, 11 insertions, 9 deletions
diff --git a/django/core/serializers/pyyaml.py b/django/core/serializers/pyyaml.py
index ed6e4b3895..c72d1fa03b 100644
--- a/django/core/serializers/pyyaml.py
+++ b/django/core/serializers/pyyaml.py
@@ -5,6 +5,7 @@ Requires PyYaml (https://pyyaml.org/), but that's checked for in __init__.
"""
import collections
+import datetime
import decimal
import yaml
@@ -12,7 +13,6 @@ import yaml
from django.core.serializers.base import DeserializationError
from django.core.serializers.python import Deserializer as PythonDeserializer
from django.core.serializers.python import Serializer as PythonSerializer
-from django.db import models
# Use the C (faster) implementation if possible
try:
@@ -44,17 +44,17 @@ class Serializer(PythonSerializer):
internal_use_only = False
- def handle_field(self, obj, field):
+ def _value_from_field(self, obj, field):
# A nasty special case: base YAML doesn't support serialization of time
# types (as opposed to dates or datetimes, which it does support). Since
# we want to use the "safe" serializer for better interoperability, we
# need to do something with those pesky times. Converting 'em to strings
# isn't perfect, but it's better than a "!!python/time" type which would
# halt deserialization under any other language.
- if isinstance(field, models.TimeField) and getattr(obj, field.name) is not None:
- self._current[field.name] = str(getattr(obj, field.name))
- else:
- super().handle_field(obj, field)
+ value = super()._value_from_field(obj, field)
+ if isinstance(value, datetime.time):
+ value = str(value)
+ return value
def end_serialization(self):
self.options.setdefault("allow_unicode", True)
diff --git a/tests/serializers/models/data.py b/tests/serializers/models/data.py
index 212ea0e06f..bb76bfba48 100644
--- a/tests/serializers/models/data.py
+++ b/tests/serializers/models/data.py
@@ -245,8 +245,9 @@ class SmallPKData(models.Model):
# class TextPKData(models.Model):
# data = models.TextField(primary_key=True)
-# class TimePKData(models.Model):
-# data = models.TimeField(primary_key=True)
+
+class TimePKData(models.Model):
+ data = models.TimeField(primary_key=True)
class UUIDData(models.Model):
diff --git a/tests/serializers/test_data.py b/tests/serializers/test_data.py
index 33ea3458de..1f8f38ba0f 100644
--- a/tests/serializers/test_data.py
+++ b/tests/serializers/test_data.py
@@ -69,6 +69,7 @@ from .models import (
Tag,
TextData,
TimeData,
+ TimePKData,
UniqueAnchor,
UUIDData,
UUIDDefaultData,
@@ -390,7 +391,7 @@ The end.""",
# It contains line breaks.
# Several of them.
# The end."""),
- # (pk_obj, 770, TimePKData, datetime.time(10, 42, 37)),
+ (pk_obj, 770, TimePKData, datetime.time(10, 42, 37)),
(pk_obj, 791, UUIDData, uuid_obj),
(fk_obj, 792, FKToUUID, uuid_obj),
(pk_obj, 793, UUIDDefaultData, uuid_obj),