How to return the whole object data with Django objects.filter?

I search for a user in my views:

user = User.objects.filter(id=id).first()
print(user)

This returns just the username of the user. I know I can access other data like the nickname with user.nickname but I need to make a json object of the user data and would like to know is there some way I can access the whole user object at once and not one by one?

Answer

There are many ways to convert an instance to a dictionary.


1. instance.__dict__

instance.__dict__

which returns

{'_state': <django.db.models.base.ModelState object at 0x7fa91aacd850>, 'id': 1, 'password': 'pbkdf2_sha256$260000$EXJTbB1QbxdxNMyPeKiixS$ghD+e5KTTvUwGdoXWr02ocjq+1t7/a277pBxxDncgWE=', 'last_login': datetime.datetime(2021, 9, 10, 7, 5, 25, 542308, tzinfo=<UTC>), 'is_superuser': True, 'username': 'admin123', 'first_name': '', 'last_name': '', 'email': '', 'is_staff': True, 'is_active': True, 'date_joined': datetime.datetime(2021, 8, 25, 14, 23, 38, 892836, tzinfo=<UTC>)}

This is the simplest, but is missing many_to_many, foreign_key.


2. model_to_dict

from django.forms.models import model_to_dict
model_to_dict(instance)

which returns

{'_state': <django.db.models.base.ModelState object at 0x7fa91aacd850>, 'id': 1, 'password': 'pbkdf2_sha256$260000$EXJTbB1QbxdxNMyPeKiixS$ghD+e5KTTvUwGdoXWr02ocjq+1t7/a277pBxxDncgWE=', 'last_login': datetime.datetime(2021, 9, 10, 7, 5, 25, 542308, tzinfo=<UTC>), 'is_superuser': True, 'username': 'admin123', 'first_name': '', 'last_name': '', 'email': '', 'is_staff': True, 'is_active': True, 'date_joined': datetime.datetime(2021, 8, 25, 14, 23, 38, 892836, tzinfo=<UTC>)}


3. model_to_dict(instance, fields=instance_fields)

from django.forms.models import model_to_dict
model_to_dict(instance, fields=[field.name for field in instance._meta.fields])

which returns

{'id': 1, 'password': 'pbkdf2_sha256$260000$EXJTbB1QbxdxNMyPeKiixS$ghD+e5KTTvUwGdoXWr02ocjq+1t7/a277pBxxDncgWE=', 'last_login': datetime.datetime(2021, 9, 10, 7, 5, 25, 542308, tzinfo=<UTC>), 'is_superuser': True, 'username': 'admin123', 'first_name': '', 'last_name': '', 'email': '', 'is_staff': True, 'is_active': True, 'date_joined': datetime.datetime(2021, 8, 25, 14, 23, 38, 892836, tzinfo=<UTC>)}

This is strictly worse than the standard model_to_dict invocation.


4. Use Serializers

Django Rest Framework‘s ModelSerialzer allows you to build a serializer automatically from a model.

from rest_framework import serializers


class SomeModelSerializer(serializers.ModelSerializer):
     class Meta:
         model = SomeModel
         fields = "__all__"

SomeModelSerializer(instance).data

which returns

{'field1': 'value1', 'field1': 'value2'}