Skip to content

Commit

Permalink
Now with Django Rest Framework Serializers #14
Browse files Browse the repository at this point in the history
  • Loading branch information
keithamoss committed Dec 13, 2018
1 parent b536c1c commit 81fc27d
Show file tree
Hide file tree
Showing 7 changed files with 97 additions and 52 deletions.
26 changes: 18 additions & 8 deletions django/scremsong/app/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import hashlib
import copy
from enum import Enum
from scremsong.app.social.twitter_utils import apply_tweet_filter_criteria

logger = make_logger(__name__)

Expand Down Expand Up @@ -56,6 +57,23 @@ class SocialColumns(models.Model):
# https://developer.twitter.com/en/docs/tweets/filter-realtime/guides/basic-stream-parameters#track
search_phrases = JSONField(default=None, blank=True, null=False)

def tweet_count(self):
"""
Count the number of tweets for the object
"""
count = apply_tweet_filter_criteria(self, Tweets.objects).count()
if count is None:
return 0
return count


class Tweets(models.Model):
"Tweets we've collected for search terms we care about."

tweet_id = models.TextField(editable=False, unique=True)
data = JSONField()
is_dismissed = models.BooleanField(default=False)


class SocialAssignments(models.Model):
"Columns configuring what to display for each social platform."
Expand All @@ -65,11 +83,3 @@ class SocialAssignments(models.Model):
social_id = models.TextField(editable=False)
user = models.ForeignKey(User, on_delete=models.CASCADE)
status = models.TextField(choices=[(tag, tag.value) for tag in SocialAssignmentStatus], default=SocialAssignmentStatus.PENDING)


class Tweets(models.Model):
"Tweets we've collected for search terms we care about."

tweet_id = models.TextField(editable=False, unique=True)
data = JSONField()
is_dismissed = models.BooleanField(default=False)
17 changes: 5 additions & 12 deletions django/scremsong/app/reviewers.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,19 +2,12 @@
from django.forms.models import model_to_dict
from scremsong.app.models import SocialAssignments, SocialAssignmentStatus
from scremsong.app.twitter import get_tweets_by_ids
from scremsong.app.serializers import ReviewerUserSerializer, TweetsSerializer, SocialAssignmentSerializer


def get_reviewer_users():
reviewers = []
for reviewer in User.objects.filter(is_staff=False, is_active=True):
reviewers.append({
"id": reviewer.id,
"username": reviewer.username,
"name": "{} {}".format(reviewer.first_name, reviewer.last_name),
"initials": "{}{}".format(reviewer.first_name[:1], reviewer.last_name[:1]),
"is_accepting_assignments": reviewer.profile.is_accepting_assignments,
})
return reviewers
users = User.objects.filter(is_staff=False, is_active=True).all()
return ReviewerUserSerializer(users, many=True).data


def get_all_pending_assignments(user=None):
Expand All @@ -28,9 +21,9 @@ def get_all_pending_assignments(user=None):
tweetIds = [a["social_id"] for a in assignments]
tweets = {}
for tweet in get_tweets_by_ids(tweetIds):
tweets[tweet["tweet_id"]] = {"id": tweet["tweet_id"], "data": tweet["data"], "is_dismissed": tweet["is_dismissed"]}
tweets[tweet["tweet_id"]] = TweetsSerializer(tweet).data

for assignment in assignments:
assignmentsById[assignment["id"]] = assignment
assignmentsById[assignment["id"]] = SocialAssignmentSerializer(assignment).data

return {"assignments": assignmentsById, "tweets": tweets}
57 changes: 53 additions & 4 deletions django/scremsong/app/serializers.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
from django.contrib.auth.models import User
from .models import Profile, SocialColumns
from .models import Profile, SocialColumns, Tweets, SocialAssignments
from rest_framework import serializers
from rest_framework.exceptions import ValidationError
from rest_framework.validators import UniqueTogetherValidator
Expand Down Expand Up @@ -31,20 +31,69 @@ class Meta:
'is_approved')


class UserPublicDetailsSerializer(serializers.ModelSerializer):
class ReviewerUserSerializer(UserSerializer):
is_accepting_assignments = serializers.BooleanField(source='profile.is_accepting_assignments')

name = serializers.SerializerMethodField()
initials = serializers.SerializerMethodField()

def get_name(self, obj):
return "{} {}".format(obj.first_name, obj.last_name)

def get_initials(self, obj):
return "{}{}".format(obj.first_name[:1], obj.last_name[:1])

class Meta:
model = User
fields = (
'id',
'username',
'first_name',
'last_name')
'name',
'initials',
'is_accepting_assignments')


class SocialColumnsSerializer(serializers.ModelSerializer):
platform = serializers.CharField()

class Meta:
model = SocialColumns
fields = (
'id',
'platform',
'search_phrases')


class SocialColumnsSerializerWithTweetCountSerializer(SocialColumnsSerializer):
tweet_count = serializers.IntegerField(read_only=True)

class Meta:
model = SocialColumns
fields = (
'id',
'platform',
'search_phrases',
'tweet_count')


class SocialAssignmentSerializer(serializers.ModelSerializer):
platform = serializers.CharField()
status = serializers.CharField()

class Meta:
model = SocialAssignments
fields = (
'id',
'platform',
'social_id',
'status',
'user_id')


class TweetsSerializer(serializers.ModelSerializer):
class Meta:
model = Tweets
fields = (
'id',
'data',
'is_dismissed')
3 changes: 2 additions & 1 deletion django/scremsong/app/social/columns.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from scremsong.app.models import SocialColumns


def get_social_columns(platform=None, columnsIds=[]):
if platform is not None:
queryset = SocialColumns.objects.filter(platform=platform)
Expand All @@ -8,4 +9,4 @@ def get_social_columns(platform=None, columnsIds=[]):
queryset = queryset.filter(id__in=columnsIds)
return queryset
else:
return SocialColumns.objects.all()
return SocialColumns.objects.all()
12 changes: 12 additions & 0 deletions django/scremsong/app/social/twitter_utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
from django.db.models import Q


def column_search_phrase_to_twitter_search_query(social_column):
return " OR ".join(social_column.search_phrases)


def apply_tweet_filter_criteria(social_column, queryset):
for phrase in social_column.search_phrases:
for phrase_part in phrase.split(" "):
queryset = queryset.filter(Q(data__extended_tweet__full_text__icontains=phrase_part) | Q(data__text__icontains=phrase_part) | Q(data__full_text__icontains=phrase_part))
return queryset.filter(data__retweeted_status__isnull=True)
32 changes: 6 additions & 26 deletions django/scremsong/app/twitter.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@
from scremsong.celery import celery_init_tweet_streaming
from scremsong.app.social.columns import get_social_columns
from scremsong.app.social.assignments import get_social_assignments
from scremsong.app.social.twitter_utils import apply_tweet_filter_criteria, column_search_phrase_to_twitter_search_query
from .serializers import SocialColumnsSerializerWithTweetCountSerializer, TweetsSerializer

logger = make_logger(__name__)

Expand Down Expand Up @@ -68,7 +70,7 @@ def fetch_some_tweets(startIndex, stopIndex, sinceId=None, maxId=None, columnIds
column_tweet_ids = []

for tweet in column_tweets:
tweets[tweet["tweet_id"]] = {"id": tweet["tweet_id"], "data": tweet["data"], "is_dismissed": tweet["is_dismissed"]}
tweets[tweet["tweet_id"]] = TweetsSerializer(tweet).data
column_tweet_ids.append(tweet["tweet_id"])

columns.append({
Expand Down Expand Up @@ -109,31 +111,9 @@ def save_tweet(status):
logger.error("Exception {}: '{}' for tweet_id {}".format(type(e), e, status.id_str))


def column_search_phrase_to_twitter_search_query(social_column):
return " OR ".join(social_column.search_phrases)


def apply_tweet_filter_criteria(social_column, queryset):
for phrase in social_column["search_phrases"]:
for phrase_part in phrase.split(" "):
queryset = queryset.filter(Q(data__extended_tweet__full_text__icontains=phrase_part) | Q(data__text__icontains=phrase_part) | Q(data__full_text__icontains=phrase_part))

return queryset.filter(data__retweeted_status__isnull=True)


def get_twitter_columns():
columns = []
for column in get_social_columns(SocialPlatformChoice.TWITTER).values():
columns.append({
**column,
"total_tweets": get_total_tweets_for_column(column),
})
return columns


def get_total_tweets_for_column(social_column):
queryset = apply_tweet_filter_criteria(social_column, Tweets.objects)
return queryset.count()
cols = get_social_columns(SocialPlatformChoice.TWITTER).all()
return SocialColumnsSerializerWithTweetCountSerializer(cols, many=True).data


def get_tweets_by_ids(tweetIds):
Expand All @@ -153,7 +133,7 @@ def get_tweets_for_column(social_column, since_id=None, max_id=None, startIndex=
logger.warning("since_id {} is out of range of max_id {} in get_tweets_for_column - it should be a lower number!")
return None

queryset = apply_tweet_filter_criteria(social_column.__dict__, queryset)
queryset = apply_tweet_filter_criteria(social_column, queryset)

tweets = queryset.order_by("-tweet_id").values()

Expand Down
2 changes: 1 addition & 1 deletion django/scremsong/app/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
import csv
from tweepy import TweepError
from scremsong.util import get_env, make_logger
from scremsong.app.twitter import twitter_user_api_auth_stage_1, twitter_user_api_auth_stage_2, get_tweets_for_column, get_total_tweets_for_column, get_tweets_by_ids, fetch_some_tweets
from scremsong.app.twitter import twitter_user_api_auth_stage_1, twitter_user_api_auth_stage_2, get_tweets_for_column, get_tweets_by_ids, fetch_some_tweets
from scremsong.celery import celery_restart_streaming
from scremsong.app.models import SocialPlatformChoice, Tweets, SocialAssignments, SocialAssignmentStatus, Profile
from scremsong.app import websockets
Expand Down

0 comments on commit 81fc27d

Please sign in to comment.