Splitting big tasks into smaller one!

So I've been thinking, why I'm so not productive lately - and I've found reason - I've been scared of big tasks that consumes a lot of time!

I've decided to spend at least one Pomodoro timer (25 minutes) for splitting issues on Biking-Endorphines project.

At least ones that are estimated on more then 4 h.

Endorphine-Badges-Acquired #23

While reading this issue I've found it's not properly specified and should be splitted into smaller issues/features to make it more "pomodoro-a-like".

So I've added additional 2 tasks that helped me a lot to make progress with this issue.

Subtasks of #23 : #44 and #45

Endpoint for gathering all acquired badges needed 2 models with following them tables : - Badges - UserBadges

And then I could work on creating endpoint with serializer.

So I've created corresponding [REST-API] Badges Model needed #44 and [REST-API] Badge-To-User model #45 and described them as specific as I could.

Pomodoro Technique Timer from Toggl :)

I've also recently started testing new platform called Toggl - for tracking time.

It has such a fancy-pancy chrome-addon that helps to track of time for specific github-issue and has build-in pomodoro timer that after 25 minutes can trigger notification from browser.

Using it helped me with "high-density" working on issues above.

Bugs /Features I've found while working

I've found few bugs/features that I'll be working on soon after this Python-Milestone will end.

Bugs:

Features:

The #47 and #46 were put into Python-Milestone because they are closely related with #26

Final version

Test code:

  • at api/tests/test_unit.py:
class TestUserBadgeSerializer(unittest.TestCase):
    "UserBadge Serializer test"

    def test_user_badge_serialize(self):
        "Tests if user_badge object serialize with RouteSerializer"
        user = User()
        user.id = 21
        user.name = "Anselmos"
        user.surname = "Somlesna"
        user.weight = 80
        user.height = 175

        badge = Badge()
        badge.id = 1
        badge.name = 'FasterThenUniverse'
        badge.description = 'you\'re average lap was faster then previous one'

        route = Route()
        route.id = 2
        route.route_name = "NameOfThisFancyRoute"
        route.avg_route = 19.9


        input_user_badge = UserBadge()
        input_user_badge.id_user = user
        input_user_badge.id_badge = badge
        input_user_badge.id_route = route
        input_user_badge.active = True
        input_user_badge.badge_acquiring_date = "2017-03-03T12:00:00+00:00"
        input_user_badge.activation_modification_date = "2017-03-03T12:00:00+00:00"

        input_serialized = UserBadgeSerializer(input_user_badge)
        self.assertEqual(
            (input_serialized.data),
            {
                'id': None,
                'id_badge': 1,
                'id_user': 21,
                'id_route': 2,
                'active': True,
                'badge_acquiring_date': '2017-03-03T12:00:00+00:00',
                'activation_modification_date': '2017-03-03T12:00:00+00:00',
            }
        )
  • at api/tests/test_integration.py::APIGeneralTestCase
    # pylint: disable=no-self-use
    def create_badge_in_db(self):
        " Creates new badge object in database "
        return Badge.objects.create(
            name='FasterThenUniverse',
            description='you\'re average lap was faster then previous one'
        )

    # pylint: disable=no-self-use
    def create_route_in_db(self):
        " Creates new route object in database "
        return Route.objects.create(route_name="NameOfThisFancyRoute", avg_route=19.9)

    # pylint: disable=no-self-use
    # pylint: disable=too-many-arguments
    def create_user_badge_in_db(self, user, badge, route, active, badge_date, activation_date):
        " Creates new UserBadge object in database "
        return UserBadge.objects.create(
            id_user=user,
            id_badge=badge,
            id_route=route,
            active=active,
            badge_acquiring_date=badge_date,
            activation_modification_date=activation_date,
        )
  • at api/tests/test_integration.py
class TestUserBadgeList(APIGeneralTestCase):
    "User Update tests"
    def setUp(self):
        super(self.__class__, self).setUp()
        self.view = UserBadgeList.as_view()

    def test_update_user(self):
        " Tests if making api request updates user with new name"

        badge = self.create_badge_in_db()
        route = self.create_route_in_db()
        user = self.create_user_in_db()
        date_badge_acquired = "2017-02-02T22:00:00"
        date_badge_activation = "2017-02-02T22:00:00"
        user_badge = self.create_user_badge_in_db(
            user,
            badge,
            route,
            True,
            date_badge_acquired + "+00:00",
            date_badge_activation + "+00:00"
        )

        self.path = "/api/badge/{}/".format(user_badge.id)
        response = self.get_response_user_api(
            pk_id=user.id
        )
        self.assertEquals(response.status_code, 200)
        self.assert_user_badge(
            response.data[0],
            user.id,
            badge.id,
            route.id,
            user_badge.active,
            unicode(date_badge_acquired + "Z"),
            unicode(date_badge_activation + "Z")
        )

    # pylint: disable=too-many-arguments
    def assert_user_badge(
            self, user_badge_object, user_id, badge_id, route_id,
            active, badge_acquiring_date, activation_modification_date):
        """ Asserts user badge object with parameters """

        self.assertEquals(user_badge_object['id_user'], user_id)
        self.assertEquals(user_badge_object['id_badge'], badge_id)
        self.assertEquals(user_badge_object['id_route'], route_id)
        self.assertEquals(user_badge_object['active'], active)
        self.assertEquals(
            user_badge_object['badge_acquiring_date'],
            badge_acquiring_date
        )
        self.assertEquals(
            user_badge_object['activation_modification_date'],
            activation_modification_date
        )

Source Code:

  • at web/models.py:
class Badge(models.Model):
    "Badge Model"
    name = models.CharField(
        max_length=50,
        help_text="describes in short name of the badge"
    )

    description = models.CharField(
        max_length=256,
        default="",
        help_text="More thorough information about badge acquiring (i.e. criteria)"
    )

    def __unicode__(self):
        "Returns Badge unicode as name: description "
        return "{}: {}".format(self.name, self.description)


class UserBadge(models.Model):
    "Users acquired Badges!"
    id_user = models.ForeignKey(User, on_delete=models.CASCADE)
    id_badge = models.ForeignKey(Badge, on_delete=models.CASCADE)

    id_route = models.ForeignKey(
        Route,
        on_delete=models.CASCADE,
        help_text="id of route on which badge has been acquired"
    )

    active = models.BooleanField(default=True)
    badge_acquiring_date = models.DateTimeField()
    activation_modification_date = models.DateTimeField()

    def __unicode__(self):
        "Returns Badge unicode as name: description "
        return "User : {},  Badge acquired-id: {}: "\
        "Route-id: {}, active?: {}, badge_acquired_date: {}, "\
        "activation_modification_date: {}".format(
            self.id_user,
            self.id_badge,
            self.id_route,
            self.active,
            self.badge_acquiring_date,
            self.activation_modification_date
        )
  • at api/serializers.py:
class UserBadgeSerializer(serializers.ModelSerializer):
    """
    User serializer
    """
    class Meta:
        model = UserBadge
        fields = (
            'id',
            'id_badge',
            'id_user',
            'id_route',
            'active',
            'badge_acquiring_date',
            'activation_modification_date'
        )

    def create(self, validated_data):
        """
        Create and return a new `UserBadge` instance, given the validated data.
        """
        return UserBadge.objects.create(**validated_data)
  • at api/views.py:
class UserBadgeList(generics.ListCreateAPIView):
    """
    get:
    Return a list of all existing user badges.

    """
    queryset = UserBadge.objects.all()
    serializer_class = UserBadgeSerializer

Code commits done for this post:

In branch feature/44-Badge-model-needed:

In branch feature/45-Badge-to-User-model:

In branch feature/23-Endorphine-badges-acquired:

Release:

28-05-07-badges-acquiring-api

What's next

Hunting never ends!! Monty Python Hunting.

I'm still on my python-hunting for collecting as much of Python Milestone Issues as I can :

Due by May 31, 2017 66% complete (9 Open/ 18 Closed)

Thanks! See you soon!



Comments

comments powered by Disqus