Reputation: 7304
I’m working through a book that introduces the Django and Django Rest frameworks. The tutorial creates a rest API with games, categories, players and scores, with a suitable relational model between them. I’ve stumbled upon an issue when inserting a game category I get the following error:
AttributeError at /game-categories/
'GameCategory' object has no attribute 'games'
Request Method: POST
Request URL: http://127.0.0.1:8000/game-categories/
Django Version: 1.10.5
Exception Type: AttributeError
Exception Value:
'GameCategory' object has no attribute 'games'
Exception Location: C:\Users\user\AppData\Local\Programs\Python\Python36-32\lib\site-packages\rest_framework\fields.py in get_attribute, line 103
Python Executable: C:\Users\user\AppData\Local\Programs\Python\Python36-32\python.exe
Python Version: 3.6.0
Python Path:
['C:\\Python\\Django01\\gamesapi',
'C:\\Users\\user\\AppData\\Local\\Programs\\Python\\Python36-32\\python36.zip',
'C:\\Users\\user\\AppData\\Local\\Programs\\Python\\Python36-32\\DLLs',
'C:\\Users\\user\\AppData\\Local\\Programs\\Python\\Python36-32\\lib',
'C:\\Users\\user\\AppData\\Local\\Programs\\Python\\Python36-32',
'C:\\Users\\user\\AppData\\Local\\Programs\\Python\\Python36-32\\lib\\site-packages']
Server time: Wed, 8 Mar 2017 09:40:42 +0000
My Game
and GameCategory
models are as follows:
class GameCategory(models.Model):
name = models.CharField(max_length=200)
class Meta:
ordering = ('name',)
def __str__(self):
return self.name
class Game(models.Model):
created = models.DateTimeField(auto_now_add=True)
name = models.CharField(max_length=200, blank=True, default='')
game_category = models.ForeignKey(GameCategory, related_name='games', on_delete=models.CASCADE)
release_date = models.DateTimeField()
game_category = models.CharField(max_length=200, blank=True, default='')
played = models.BooleanField(default=False)
class Meta:
ordering = ('name',)
def __str__(self):
return self.name
and the snippet of my urls.py:
urlpatterns = [
url(r'^game-categories/$', views.GameCategoryList.as_view(),name=views.GameCategoryList.name),
url(r'^game-categories/(?P<pk>[0-9]+)$', views.GameCategoryDetail.as_view(), name=views.GameCategoryDetail.name),
views.py:
from games.models import GameCategory
from games.models import Game
from games.models import Player
from games.models import PlayerScore
from games.serializers import GameCategorySerializer
from games.serializers import GameSerializer
from games.serializers import PlayerSerializer
from games.serializers import PlayerScoreSerializer
from rest_framework import generics
from rest_framework.response import Response
from rest_framework.reverse import reverse
class GameCategoryList(generics.ListCreateAPIView):
queryset=GameCategory.objects.all()
serializer_class=GameCategorySerializer
name='gamecategory-list'
class GameCategoryDetail(generics.RetrieveUpdateDestroyAPIView):
queryset=GameCategory.objects.all()
serializer_class = GameCategorySerializer
name = 'gamecategory-detail'
class GameList(generics.ListCreateAPIView):
queryset=Game.objects.all()
serializer_class = GameSerializer
name = 'game-detail'
class GameDetail(generics.RetrieveUpdateDestroyAPIView):
queryset=Game.objects.all()
serializer_class=GameSerializer
name='game-detail'
serializers.py
from rest_framework import serializers
from games.models import GameCategory
from games.models import Game
from games.models import Player
from games.models import PlayerScore
import games.views
class GameCategorySerializer(serializers.HyperlinkedModelSerializer):
games = serializers.HyperlinkedRelatedField(
many=True,
read_only=True,
view_name='game-detail'
)
class Meta:
model = GameCategory
fields = ('url','pk','name','games')
class GameSerializer(serializers.HyperlinkedModelSerializer):
#We want to display the game categorys name instead of the id
game_category = serializers.SlugRelatedField(queryset=GameCategory.objects.all(), slug_field='name')
class Meta:
model = Game
fields = (
'url',
'game_category',
'name',
'release_date',
'played'
)
I’m still very new to Python, let alone Django, so I am struggling to source the error here from the debug information given.
Can anyone help me understand where the problem is and why?
Upvotes: 1
Views: 1825
Reputation: 12086
How about removing HyperlinkedModelSerializer
from GameCategorySerializer
?
class GameCategorySerializer(serializers.ModelSerializer):
# rest here unchanged
Check here for more.
[UPDATE]: You have a duplication inside the Game
model!
game_category = models.ForeignKey(GameCategory, related_name='games', on_delete=models.CASCADE)
and
game_category = models.CharField(max_length=200, blank=True, default='')
You should rename the second game_category
field to something else. Thus, the error you'are getting. GameCategorySerializer
tries to handle this field (which does not have a related_name
attribute) instead of the first (ForeignKey
) one.
Upvotes: 1