Reputation: 257
I have a Django REST API endpoint with this structure, that I need to post to an external API:
{
"body": [
"...",
"...",
"...",
],
"title": [
"...",
"...",
"...",
],
"id": [
"...",
"...",
"...",
]
}
The first item under 'body' goes with the first under 'title' and 'id', and so forth.
The problem I'm having is that the API in question expects JSON data with the following structure:
{
"texts": [
{
"body": "...",
"title": "...",
"id": "..."
},
{
"body": "...",
"title": "...",
"id": "..."
},
{
"body": "...",
"title": "...",
"id": "..."
},
],
"language": "EN",
}
And I can't figure out how have my endpoint mirror that structure, with the bodies
, titles
, and ids
grouped together, those groupings nested under texts
, and with the language
parameter appended at the end.
The serializer I'm using in my views.py
looks as follows:
class MyReasonsSerializer(serializers.Serializer):
body = serializers.SerializerMethodField()
title = serializers.SerializerMethodField()
id = serializers.SerializerMethodField()
def get_body(self, obj):
return obj.reasons.order_by('transaction_date').values_list('body', flat=True)
def get_title(self, obj):
return obj.reasons.order_by('transaction_date').values_list('title', flat=True)
def get_id(self, obj):
return obj.reasons.order_by('transaction_date').values_list('transaction_date', flat=True)
class ReasonsData(RetrieveAPIView):
queryset = Market.objects.all().prefetch_related('reasons')
authentication_classes = []
permission_classes = []
serializer_class = MyReasonsSerializer
Thanks in advance for any advice!
EDIT:
Here are the models:
class Market(models.Model):
title = models.CharField(max_length=50, default="")
current_price = models.DecimalField(max_digits=5, decimal_places=2, default=0.50)
description = models.TextField(default="")
...
language = models.CharField(max_length=2, default="EN")
def __str__(self):
return self.title[:50]
class Reason(models.Model):
user_id = models.ForeignKey('users.CustomUser',
on_delete=models.CASCADE,
related_name='user_reasons',
default=None)
market = models.ForeignKey(
Market,
on_delete=models.CASCADE,
related_name='reasons',
default=None)
...
valence = models.CharField(max_length=11, default="")
title = models.TextField(default="")
body = models.TextField(default="")
def __str__(self):
return str(self.title)
Upvotes: 1
Views: 303
Reputation: 851
I would structure it like this... (its hard to know exactly without seeing the models and trying it out)
class ReasonSerializer(serializers.ModelSerializer):
class Meta:
model = Reason
fields = ("id", "body", "title")
class MarketSerializer(serializers.Serializer):
texts = ReasonSerializer(many=True, source="reasons")
language = serializers.CharField()
class Meta:
model = Market
class ReasonsData(RetrieveAPIView):
queryset = Market.objects.all()
authentication_classes = []
permission_classes = []
serializer_class = MarketSerializer
def get_queryset(self):
qs = super().get_queryset()
# filter queryset by valence if passed as a query param
# ?valence=something
valence = self.request.query_params.get("valence", None)
if valence is not None:
qs = qs.filter(reasons__valence=valence)
return qs
Upvotes: 1