From 037b3fe0d6ad70e59b95702b7888e233ccf1d63e Mon Sep 17 00:00:00 2001 From: giovannimhern Date: Thu, 30 Nov 2023 13:41:19 -0600 Subject: [PATCH 1/4] Added tests for getting game lists using serializers and the api-game-list URL --- src/chigame/api/tests/test_api.py | 91 ++++++++++++++++++++++++++++++- 1 file changed, 89 insertions(+), 2 deletions(-) diff --git a/src/chigame/api/tests/test_api.py b/src/chigame/api/tests/test_api.py index 5ce0956f..004be534 100644 --- a/src/chigame/api/tests/test_api.py +++ b/src/chigame/api/tests/test_api.py @@ -1,12 +1,16 @@ # from django.test import TestCase # Create your tests here. - # Compare this snippet from src/chigame/api/tests.py: from django.urls import reverse + +# Related third party imports from rest_framework import status from rest_framework.test import APITestCase +from rest_framework.utils.serializer_helpers import ReturnDict +# Local application/library specific imports +from chigame.api.serializers import GameSerializer from chigame.api.tests.factories import ChatFactory, GameFactory, TournamentFactory, UserFactory from chigame.games.models import Game, Message @@ -17,7 +21,14 @@ def check_equal(self, obj, expected: dict): Helper function to check that the object data matches the expected data. """ for key in expected: - self.assertEqual(getattr(obj, key), expected[key]) + if isinstance(obj, (ReturnDict, dict)): + # Use key indexing for dictionaries and ReturnDict + obj_value = obj[key] + else: + # Use getattr for object instances + obj_value = getattr(obj, key, None) + + self.assertEqual(obj_value, expected[key]) # def test_get_game(self): # """ @@ -36,6 +47,82 @@ def check_equal(self, obj, expected: dict): # self.assertEqual(Game.objects.count(), 1) # self.check_equal(Game.objects.get(), response.data) + def test_get_game(self): + """ + Ensure we can get a game object. + """ + + # Create a game object + game = GameFactory() + + # Get the game object + url = reverse("api-game-list") + response = self.client.get(url, format="json") + serialized_game = GameSerializer(game).data + + # Check that the game object was retrieved correctly + self.assertEqual(response.status_code, status.HTTP_200_OK) + self.assertEqual(Game.objects.count(), 1) + self.check_equal(serialized_game, response.data[0]) + + def test_get_game_list1(self): + """ + Ensure we can get a list of game objects. + """ + url = reverse("api-game-list") + + # create three game objects + game1 = GameFactory() + game2 = GameFactory() + game3 = GameFactory() + + # Get the game object list + url = reverse("api-game-list") + response = self.client.get(url, format="json") + + # Check that the game object list was retrieved correctly + self.assertEqual(response.status_code, status.HTTP_200_OK) + + # test that the game object list contains the two game objects we created + self.assertEqual(Game.objects.count(), 3) + serialized_game1 = GameSerializer(game1).data + serialized_game2 = GameSerializer(game2).data + serialized_game3 = GameSerializer(game3).data + + self.check_equal(serialized_game1, response.data[0]) + self.check_equal(serialized_game2, response.data[1]) + self.check_equal(serialized_game3, response.data[2]) + + def test_game_list2(self): + """ + Ensure we can get a list of game objects. + """ + url = reverse("api-game-list") + + # create four game objects + game1 = GameFactory() + game2 = GameFactory() + game3 = GameFactory() + game4 = GameFactory() + + # Get the game object list + url = reverse("api-game-list") + response = self.client.get(url, format="json") + + # Check that the game object list was retrieved correctly + self.assertEqual(response.status_code, status.HTTP_200_OK) + + serialized_game1 = GameSerializer(game1).data + serialized_game2 = GameSerializer(game2).data + serialized_game3 = GameSerializer(game3).data + serialized_game4 = GameSerializer(game4).data + + # test that the game object list contains the two game objects we created + self.check_equal(serialized_game1, response.data[0]) + self.check_equal(serialized_game2, response.data[1]) + self.check_equal(serialized_game3, response.data[2]) + self.check_equal(serialized_game4, response.data[3]) + def test_update_game(self): """ Ensure we can update a game object. From af764cf317ddb34466caa2af0ffd27a18f6c8316 Mon Sep 17 00:00:00 2001 From: giovannimhern Date: Sun, 3 Dec 2023 14:57:00 -0600 Subject: [PATCH 2/4] Fixing run tests failures due to dictionary access --- src/chigame/api/tests/test_api.py | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/src/chigame/api/tests/test_api.py b/src/chigame/api/tests/test_api.py index 004be534..2ed50eea 100644 --- a/src/chigame/api/tests/test_api.py +++ b/src/chigame/api/tests/test_api.py @@ -63,13 +63,12 @@ def test_get_game(self): # Check that the game object was retrieved correctly self.assertEqual(response.status_code, status.HTTP_200_OK) self.assertEqual(Game.objects.count(), 1) - self.check_equal(serialized_game, response.data[0]) + self.check_equal(serialized_game, response.data["results"][0]) def test_get_game_list1(self): """ Ensure we can get a list of game objects. """ - url = reverse("api-game-list") # create three game objects game1 = GameFactory() @@ -89,9 +88,9 @@ def test_get_game_list1(self): serialized_game2 = GameSerializer(game2).data serialized_game3 = GameSerializer(game3).data - self.check_equal(serialized_game1, response.data[0]) - self.check_equal(serialized_game2, response.data[1]) - self.check_equal(serialized_game3, response.data[2]) + self.check_equal(serialized_game1, response.data["results"][0]) + self.check_equal(serialized_game2, response.data["results"][1]) + self.check_equal(serialized_game3, response.data["results"][2]) def test_game_list2(self): """ @@ -118,10 +117,10 @@ def test_game_list2(self): serialized_game4 = GameSerializer(game4).data # test that the game object list contains the two game objects we created - self.check_equal(serialized_game1, response.data[0]) - self.check_equal(serialized_game2, response.data[1]) - self.check_equal(serialized_game3, response.data[2]) - self.check_equal(serialized_game4, response.data[3]) + self.check_equal(serialized_game1, response.data["results"][0]) + self.check_equal(serialized_game2, response.data["results"][1]) + self.check_equal(serialized_game3, response.data["results"][2]) + self.check_equal(serialized_game4, response.data["results"][3]) def test_update_game(self): """ From bff5bfb907fbef50751a35ed8d04a7f92367aee1 Mon Sep 17 00:00:00 2001 From: giovannimhern Date: Thu, 7 Dec 2023 14:20:02 -0600 Subject: [PATCH 3/4] Added comment for why key indexing is necessary for different types --- src/chigame/api/tests/test_api.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/chigame/api/tests/test_api.py b/src/chigame/api/tests/test_api.py index 2ed50eea..80f40e51 100644 --- a/src/chigame/api/tests/test_api.py +++ b/src/chigame/api/tests/test_api.py @@ -22,7 +22,10 @@ def check_equal(self, obj, expected: dict): """ for key in expected: if isinstance(obj, (ReturnDict, dict)): - # Use key indexing for dictionaries and ReturnDict + # If so, use key indexing to retrieve the value corresponding to 'key' + # This is suitable for dictionary-like objects where data is accessed by keys + # This ensures that despite the types (either serialized or unserialized), + # we can still compare the data correctly (e.g. id, name, etc.) obj_value = obj[key] else: # Use getattr for object instances From 0d3b05b93e08c7675310523d746aa1009a213dfd Mon Sep 17 00:00:00 2001 From: giovannimhern Date: Thu, 7 Dec 2023 14:44:57 -0600 Subject: [PATCH 4/4] Comment for helper function part 2 --- src/chigame/api/tests/test_api.py | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/src/chigame/api/tests/test_api.py b/src/chigame/api/tests/test_api.py index d702cfa2..aea8367c 100644 --- a/src/chigame/api/tests/test_api.py +++ b/src/chigame/api/tests/test_api.py @@ -21,11 +21,18 @@ def check_equal(self, obj, expected: dict): Helper function to check that the object data matches the expected data. """ for key in expected: + # Issue: Serialized data often converts numbers to strings for transport + # leading to a type mismatch when compared with their original Python types. + + # Solution: The check on lines 35-36 converts the serialized data to + # the original Python type before comparing it with the expected data. + # This ensures that the comparison is done on the same type of data. + + # For example, without this check, you might encounter issues + # when comparing Decimal('5') and '5.00', + # which would fail due to type mismatch despite representing the same value. + if isinstance(obj, (ReturnDict, dict)): - # If so, use key indexing to retrieve the value corresponding to 'key' - # This is suitable for dictionary-like objects where data is accessed by keys - # This ensures that despite the types (either serialized or unserialized), - # we can still compare the data correctly (e.g. id, name, etc.) obj_value = obj[key] else: # Use getattr for object instances