Coverage for apis_core/history/serializers.py: 48%
71 statements
« prev ^ index » next coverage.py v7.5.3, created at 2025-09-03 06:15 +0000
« prev ^ index » next coverage.py v7.5.3, created at 2025-09-03 06:15 +0000
1from drf_spectacular.types import OpenApiTypes
2from drf_spectacular.utils import extend_schema_field
3from rest_framework import serializers
6class ModelChangeSerializer(serializers.Serializer):
7 field = serializers.CharField()
8 old = serializers.SerializerMethodField(method_name="get_field_data_old")
9 new = serializers.SerializerMethodField(method_name="get_field_data_new")
11 def get_data_for_m2m_field(self, value, field):
12 sst = [
13 str(obj2)
14 for obj2 in field.related_model.objects.filter(
15 pk__in=[obj3[field.attname] for obj3 in value]
16 )
17 ]
18 return " | ".join(sst)
20 def get_field_data(self, obj, new: bool):
21 if new:
22 value = obj.new
23 else:
24 value = obj.old
25 if obj.field in [x.name for x in self._parent_object._meta.local_fields]:
26 field = self._parent_object._meta.get_field(obj.field)
27 if field.is_relation and value is not None:
28 return str(getattr(self._args[1], obj.field))
29 return value
30 else:
31 for field in self._parent_object._history_m2m_fields:
32 if field.attname == obj.field:
33 return self.get_data_for_m2m_field(value, field)
34 return obj
36 def get_field_data_new(self, obj):
37 repr = self.get_field_data(obj, True)
38 return repr
40 def get_field_data_old(self, obj):
41 repr = self.get_field_data(obj, False)
42 return repr
44 def __init__(self, instance=None, parent_object=None, **kwargs):
45 self._parent_object = parent_object
46 super().__init__(instance, **kwargs)
49class HistoryLogSerializer(serializers.Serializer):
50 diff = serializers.SerializerMethodField()
51 timestamp = serializers.DateTimeField(source="history_date")
52 user = serializers.CharField(source="history_user")
53 action = serializers.SerializerMethodField()
54 model = serializers.CharField(source="instance.__class__.__name__")
55 module = serializers.CharField(source="instance.__class__._meta.app_label")
56 instance = serializers.CharField()
57 object_id = serializers.IntegerField(source="id")
58 history_id = serializers.IntegerField()
60 @extend_schema_field(OpenApiTypes.OBJECT)
61 def get_diff(self, obj):
62 if obj.history_type == "-":
63 return None
64 changed_fields = []
65 changes = []
66 for change in obj.get_diff():
67 changed_fields.append(change.field)
68 changes.append(ModelChangeSerializer(change, obj).data)
69 return {"changed_fields": changed_fields, "changes": changes}
71 def get_action(self, obj) -> str:
72 match obj.history_type:
73 case "+":
74 return "created"
75 case "~":
76 return "changed"
77 case "-":
78 return "deleted"
81class HistoryObjectSerializer(serializers.Serializer):
82 history = serializers.SerializerMethodField()
83 model = serializers.CharField(source="__class__.__name__")
84 module = serializers.CharField(source="_meta.app_label")
85 instance = serializers.SerializerMethodField()
86 object_id = serializers.IntegerField(source="id")
88 def get_instance(self, obj) -> str:
89 return str(obj)
91 @extend_schema_field(HistoryLogSerializer(many=True))
92 def get_history(self, obj):
93 return HistoryLogSerializer(obj.get_history_data(), many=True).data