Skip to content

Commit

Permalink
Merge branch 'develop' into ft-like-comment-164069241
Browse files Browse the repository at this point in the history
  • Loading branch information
CryceTruly committed Mar 21, 2019
2 parents c705886 + 3882480 commit 532b04b
Show file tree
Hide file tree
Showing 10 changed files with 225 additions and 122 deletions.
22 changes: 19 additions & 3 deletions authors/apps/articles/migrations/0001_initial.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
# Generated by Django 2.1.5 on 2019-03-20 11:50
# Generated by Django 2.1.5 on 2019-03-21 09:14

from django.conf import settings
import django.contrib.postgres.fields
from django.db import migrations, models
import django.db.models.deletion
Expand All @@ -11,17 +12,18 @@ class Migration(migrations.Migration):

dependencies = [
('profiles', '0001_initial'),
migrations.swappable_dependency(settings.AUTH_USER_MODEL),
]

operations = [
migrations.CreateModel(
name='Article',
fields=[
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=100)),
('title', models.CharField(max_length=255)),
('body', models.TextField()),
('slug', models.SlugField(blank=True, unique=True)),
('description', models.CharField(max_length=100)),
('description', models.CharField(max_length=255)),
('likes', models.IntegerField(default=0)),
('dislikes', models.IntegerField(default=0)),
('created_at', models.DateTimeField(auto_now_add=True)),
Expand All @@ -31,6 +33,8 @@ class Migration(migrations.Migration):
('tagList', django.contrib.postgres.fields.ArrayField(base_field=models.CharField(max_length=200), blank=True, default=list, size=None)),
('favorited', models.BooleanField(default=False)),
('favoritesCount', models.IntegerField(default=0)),
('author', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='author_articles', to='profiles.Profile')),
('favorites', models.ManyToManyField(blank=True, related_name='favorited_articles', to='profiles.Profile')),
],
options={
'ordering': ['-created_at'],
Expand All @@ -43,6 +47,17 @@ class Migration(migrations.Migration):
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('likes', models.BooleanField(default=False, null=True)),
('created_at', models.DateTimeField(auto_now_add=True)),
('article', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='articles.Article')),
('user', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='profiles.Profile')),
],
),
migrations.CreateModel(
name='Bookmark',
fields=[
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('bookmarked_at', models.DateTimeField(auto_now_add=True)),
('article', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='articles.Article')),
('user', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
],
),
migrations.CreateModel(
Expand All @@ -52,6 +67,7 @@ class Migration(migrations.Migration):
('rated_on', models.DateTimeField(auto_now_add=True)),
('score', models.DecimalField(decimal_places=2, max_digits=5)),
('article', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='ratings', to='articles.Article')),
('rated_by', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, related_name='scores', to=settings.AUTH_USER_MODEL)),
],
options={
'ordering': ['-score'],
Expand Down
44 changes: 0 additions & 44 deletions authors/apps/articles/migrations/0002_auto_20190320_1150.py

This file was deleted.

7 changes: 7 additions & 0 deletions authors/apps/articles/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
from django.contrib.postgres.fields import ArrayField
from rest_framework.response import Response
from rest_framework import status

from authors.apps.authentication.models import User
from authors.apps.profiles.models import Profile

from authors.settings import WORD_LENGTH, WORD_PER_MINUTE
Expand Down Expand Up @@ -135,3 +137,8 @@ class Meta:

def __str__(self):
return self.reason
class Bookmark(models.Model):
"""Model for creating bookmarks of an article by a user."""
user = models.ForeignKey(User, on_delete=models.CASCADE, blank=False)
article = models.ForeignKey(Article, on_delete=models.CASCADE)
bookmarked_at = models.DateTimeField(auto_now_add=True)
8 changes: 8 additions & 0 deletions authors/apps/articles/serializers.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
from authors.apps.comments.models import Comment
from .models import Article, ArticleLikesDislikes, Rating, ReportedArticle

from .models import Article, ArticleLikesDislikes, Rating, Bookmark

from ..profiles.serializers import ProfileSerializer


Expand Down Expand Up @@ -114,3 +116,9 @@ class ReportedArticleSerializer(serializers.ModelSerializer):
class Meta:
model = ReportedArticle
fields = ('id', 'reporter', 'article', 'reason',)
class BookmarkSerializer(serializers.ModelSerializer):
article = ArticleSerializer(read_only=True)

class Meta:
model = Bookmark
fields = ('id', 'article', 'bookmarked_at',)
99 changes: 99 additions & 0 deletions authors/apps/articles/tests/test_bookmarks.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
from django.urls import reverse
from authors.apps.articles.tests.base_class import ArticlesBaseTest
from ..models import Article


class TestBookmarks(ArticlesBaseTest):
"""Bookmark tests"""
def setUp(self):
super().setUp()

def test_bookmark_your_own_article(self):
"""Test for bookmarking your own article an article"""
self.add_article()
article = Article.objects.all().first()
url = reverse("articles:bookmark_article", kwargs={'slug': article.slug})
response = self.client.post(url)
self.assertEqual(response.status_code, 403)
self.assertIn(response.data['error'], 'You can not bookmark your own article')

def test_bookmark_another_authors_article(self):
"""Test for bookmarking another authors article"""
self.add_article()
self.register_and_login_new_user()
article = Article.objects.all().first()
url = reverse("articles:bookmark_article", kwargs={'slug': article.slug})
response = self.client.post(url)
self.assertEqual(response.status_code, 201)
self.assertIn(response.data['message'], 'Article has been bookmarked')

def test_bookmark_article_that_does_not_exist(self):
"""Test for bookmarking an article that does not exist"""
self.add_article()
self.register_and_login_new_user()
url = reverse("articles:bookmark_article", kwargs={'slug': 't990'})
response = self.client.post(url)
self.assertEqual(response.status_code, 404)
self.assertIn(response.data['detail'], 'Not found.')

def test_bookmark_article_that_has_already_been_bookmarked(self):
"""Test bookmarking an article that has already been bookmarked"""
self.add_article()
self.register_and_login_new_user()
article = Article.objects.all().first()
self.client.post(reverse("articles:bookmark_article", kwargs={'slug': article.slug}))
url = reverse("articles:bookmark_article", kwargs={'slug': article.slug})
response = self.client.post(url)
self.assertEqual(response.status_code, 400)
self.assertIn(response.data['error'], 'You have already bookmarked this article')

def test_unbookmark_article(self):
"""Test for unbookmarking an article"""
self.add_article()
self.register_and_login_new_user()
article = Article.objects.all().first()
self.client.post(reverse("articles:bookmark_article", kwargs={'slug': article.slug}))
url = reverse("articles:bookmark_article", kwargs={'slug': article.slug})
response = self.client.delete(url)
self.assertEqual(response.status_code, 200)
self.assertIn(response.data['message'], 'Article has been unbookmarked')

def test_unbookmark_article_that_has_already_been_unbookmarked(self):
"""Test for unbookmarking an article that has already been unbookmarked"""
self.add_article()
self.register_and_login_new_user()
article = Article.objects.all().first()
self.client.post(reverse("articles:bookmark_article", kwargs={'slug': article.slug}))
self.client.delete(reverse("articles:bookmark_article", kwargs={'slug': article.slug}))
url = reverse("articles:bookmark_article", kwargs={'slug': article.slug})
response = self.client.delete(url)
self.assertEqual(response.status_code, 400)
self.assertIn(response.data['error'], 'Article does not exist in your bookmarks list')

def test_get_bookmarked_articles(self):
"""Test to get bookmarked articles by a user"""
self.add_article()
self.register_and_login_new_user()
article = Article.objects.all().first()
self.client.post(reverse("articles:bookmark_article", kwargs={'slug': article.slug}))
url = reverse('articles:articles_bookmarked')
response = self.client.get(url)
self.assertEqual(response.status_code, 200)

def test_get_no_articles_bookmarked(self):
"""Test to get empty bookmarks list"""
self.add_article()
self.register_and_login_new_user()
url = reverse('articles:articles_bookmarked')
response = self.client.get(url)
self.assertEqual(response.status_code, 200)
self.assertIn(response.data['message'], 'You have not bookmarked any articles yet')

def test_unbookmark_article_that_does_not_exist(self):
"""Test unbookmark article that does not exist in the bookmarks list"""
self.add_article()
self.register_and_login_new_user()
url = reverse("articles:bookmark_article", kwargs={'slug': 't990'})
response = self.client.delete(url)
self.assertEqual(response.status_code, 404)
self.assertIn(response.data['detail'], 'Not found.')
3 changes: 2 additions & 1 deletion authors/apps/articles/tests/test_data.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@

"title": "When ooh in oo updated ocean",
"description": "this is the description,.",
"body": "this is the body"
"body": "this is the body",
"tagList": ["python", "java"]
}


Expand Down
7 changes: 4 additions & 3 deletions authors/apps/articles/urls.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,8 @@
from .views import (
ArticlesApiView, ArticleDetailApiView,
ArticleLikeApiView, RateArticleView,
FavoriteHandlerView, ArticleTagsApiView, ReportArticleView
)

FavoriteHandlerView, ArticleTagsApiView, ReportArticleView,
BookmarksApiView,BookmarksListView)

urlpatterns = [
path('articles/', ArticlesApiView.as_view(), name='articles'),
Expand All @@ -31,4 +30,6 @@
),
path('articles/<slug>/favorite', FavoriteHandlerView.as_view(),
name='article-favorite'),
path('articles/<slug>/bookmark/', BookmarksApiView.as_view(), name="bookmark_article"),
path('bookmarks/', BookmarksListView.as_view(), name="articles_bookmarked"),
]
Loading

0 comments on commit 532b04b

Please sign in to comment.