Added an association table to app/models.py.
The table is not written as a class as it is simply an association table with no other relevant job in the DB.
The followers and followed users is deemed to be a many-many relationship. These DB relationships are modelled using association tables.
In this case, the association is self-referential: both followers and followed are User instances, and so, they both link to user.id as the foreign key.
Added relationship function to User class to handle the followers-followed relationship.
Let A->B means A follows B. The relationship is defined from the left side entity with the name followed. When we query this relationship from the left side we will get the list of followed users.
1. 'User' arg is a right side entity in the relationship (left side entity being the parent class). Self-referential relationship asks for the same class on both sides.
2. secondary arg indicates that an association table is used for this relationship.
3. primaryjoin arg indicates the condition on which the left side entity is joined with the association table. As followers is not a model subclass, the syntax is a bit different here.
4. secondaryjoin arg links the right side entity with the association table (followed user).
5. backref arg defines how relationship is accessed from right side entity. For a given user, query named 'followed' returns all right side users that have target user on the left side. The back reference is called 'followers', and returns left side users for a target right side user in the right side. 'lazy' defines execution mode for the query, and 'dynamic' setting allows us to not let the query run until requested.
6. 'lazy' again.
Migrated the DB to a new version.
Also took the definition of the followers table to the top of the source file, as it was not being recognized in the call to db.relationship() in User class otherwise.
Added follow and unfollow methods to the User class.
Instead of introducing them in app/views.py, we have done it in app/models.py.
The reason for this is it makes it simpler to test and follow/unfollow can be used in the application. View functions should be simple.
Added a followed_posts method to User class.
This method executes a query which is three pronged in nature -:
1. First, a join is performed on the Posts (left) and followers (right) table, on the condition that followers.followed_id equals Post.user_id.
2. Next, a filter is applied where the follower_id in followers table must match the id of the target user, i.e., the user executing the query whose followed posts we wish to find.
3. Lastly, the result is sorted according to Post.timestamp.
Added tests for testing the followed posts mechanism.
Modified the after login handler in app/views.py.
It now caters to users following themselves.
Added a view function for '/follow/<nickname>'.
It takes nickname as an arg, obtains the User that has this nickname, and then after a few checks, adds the User object returned by the follow function to the DB.
This updates the User.
Added a view function for unfollowing a User.
Modified the user template.
Added links to Follow and Unfollow which invoke follow() and unfollow() in views.py.
Merge pull request #6 from VaticanCameos/ch8

Adding chapter 8