0
0
mirror of https://github.com/django/django.git synced 2024-11-21 19:09:18 +01:00

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`.
This commit is contained in:
Adam Zapletal 2024-11-09 21:20:22 -06:00 committed by Sarah Boyce
parent c12bc980e5
commit b9aa3239ab
3 changed files with 11 additions and 9 deletions

View File

@ -5,6 +5,7 @@ Requires PyYaml (https://pyyaml.org/), but that's checked for in __init__.
""" """
import collections import collections
import datetime
import decimal import decimal
import yaml import yaml
@ -12,7 +13,6 @@ import yaml
from django.core.serializers.base import DeserializationError from django.core.serializers.base import DeserializationError
from django.core.serializers.python import Deserializer as PythonDeserializer from django.core.serializers.python import Deserializer as PythonDeserializer
from django.core.serializers.python import Serializer as PythonSerializer from django.core.serializers.python import Serializer as PythonSerializer
from django.db import models
# Use the C (faster) implementation if possible # Use the C (faster) implementation if possible
try: try:
@ -44,17 +44,17 @@ class Serializer(PythonSerializer):
internal_use_only = False 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 # A nasty special case: base YAML doesn't support serialization of time
# types (as opposed to dates or datetimes, which it does support). Since # types (as opposed to dates or datetimes, which it does support). Since
# we want to use the "safe" serializer for better interoperability, we # we want to use the "safe" serializer for better interoperability, we
# need to do something with those pesky times. Converting 'em to strings # 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 # isn't perfect, but it's better than a "!!python/time" type which would
# halt deserialization under any other language. # halt deserialization under any other language.
if isinstance(field, models.TimeField) and getattr(obj, field.name) is not None: value = super()._value_from_field(obj, field)
self._current[field.name] = str(getattr(obj, field.name)) if isinstance(value, datetime.time):
else: value = str(value)
super().handle_field(obj, field) return value
def end_serialization(self): def end_serialization(self):
self.options.setdefault("allow_unicode", True) self.options.setdefault("allow_unicode", True)

View File

@ -245,8 +245,9 @@ class SmallPKData(models.Model):
# class TextPKData(models.Model): # class TextPKData(models.Model):
# data = models.TextField(primary_key=True) # 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): class UUIDData(models.Model):

View File

@ -69,6 +69,7 @@ from .models import (
Tag, Tag,
TextData, TextData,
TimeData, TimeData,
TimePKData,
UniqueAnchor, UniqueAnchor,
UUIDData, UUIDData,
UUIDDefaultData, UUIDDefaultData,
@ -390,7 +391,7 @@ The end.""",
# It contains line breaks. # It contains line breaks.
# Several of them. # Several of them.
# The end."""), # 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), (pk_obj, 791, UUIDData, uuid_obj),
(fk_obj, 792, FKToUUID, uuid_obj), (fk_obj, 792, FKToUUID, uuid_obj),
(pk_obj, 793, UUIDDefaultData, uuid_obj), (pk_obj, 793, UUIDDefaultData, uuid_obj),