diff --git a/application/celery.py b/application/celery.py index af41b0a..e36217d 100644 --- a/application/celery.py +++ b/application/celery.py @@ -16,11 +16,13 @@ os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'application.settings') + def load_env(): "Get the path to the .env file and load it." project_dir = os.path.dirname(os.path.dirname(__file__)) dotenv.read_dotenv(os.path.join(project_dir, '.env')) + if not any(x in os.environ for x in platforms): load_env() @@ -54,7 +56,7 @@ def load_env(): app.conf.worker_concurrency = settings.CELERY_CONCURRENCY # Results settings -#app.conf.result_backend = settings.CELERY_RESULT_BACKEND +# app.conf.result_backend = settings.CELERY_RESULT_BACKEND app.conf.result_serializer = settings.CELERY_RESULT_SERIALIZER app.conf.result_expires = settings.CELERY_TASK_RESULT_EXPIRES @@ -82,10 +84,12 @@ def load_env(): app.conf.monitors_expire_error = settings.CELERY_MONITORS_EXPIRE_ERROR app.conf.monitors_expire_pending = settings.CELERY_MONITORS_EXPIRE_PENDING + class CeleryConfig(AppConfig): name = 'application' verbose_name = 'Celery Config' + @app.task(bind=True) def debug_task(self): print('Request: {0!r}'.format(self.request)) diff --git a/application/custom_storages.py b/application/custom_storages.py index e7368e8..56ae496 100644 --- a/application/custom_storages.py +++ b/application/custom_storages.py @@ -1,8 +1,10 @@ from django.conf import settings from storages.backends.s3boto import S3BotoStorage + class StaticStorage(S3BotoStorage): location = settings.STATICFILES_LOCATION + class MediaStorage(S3BotoStorage): location = settings.MEDIAFILES_LOCATION diff --git a/application/wsgi.py b/application/wsgi.py index d8e1a4c..c6967b2 100644 --- a/application/wsgi.py +++ b/application/wsgi.py @@ -11,16 +11,20 @@ https://docs.djangoproject.com/en/1.9/howto/deployment/wsgi/ """ -import os, sys, dotenv +import os +import dotenv + from django.core.wsgi import get_wsgi_application platforms = ["TRAVIS", "HEROKU", "BLUEMIX"] + def load_env(): - "Get the path to the .env file and load it." + """Get the path to the .env file and load it.""" project_dir = os.path.dirname(os.path.dirname(__file__)) dotenv.read_dotenv(os.path.join(project_dir, '.env')) + if not any(x in os.environ for x in platforms): load_env() diff --git a/feedcrunch/management/commands/load_data.py b/feedcrunch/management/commands/load_data.py index 08c129c..f9d8d18 100644 --- a/feedcrunch/management/commands/load_data.py +++ b/feedcrunch/management/commands/load_data.py @@ -2,17 +2,20 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.core.management.base import BaseCommand, CommandError +from django.core.management.base import BaseCommand from feedcrunch.models import * from application.settings import * import os import csv + def unicode_csv_reader(utf8_data, dialect=csv.excel, **kwargs): csv_reader = csv.reader(utf8_data, dialect=dialect, **kwargs) + for row in csv_reader: - yield [unicode(cell, 'utf-8') for cell in row] + yield [str(cell) for cell in row] + class Command(BaseCommand): help = 'Load Data from continents.csv and countries.csv' @@ -21,22 +24,22 @@ def handle(self, *args, **options): ## Load Continents to DATABASE - print ("Saving Continents ...") + print("Saving Continents ...") with open(os.path.join(BASE_DIR, 'feedcrunch/data/continents.csv'), 'rb') as f: reader = csv.reader(f) - next(reader, None) #skip the headers + next(reader, None) # skip the headers for row in reader: cntnt = Continent(code=row[0], name=row[1]) cntnt.save() - print ("Continents Saved !") + print("Continents Saved !") ## Load Countries to DATABASE - print ("Saving Countries ...") + print("Saving Countries ...") with open(os.path.join(BASE_DIR, 'feedcrunch/data/countries.csv'), 'rb') as f: reader = unicode_csv_reader(f) - next(reader, None) #skip the headers + next(reader, None) # skip the headers for row in reader: cntry = Country(continent=Continent.objects.get(name=row[2]), code=row[1], name=row[0]) cntry.save() - print ("Countries Saved !") + print("Countries Saved !") diff --git a/feedcrunch/model_files/models_estimators.py b/feedcrunch/model_files/models_estimators.py index df5b047..99076f9 100644 --- a/feedcrunch/model_files/models_estimators.py +++ b/feedcrunch/model_files/models_estimators.py @@ -3,22 +3,26 @@ from __future__ import unicode_literals +import datetime + +from io import StringIO + +import string +import pickle +import random +import uuid +import urllib + # original based on sci-kit hashing function from django.conf import settings -from django.core.exceptions import ValidationError from django.db import models -from django.core.files.base import ContentFile from django.core.files.uploadedfile import InMemoryUploadedFile -import datetime - -from io import StringIO - -import os, string, pickle, random, uuid, urllib def id_generator(size=20, chars=string.ascii_uppercase + string.ascii_lowercase + string.digits): return ''.join(random.choice(chars) for _ in range(size)) + def get_upload_path(): while True: @@ -31,6 +35,7 @@ def get_upload_path(): return settings.USER_ESTIMATOR_PATH + filename + def get_upload_path_instance(instance, filename): if instance.object_file: @@ -45,7 +50,6 @@ def get_upload_path_instance(instance, filename): return get_upload_path() - class Estimator(models.Model): """This class creates estimator objects that persists predictive models @@ -55,7 +59,7 @@ class Estimator(models.Model): :description: :estimator: - >>> from estimators.models import Estimator + >>> from feedcrunch.model_files.models_estimators import Estimator >>> est = Estimator() >>> est.estimator = object >>> est.description = "k-means with 5 clusters" diff --git a/feedcrunch/model_files/models_geo.py b/feedcrunch/model_files/models_geo.py index 4871647..3c4216f 100644 --- a/feedcrunch/model_files/models_geo.py +++ b/feedcrunch/model_files/models_geo.py @@ -2,10 +2,12 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + from django.db import models ############################# Localisation ##################################### + class Continent(models.Model): name = models.CharField(primary_key=True, max_length=60) code = models.CharField(max_length=2) @@ -13,6 +15,7 @@ class Continent(models.Model): def __str__(self): return self.name + class Country(models.Model): name = models.CharField(primary_key=True, max_length=60) code = models.CharField(max_length=2) diff --git a/feedcrunch/model_files/models_interest.py b/feedcrunch/model_files/models_interest.py index 1f8b079..d7c32f8 100644 --- a/feedcrunch/model_files/models_interest.py +++ b/feedcrunch/model_files/models_interest.py @@ -2,18 +2,24 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + +import random +import urllib +import string +import uuid + from django.db import models from django.conf import settings -from .models_rssfeed import RSSFeed +from feedcrunch.model_files.models_rssfeed import RSSFeed -import random, urllib, string, uuid ############################## Interest MODEL ################################### def id_generator(size=20, chars=string.ascii_uppercase + string.ascii_lowercase + string.digits): return ''.join(random.choice(chars) for _ in range(size)) + def get_photo_path(instance, filename): ext = filename.split('.')[-1] @@ -27,6 +33,7 @@ def get_photo_path(instance, filename): return settings.INTEREST_PHOTO_PATH + filename + class Interest(models.Model): name = models.CharField(max_length=255, primary_key=True) rssfeeds = models.ManyToManyField(RSSFeed, blank=True, related_name='rel_interests') diff --git a/feedcrunch/model_files/models_options.py b/feedcrunch/model_files/models_options.py index f745317..37c847f 100644 --- a/feedcrunch/model_files/models_options.py +++ b/feedcrunch/model_files/models_options.py @@ -2,15 +2,17 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + from django.db import models from encrypted_model_fields.fields import EncryptedCharField + ############################## Option MODEL ################################### class Option(models.Model): parameter = models.CharField(max_length=255, primary_key=True) - value = EncryptedCharField(max_length=255, default='') + value = EncryptedCharField(max_length=255, default='') # TODO Check This def __str__(self): return self.parameter diff --git a/feedcrunch/model_files/models_post.py b/feedcrunch/model_files/models_post.py index bd4268d..d06bed6 100644 --- a/feedcrunch/model_files/models_post.py +++ b/feedcrunch/model_files/models_post.py @@ -2,19 +2,19 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.db import models -from django.contrib.auth.models import User, UserManager -import re, uuid, datetime, random, string +from feedcrunch.model_files.models_user import * +from feedcrunch.model_files.models_tag import * -from .models_geo import * -from .models_user import * -from .models_tag import * +from functions.get_domain import get_domain -from get_domain import get_domain def create_key(size=8): - return ''.join(random.SystemRandom().choice(string.ascii_uppercase + string.ascii_lowercase + string.digits) for _ in range(size)) + return ''.join( + random.SystemRandom().choice(string.ascii_uppercase + string.ascii_lowercase + string.digits) + for _ in range(size) + ) + ############################## Post MODEL ################################### diff --git a/feedcrunch/model_files/models_rss_assocs.py b/feedcrunch/model_files/models_rss_assocs.py index 6c1edb5..b4619a1 100644 --- a/feedcrunch/model_files/models_rss_assocs.py +++ b/feedcrunch/model_files/models_rss_assocs.py @@ -4,13 +4,12 @@ from __future__ import unicode_literals from django.db import models -import datetime, string, re, uuid +from feedcrunch.model_files.models_user import FeedUser +from feedcrunch.model_files.models_rssfeed import RSSFeed +from feedcrunch.model_files.models_rssarticle import RSSArticle -from .models_user import FeedUser -from .models_rssfeed import RSSFeed -from .models_rssarticle import RSSArticle +from functions.clean_html import clean_html -from clean_html import clean_html def shorten_string(string, max_size): if max_size < 7: @@ -20,6 +19,7 @@ def shorten_string(string, max_size): else: return string + class RSSFeed_SubManager(models.Manager): def create(self, *args, **kwargs): @@ -33,6 +33,7 @@ def create(self, *args, **kwargs): return super(RSSFeed_SubManager, self).create(*args, **kwargs) + class RSSFeed_Sub(models.Model): objects = RSSFeed_SubManager() @@ -72,8 +73,6 @@ def short_title(self): return shorten_string(self.title, 75) -################################################################################################################################### - class RSSArticle_AssocManager(models.Manager): def create(self, *args, **kwargs): @@ -82,6 +81,7 @@ def create(self, *args, **kwargs): return super(RSSArticle_AssocManager, self).create(*args, **kwargs) + class RSSArticle_Assoc(models.Model): objects = RSSArticle_AssocManager() diff --git a/feedcrunch/model_files/models_rss_subscriber.py b/feedcrunch/model_files/models_rss_subscriber.py index 0c9c491..aff1d3d 100644 --- a/feedcrunch/model_files/models_rss_subscriber.py +++ b/feedcrunch/model_files/models_rss_subscriber.py @@ -2,16 +2,19 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.core.validators import MaxValueValidator, MinValueValidator + +import datetime + +from django.core.validators import MaxValueValidator +from django.core.validators import MinValueValidator from django.db import models -from .models_user import FeedUser +from feedcrunch.model_files.models_user import FeedUser from djchoices import DjangoChoices, ChoiceItem -from ipware.ip import get_real_ip, get_ip - -import datetime +from ipware.ip import get_real_ip +from ipware.ip import get_ip ######################################## Subscription ################################################ diff --git a/feedcrunch/model_files/models_rssarticle.py b/feedcrunch/model_files/models_rssarticle.py index 93e79ec..c68f374 100644 --- a/feedcrunch/model_files/models_rssarticle.py +++ b/feedcrunch/model_files/models_rssarticle.py @@ -2,14 +2,16 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + +import uuid + from django.db import models -import datetime, string, re, uuid +from feedcrunch.model_files.models_rssfeed import RSSFeed -from .models_rssfeed import RSSFeed +from functions.get_domain import get_domain +from functions.clean_html import clean_html -from get_domain import get_domain -from clean_html import clean_html class RSSArticleManager(models.Manager): def create(self, *args, **kwargs): @@ -28,6 +30,7 @@ def create(self, *args, **kwargs): return super(RSSArticleManager, self).create(*args, **kwargs) + class RSSArticle(models.Model): objects = RSSArticleManager() diff --git a/feedcrunch/model_files/models_rssfeed.py b/feedcrunch/model_files/models_rssfeed.py index d70ed94..03f8b6d 100644 --- a/feedcrunch/model_files/models_rssfeed.py +++ b/feedcrunch/model_files/models_rssfeed.py @@ -2,15 +2,17 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + +import unicodedata +import feedparser + from django.db import models from django.conf import settings -import datetime, string, re, unicodedata, feedparser +from functions.get_domain import get_domain +from functions.clean_html import clean_html +from functions.feed_validation import validate_feed -from get_domain import get_domain -from clean_html import clean_html - -from feed_validation import validate_feed class RSSFeedManager(models.Manager): def create(self, *args, **kwargs): @@ -33,6 +35,7 @@ def create(self, *args, **kwargs): return super(RSSFeedManager, self).create(*args, **kwargs) + class RSSFeed(models.Model): objects = RSSFeedManager() diff --git a/feedcrunch/model_files/models_slack_integrations.py b/feedcrunch/model_files/models_slack_integrations.py index 80965aa..edd1ee6 100644 --- a/feedcrunch/model_files/models_slack_integrations.py +++ b/feedcrunch/model_files/models_slack_integrations.py @@ -2,12 +2,14 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + from django.db import models -from .models_user import FeedUser +from feedcrunch.model_files.models_user import FeedUser from encrypted_model_fields .fields import EncryptedCharField + ############################## TAG MODEL ################################### class SlackIntegration(models.Model): diff --git a/feedcrunch/model_files/models_tag.py b/feedcrunch/model_files/models_tag.py index f02aa49..385c921 100644 --- a/feedcrunch/model_files/models_tag.py +++ b/feedcrunch/model_files/models_tag.py @@ -2,8 +2,10 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals + from django.db import models + ############################## TAG MODEL ################################### class Tag(models.Model): diff --git a/feedcrunch/model_files/models_user.py b/feedcrunch/model_files/models_user.py index 2c80662..f1f9671 100644 --- a/feedcrunch/model_files/models_user.py +++ b/feedcrunch/model_files/models_user.py @@ -3,39 +3,61 @@ from __future__ import unicode_literals -import re, uuid, datetime, unicodedata, random, urllib, string +import re +import uuid +import datetime +import unicodedata +import random +import urllib +import string + from xml.sax.saxutils import escape as escape_xml from django.conf import settings -from django.contrib.auth.models import UserManager, PermissionsMixin -from django.contrib.auth.base_user import AbstractBaseUser, BaseUserManager + +from django.contrib.auth.models import UserManager +from django.contrib.auth.models import PermissionsMixin + +from django.contrib.auth.base_user import BaseUserManager +from django.contrib.auth.base_user import AbstractBaseUser + from django.core.exceptions import ValidationError from django.core.mail import send_mail + from django.db import models -from django.utils import six, timezone + +from django.utils import six +from django.utils import timezone from django.utils.encoding import force_text from django.utils.translation import ugettext_lazy as _ from pyisemail import is_email -from encrypted_model_fields .fields import EncryptedCharField +from encrypted_model_fields.fields import EncryptedCharField -from feedcrunch.models import Country, Estimator, Interest +from feedcrunch.models import Country +from feedcrunch.models import Estimator +from feedcrunch.models import Interest from oauth.twitterAPI import TwitterAPI from oauth.facebookAPI import FacebookAPI from oauth.linkedinAPI import LinkedInAPI from oauth.slackAPI import SlackAPI -from functions.validators import ASCIIUsernameValidator, UnicodeUsernameValidator +from functions.validators import UnicodeUsernameValidator +from functions.validators import ASCIIUsernameValidator + +from datetime import timedelta +from datetime import datetime -from datetime import timedelta, datetime def generateDummyDesc(): return "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aliquam dui nisl, aliquam nec quam nec, laoreet porta odio. Morbi ultrices sagittis ligula ut consectetur. Aenean quis facilisis augue. Vestibulum maximus aliquam augue, ut lobortis turpis euismod vel. Sed in mollis tellus, eget eleifend turpis. Vivamus aliquam ornare felis at dignissim. Integer vitae cursus eros, non dignissim dui. Suspendisse porttitor justo nec lacus dictum commodo. Sed in fringilla tortor, at pharetra tortor." + def id_generator(size=20, chars=string.ascii_uppercase + string.ascii_lowercase + string.digits): return ''.join(random.choice(chars) for _ in range(size)) + def get_photo_path(instance, filename): ext = filename.split('.')[-1] @@ -49,6 +71,7 @@ def get_photo_path(instance, filename): return settings.USER_PHOTO_PATH + filename + class FeedUserManager(BaseUserManager): use_in_migrations = True @@ -278,6 +301,7 @@ def email_user(self, subject, message, from_email=None, **kwargs): """ send_mail(subject, message, from_email, [self.email], **kwargs) + class FeedUser(AbstractFeedUser): ################################### ============================== ################################### diff --git a/feedcrunch/task_files/task_send_emails.py b/feedcrunch/task_files/task_send_emails.py index 342b0ff3..6f84a55 100644 --- a/feedcrunch/task_files/task_send_emails.py +++ b/feedcrunch/task_files/task_send_emails.py @@ -4,7 +4,7 @@ from __future__ import unicode_literals from application.celery import app as celery -# + from django.conf import settings from django.core.mail import send_mail from django.template.loader import render_to_string diff --git a/feedcrunch/tests/test_post_model.py b/feedcrunch/tests/test_post_model.py index 7dfcdfd..392d81d 100644 --- a/feedcrunch/tests/test_post_model.py +++ b/feedcrunch/tests/test_post_model.py @@ -2,12 +2,19 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.test import TestCase, Client -from feedcrunch.models import Post, FeedUser +from django.test import TestCase from feedcrunch.factories import * -from application.settings import * -import factory, datetime +import datetime + + +def validate_date(date_text): + try: + datetime.datetime.strptime(date_text, '%Y/%m/%d %H:%M') + return True + except ValueError: + raise ValueError("Incorrect data format, should be %Y/%m/%d %H:%M") + class PostTest(TestCase): @@ -40,20 +47,13 @@ def test_get_domain_error(self): def test_get_date(self): date = PostFactory().get_date() self.assertIsInstance(date, str) - self.assertTrue(self.validate_date(date)) + self.assertTrue(validate_date(date)) def test_validate_date_ok(self): date = "2016/06/11 22:36" - self.assertTrue(self.validate_date(date)) + self.assertTrue(validate_date(date)) def test_validate_date_ko(self): date = "2016/21/01 22:36" with self.assertRaises(ValueError): - self.validate_date(date) - - def validate_date(self, date_text): - try: - datetime.datetime.strptime(date_text, '%Y/%m/%d %H:%M') - return True - except ValueError: - raise ValueError("Incorrect data format, should be %Y/%m/%d %H:%M") + validate_date(date) diff --git a/feedcrunch_api_v1/admin.py b/feedcrunch_api_v1/admin.py index 246461b..faa18be 100644 --- a/feedcrunch_api_v1/admin.py +++ b/feedcrunch_api_v1/admin.py @@ -1,7 +1,2 @@ #!/usr/bin/env python # -*- coding: utf-8 -*- - -from __future__ import unicode_literals -from django.contrib import admin - -# Register your models here. diff --git a/feedcrunch_api_v1/urls.py b/feedcrunch_api_v1/urls.py index 400d7eb..f196f7a 100644 --- a/feedcrunch_api_v1/urls.py +++ b/feedcrunch_api_v1/urls.py @@ -2,13 +2,9 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.conf import settings -from django.conf.urls import include, url -import django.contrib.auth.views -from django.views.decorators.csrf import csrf_exempt +from django.conf.urls import url -#from .admin import admin_site -from .views import * +from feedcrunch_api_v1.views import * from rest_framework.authtoken import views urlpatterns = [ diff --git a/feedcrunch_api_v1/views.py b/feedcrunch_api_v1/views.py index 5bdd022..5e1e95d 100644 --- a/feedcrunch_api_v1/views.py +++ b/feedcrunch_api_v1/views.py @@ -523,6 +523,7 @@ def get(self, request): ################### NEED TO CHECK AUTHENTICATION PROCESS ################### + class ArticleView(APIView): def get(self, request): diff --git a/feedcrunch_home/urls.py b/feedcrunch_home/urls.py index bb4f263..8e2b45a 100644 --- a/feedcrunch_home/urls.py +++ b/feedcrunch_home/urls.py @@ -5,10 +5,11 @@ from django.conf.urls import url +from django.conf import settings import django.contrib.auth.views import django.views.static -from .views import * +from feedcrunch_home.views import * urlpatterns = [ url(r'^$', index, name='index'), diff --git a/feedcrunch_home/views.py b/feedcrunch_home/views.py index 6487a5b..44cd5e8 100644 --- a/feedcrunch_home/views.py +++ b/feedcrunch_home/views.py @@ -3,17 +3,19 @@ from __future__ import unicode_literals -from django.contrib.auth import authenticate, login, logout -from django.conf import settings -from django.http import HttpResponse, HttpResponseRedirect -from django.shortcuts import render_to_response, redirect -from django.template import RequestContext, loader +from django.contrib.auth import authenticate +from django.contrib.auth import login + +from django.http import HttpResponseRedirect from rest_framework.authtoken.models import Token -from feedcrunch.models import Country, Option, FeedUser +from feedcrunch.models import Country +from feedcrunch.models import Option +from feedcrunch.models import FeedUser + +from functions.custom_render import myrender as render -from custom_render import myrender as render def index(request): try: @@ -24,18 +26,23 @@ def index(request): return render(request, 'home.html', {'free_period': freemium_period}) + def faq(request): return render(request, 'faq.html', {}) + def contact(request): return render(request, 'contact.html', {}) + def about(request): return render(request, 'about.html', {}) + def terms(request): return render(request, 'terms.html', {}) + def loginView(request): if request.method == 'POST': username = request.POST['username'].lower() @@ -55,6 +62,7 @@ def loginView(request): else: return render(request, 'login.html', {}) + def signUPView(request): if request.method == 'POST': diff --git a/feedcrunch_rssadmin/tests/__init__.py b/feedcrunch_rssadmin/tests/__init__.py index e69de29..faa18be 100644 --- a/feedcrunch_rssadmin/tests/__init__.py +++ b/feedcrunch_rssadmin/tests/__init__.py @@ -0,0 +1,2 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- diff --git a/feedcrunch_rssadmin/urls.py b/feedcrunch_rssadmin/urls.py index 30b5635..5505cd2 100644 --- a/feedcrunch_rssadmin/urls.py +++ b/feedcrunch_rssadmin/urls.py @@ -2,11 +2,9 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.conf.urls import include, url -from django.conf import settings +from django.conf.urls import url -#from .admin import admin_site -from .views import * +from feedcrunch_rssadmin.views import * urlpatterns = [ url(r'^$', index, name='dashboard'), diff --git a/feedcrunch_rssadmin/views.py b/feedcrunch_rssadmin/views.py index 7cacdcd..af0a2df 100644 --- a/feedcrunch_rssadmin/views.py +++ b/feedcrunch_rssadmin/views.py @@ -2,37 +2,39 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.contrib.auth import authenticate, login, logout -from django.core.validators import URLValidator -from django.core.exceptions import ValidationError, ObjectDoesNotExist -from django.http import HttpResponse, HttpResponseRedirect, JsonResponse -from django.shortcuts import render_to_response, redirect -from django.template import RequestContext, loader -from django.urls import reverse -import datetime, unicodedata, json +import datetime +import unicodedata from calendar import monthrange -from feedcrunch.models import Post, FeedUser, Country, Tag, RSSFeed, RSSArticle, RSSFeed_Sub, RSSArticle_Assoc, Interest, Option +from django.core.validators import URLValidator +from django.core.exceptions import ObjectDoesNotExist +from django.http import HttpResponseRedirect +from django.http import JsonResponse +from django.urls import reverse + +from feedcrunch.models import Post +from feedcrunch.models import FeedUser +from feedcrunch.models import Country +from feedcrunch.models import RSSFeed_Sub +from feedcrunch.models import RSSArticle_Assoc +from feedcrunch.models import Interest +from feedcrunch.models import Option -from oauth.twitterAPI import TwitterAPI +from oauth.twitterAPI import TwitterAPI from oauth.facebookAPI import FacebookAPI from oauth.linkedinAPI import LinkedInAPI from oauth.slackAPI import SlackAPI -from check_admin import check_admin -from data_convert import str2bool -from ap_style import format_title -from image_validation import get_image_dimensions -from custom_render import myrender as render +from functions.check_admin import check_admin +from functions.custom_render import myrender as render -# Create your views here. def index(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: @@ -74,10 +76,11 @@ def index(request, feedname=None): return render(request, 'admin/admin_dashboard.html', data) + def personal_info_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: @@ -85,42 +88,47 @@ def personal_info_form(request, feedname=None): country_list = Country.objects.all().order_by('name') return render(request, 'admin/admin_personal.html', {'countries': country_list}) + def preferences_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: return render(request, 'admin/admin_preferences.html', {"social_networks_enabled": request.user.is_social_network_enabled()}) + def password_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: return render(request, 'admin/admin_password.html') + def picture_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: return render(request, 'admin/admin_photo.html') + def social_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: return render(request, 'admin/admin_social_accounts.html') + def slack_management(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: request_data = dict() @@ -138,10 +146,11 @@ def slack_management(request, feedname=None): return render(request, 'admin/admin_slack_management.html', request_data) + def services_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: request_data = dict() @@ -165,18 +174,20 @@ def services_form(request, feedname=None): return render(request, 'admin/admin_social_sharing.html', request_data) + def add_article_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: return render(request, 'admin/admin_article_form.html') + def modify_article_form(request, feedname=None, postID=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed elif postID == None: @@ -190,32 +201,36 @@ def modify_article_form(request, feedname=None, postID=None): except: return HttpResponseRedirect("/@"+feedname+"/admin/modify") + def modify_article_listing(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: posts = Post.objects.filter(user = feedname).order_by('-id') return render(request, 'admin/admin_post_listing.html', {'posts': posts}) + def delete_article_listing(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: posts = Post.objects.filter(user = feedname).order_by('-id') return render(request, 'admin/admin_post_listing.html', {'posts': posts}) + def contact_form(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: return render(request, 'admin/admin_contact.html') + def upload_picture(request, feedname=None): try: @@ -260,17 +275,19 @@ def upload_picture(request, feedname=None): return HttpResponseRedirect('/@'+request.user.username+'/admin/account/picture/') + def sub_management(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: feeds = RSSFeed_Sub.objects.filter(user=feedname, feed__active=True).order_by("title") return render(request, 'admin/admin_sub_listing.html', {'feeds': feeds}) + def reading_recommendation(request, feedname=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed else: @@ -306,9 +323,10 @@ def reading_recommendation(request, feedname=None): print (len(rssarticles_data)) return render(request, 'admin/admin_reading_recommendation.html', {'rssarticles': rssarticles_data}) + def redirect_recommendation(request, feedname=None, RSSArticle_AssocID=None): check_passed = check_admin(feedname, request.user) - if check_passed != True: + if not check_passed: return check_passed try: @@ -321,10 +339,11 @@ def redirect_recommendation(request, feedname=None, RSSArticle_AssocID=None): except: return HttpResponseRedirect("/@"+feedname+"/admin/reading/recommendation/") + def onboarding_view(request, feedname=None): check_passed = check_admin(feedname, request.user, bypassOnboardingCheck = True) - if check_passed != True: + if not check_passed: return check_passed else: @@ -355,10 +374,11 @@ def onboarding_view(request, feedname=None): return render(request, 'admin/onboarding.html', request_data) + def process_onboarding_view(request, feedname=None): check_passed = check_admin(feedname, request.user, bypassOnboardingCheck = True) - if check_passed != True: + if not check_passed: return check_passed else: diff --git a/feedcrunch_rssviewer/admin.py b/feedcrunch_rssviewer/admin.py index 246461b..faa18be 100644 --- a/feedcrunch_rssviewer/admin.py +++ b/feedcrunch_rssviewer/admin.py @@ -1,7 +1,2 @@ #!/usr/bin/env python # -*- coding: utf-8 -*- - -from __future__ import unicode_literals -from django.contrib import admin - -# Register your models here. diff --git a/feedcrunch_rssviewer/tests/test_feedradar_rssviewer.py b/feedcrunch_rssviewer/tests/test_feedradar_rssviewer.py index 10b775e..e215ced 100644 --- a/feedcrunch_rssviewer/tests/test_feedradar_rssviewer.py +++ b/feedcrunch_rssviewer/tests/test_feedradar_rssviewer.py @@ -2,18 +2,16 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.test import TestCase, Client +from django.test import TestCase +from django.test import Client from django.urls import reverse -from feedcrunch.models import Post -from application.settings import * from feedcrunch.factories import * -import factory from feedparser import parse -from rss_generator import generateRSS -# Create your tests here. +from functions.rss_generator import generateRSS + class feedcrunch_rssviewer_TestCase(TestCase): def setUp(self): diff --git a/feedcrunch_rssviewer/urls.py b/feedcrunch_rssviewer/urls.py index 5d6b1e6..7cf75a4 100644 --- a/feedcrunch_rssviewer/urls.py +++ b/feedcrunch_rssviewer/urls.py @@ -2,11 +2,9 @@ # -*- coding: utf-8 -*- from __future__ import unicode_literals -from django.conf.urls import include, url -from django.conf import settings +from django.conf.urls import url -#from .admin import admin_site -from .views import * +from feedcrunch_rssviewer.views import * urlpatterns = [ diff --git a/feedcrunch_rssviewer/views.py b/feedcrunch_rssviewer/views.py index 3432440..746c61c 100644 --- a/feedcrunch_rssviewer/views.py +++ b/feedcrunch_rssviewer/views.py @@ -3,22 +3,17 @@ from __future__ import unicode_literals -from django.conf import settings -from django.contrib.auth import authenticate, login, logout -from django.http import HttpResponse, HttpResponseRedirect, JsonResponse -from django.shortcuts import render_to_response, redirect -from django.template import RequestContext, loader +from django.http import HttpResponse +from django.http import HttpResponseRedirect +from django.http import JsonResponse -import sys, os +from feedcrunch.models import Post +from feedcrunch.models import FeedUser +from feedcrunch.models import RSSSubscriber -from mimetypes import MimeTypes +from functions.custom_render import myrender as render +from functions.rss_generator import generateRSS -from feedcrunch.models import Post, FeedUser, RSSSubscriber - -from custom_render import myrender as render -from rss_generator import generateRSS - -# Create your views here. def index(request, feedname=None): @@ -37,6 +32,7 @@ def index(request, feedname=None): requested_user = FeedUser.objects.get(username=feedname) return render(request, 'rssviewer.html', {'posts': posts, 'requested_user': requested_user, 'rss_feed_display': True}) + def dataset(request, feedname=None): if feedname == None or (not FeedUser.objects.filter(username = feedname).exists()): @@ -55,6 +51,7 @@ def dataset(request, feedname=None): return HttpResponse(data_output) + def search(request, feedname=None): result = dict() @@ -90,6 +87,7 @@ def search(request, feedname=None): result["search_str"] = search_str return JsonResponse(result) + def redirect(request, feedname=None, postID=None): if postID == None or feedname == None : return HttpResponse("Error") @@ -104,6 +102,7 @@ def redirect(request, feedname=None, postID=None): except: return HttpResponseRedirect("/@"+feedname) + def rss_feed(request, feedname=None): if feedname == None: return HttpResponse("Error") @@ -121,6 +120,7 @@ def rss_feed(request, feedname=None): else: return HttpResponse("No Entries in this feed yet") + def atom_feed(request, feedname=None): if feedname == None: return HttpResponse("Error") diff --git a/functions/ap_style.py b/functions/ap_style.py index 2c6ae53..d249598 100644 --- a/functions/ap_style.py +++ b/functions/ap_style.py @@ -5,12 +5,13 @@ import re + def format_title(title): stopwords = 'a an and at but by for in nor of on or so the to up yet'.split(' ') if isinstance(title, str): - title = title.replace("–", "-") #en dash - title = title.replace("\u2013", "-") #en dash + title = title.replace("–", "-") # en dash + title = title.replace("\u2013", "-") # en dash title = title.strip().lower() rslt = "" @@ -30,4 +31,4 @@ def format_title(title): return output else: - raise ValueError("This datatype ( "+ type(title) +" ) is not handled by the application.") + raise ValueError("The datatype ( `%s` ) is not handled by the application." % type(title)) diff --git a/functions/check_admin.py b/functions/check_admin.py index d5b3b6a..9dc7f38 100644 --- a/functions/check_admin.py +++ b/functions/check_admin.py @@ -3,7 +3,9 @@ from __future__ import unicode_literals -from django.http import HttpResponse, HttpResponseRedirect +from django.http import HttpResponse +from django.http import HttpResponseRedirect + def check_admin(feedname, user, bypassOnboardingCheck = False): if feedname == None: @@ -24,6 +26,7 @@ def check_admin(feedname, user, bypassOnboardingCheck = False): else: return True + def check_admin_api(user): if not user.is_authenticated: diff --git a/functions/check_social_network.py b/functions/check_social_network.py index 9b43ca7..e4a7a77 100644 --- a/functions/check_social_network.py +++ b/functions/check_social_network.py @@ -5,6 +5,7 @@ from feedcrunch.models import FeedUser + def auto_format_social_network(social_network=None): if social_network is None: diff --git a/functions/clean_html.py b/functions/clean_html.py index 874eec5..73d06fc 100644 --- a/functions/clean_html.py +++ b/functions/clean_html.py @@ -3,19 +3,17 @@ from __future__ import unicode_literals -import re, unicodedata -from html.parser import HTMLParser +import re +import unicodedata +import html def clean_html(raw_html): # Normalizarion - if isinstance(raw_html, str): - cleantext = unicodedata.normalize('NFC', raw_html) + cleantext = unicodedata.normalize('NFC', raw_html) # Removing all HTML Tags cleanr = re.compile('<.*?>') cleantext = re.sub(cleanr, '', cleantext) # Remove all HTML Codes and convert them to string - cleantext = HTMLParser().unescape(cleantext) - - return cleantext + return html.unescape(cleantext) diff --git a/functions/custom_render.py b/functions/custom_render.py index 239f759..768ddba 100644 --- a/functions/custom_render.py +++ b/functions/custom_render.py @@ -6,7 +6,10 @@ from django.shortcuts import render from django.conf import settings -from feedcrunch.models import FeedUser, Post, Option +from feedcrunch.models import FeedUser +from feedcrunch.models import Post +from feedcrunch.models import Option + def myrender(request, template, dictionary={}): dictionary.update({'template_name': template}) diff --git a/functions/date_manipulation.py b/functions/date_manipulation.py index 30c423d..0a52d26 100644 --- a/functions/date_manipulation.py +++ b/functions/date_manipulation.py @@ -20,6 +20,6 @@ def get_N_time_period(N_periods=14, duration=1, max_date=datetime.datetime.now() for d in range(0, N_periods): rslt.append(d_today - datetime.timedelta(days=d*delta+1)) - rslt.reverse() #From the oldest day to the most recent + rslt.reverse() # From the oldest day to the most recent return rslt diff --git a/functions/feed_validation.py b/functions/feed_validation.py index fdfc6f6..e6e6cd0 100644 --- a/functions/feed_validation.py +++ b/functions/feed_validation.py @@ -5,6 +5,7 @@ import feedparser + def validate_feed(feed): if isinstance(feed, str): feed = feedparser.parse(feed) diff --git a/functions/image_validation.py b/functions/image_validation.py index ea352e9..911c523 100644 --- a/functions/image_validation.py +++ b/functions/image_validation.py @@ -46,7 +46,7 @@ def get_image_dimensions(data): height = int(h) elif is_jpeg(data): - jpeg = StringIO.StringIO(data) + jpeg = StringIO(data) jpeg.read(2) b = jpeg.read(1) try: diff --git a/functions/rss_generator.py b/functions/rss_generator.py index 5603b6e..5f29ec5 100644 --- a/functions/rss_generator.py +++ b/functions/rss_generator.py @@ -5,9 +5,13 @@ from django.core.exceptions import ObjectDoesNotExist -from feedcrunch.models import Post, FeedUser, Option +from feedcrunch.models import Post +from feedcrunch.models import FeedUser +from feedcrunch.models import Option + from feedgen.feed import FeedGenerator + def generateRSS(type="", username=""): if type not in ["rss", "atom"]: raise ValueError('Wrong Type of RSS Feed given to the generator, only "rss" and "atom" accepted.') diff --git a/functions/time_funcs.py b/functions/time_funcs.py index 48a0775..52e7c70 100644 --- a/functions/time_funcs.py +++ b/functions/time_funcs.py @@ -4,7 +4,7 @@ from __future__ import unicode_literals import datetime, time -# Create your views here. + def get_timestamp(): return datetime.datetime.fromtimestamp(time.time()).strftime('%Y-%m-%d %H:%M:%S') diff --git a/functions/validators.py b/functions/validators.py index 476c039..bd46b4c 100644 --- a/functions/validators.py +++ b/functions/validators.py @@ -5,6 +5,7 @@ import re from django.core import validators + from django.utils import six from django.utils.deconstruct import deconstructible from django.utils.translation import ugettext_lazy as _ diff --git a/oauth/facebookAPI.py b/oauth/facebookAPI.py index 5199105..1cea4a8 100644 --- a/oauth/facebookAPI.py +++ b/oauth/facebookAPI.py @@ -7,14 +7,15 @@ from feedcrunch.models import * -import sys, facebook, json +import facebook + class FacebookAPI(object): api = False post_illustration = "https://s3-eu-west-1.amazonaws.com/feedcrunch/static/home/images/social-share-images/social-img.png" callback_url = 'https://www.feedcrunch.io/oauth/facebook/get_callback/' callback_url_debug = 'http://local.feedcrunch.io:5000/oauth/facebook/get_callback/' - baseurl = "" + baseurl = '' app_permissions = [ 'public_profile', 'user_about_me', @@ -34,7 +35,7 @@ def __init__(self, user): self.api = facebook.GraphAPI(user.facebook_access_token) self.baseurl = "https://www.feedcrunch.io/@"+user.username+"/redirect/" - except Exception as e: + except Exception: self.api = False def connection_status(self): @@ -82,16 +83,18 @@ def verify_credentials(self): except: return {'status':False, 'error': "FacebookAPI.verify_credentials(): Credentials have not been verified"} + def publish_post(self, title, id, tag_list=None): + if tag_list is None: + tag_list = list() - def publish_post(self, title, id, tag_list=[]): try: - if self.api == False: + if not self.api: raise Exception("API Connection has failed during init phase") - tag_str = "" - if isinstance(tag_list, list) and tag_list: # if tag_list is not empty: + + if isinstance(tag_list, list) and tag_list: # if tag_list is not empty: for tag in tag_list: @@ -113,10 +116,13 @@ def publish_post(self, title, id, tag_list=[]): ## Response: {'id': '10211352122892746_10211354892441983'} response = self.api.put_wall_post(message, attachment=attach) - return {'status':True} + return {'status': True} except Exception as e: - return {'status':False, 'error':'FacebookAPI.publish_post() - Error: ' + str(e)} + return { + 'status': False, + 'error': 'FacebookAPI.publish_post() - Error: ' + str(e) + } ########################################################################################################## # =========================================== STATIC METHODS =========================================== # diff --git a/oauth/linkedinAPI.py b/oauth/linkedinAPI.py index 513401c..adcfa9d 100644 --- a/oauth/linkedinAPI.py +++ b/oauth/linkedinAPI.py @@ -7,9 +7,9 @@ from feedcrunch.models import * -import sys, json from linkedin import linkedin + class LinkedInAPI(object): api = False post_illustration = 'https://s3-eu-west-1.amazonaws.com/feedcrunch/static/home/images/social-share-images/social-img.png' @@ -56,7 +56,7 @@ def publish_post(self, title, id, tag_list=[]): raise Exception("API Connection has failed during init phase") tag_str = "" - if isinstance(tag_list, list) and tag_list: # if tag_list is not empty: + if isinstance(tag_list, list) and tag_list: # if tag_list is not empty: for tag in tag_list: @@ -77,10 +77,10 @@ def publish_post(self, title, id, tag_list=[]): visibility_code = 'anyone' ) - return {'status':True} + return {'status': True} except Exception as e: - return {'status':False, 'LinkedInAPI.publish_post() - Error': str(e)} + return {'status': False, 'LinkedInAPI.publish_post() - Error': str(e)} ########################################################################################################## # =========================================== STATIC METHODS =========================================== # @@ -117,7 +117,6 @@ def get_authorized_tokens(code): except: return {'status':False, 'error': "Failed to retrieve the consumer keys."} - if settings.DEBUG or settings.TESTING: api = linkedin.LinkedInAuthentication(linkedin_client_id, linkedin_client_secret, LinkedInAPI.callback_url_debug, LinkedInAPI.app_permissions) else: @@ -129,4 +128,4 @@ def get_authorized_tokens(code): return {'status':True, 'access_token': response.access_token, 'expires_in': response.expires_in} except Exception as e: - return {'status':False, 'error':'LinkedInAPI.get_authorized_tokens() - Error: ' + str(e)} + return {'status': False, 'error': 'LinkedInAPI.get_authorized_tokens() - Error: ' + str(e)} diff --git a/oauth/slackAPI.py b/oauth/slackAPI.py index d8882fc..779ac62 100644 --- a/oauth/slackAPI.py +++ b/oauth/slackAPI.py @@ -7,10 +7,9 @@ from feedcrunch.models import * -import sys, json - from slacker import Slacker + class SlackAPI(object): api = False post_illustration = 'https://s3-eu-west-1.amazonaws.com/feedcrunch/static/home/images/social-share-images/social-img.png' @@ -50,7 +49,7 @@ def connection_status(self): def verify_credentials(self): try: - if self.api == False: + if not self.api: raise Exception("API Connection has failed during init phase") if self.api.auth.test().body["ok"] == True: @@ -92,11 +91,11 @@ def is_channel_active(self, channel_name): def publish_post(self, slackChannel, title, postID, tag_list=[]): try: - if self.api == False: + if not self.api: raise Exception("API Connection has failed during init phase") tag_str = "" - if isinstance(tag_list, list) and tag_list: # if tag_list is not empty: + if isinstance(tag_list, list) and tag_list: # if tag_list is not empty: for tag in tag_list: diff --git a/oauth/tests.py b/oauth/tests.py index 7ce503c..8b13789 100644 --- a/oauth/tests.py +++ b/oauth/tests.py @@ -1,3 +1 @@ -from django.test import TestCase -# Create your tests here. diff --git a/oauth/twitterAPI.py b/oauth/twitterAPI.py index 2f8bd92..27b8e5d 100644 --- a/oauth/twitterAPI.py +++ b/oauth/twitterAPI.py @@ -7,10 +7,11 @@ from twython import Twython + class TwitterAPI(object): api = False maxsize_tweet = 140 - maxsize_hashtags = 27 # Allow to keep 85 char for the post title (95% of the post length is < 85 chars) + maxsize_hashtags = 27 # Allow to keep 85 char for the post title (95% of the post length is < 85 chars) length_link = 23 baseurl = "" @@ -23,14 +24,16 @@ def __init__(self, user): if not user.is_social_network_enabled(network="twitter"): raise ValueError("User has not enabled Twitter") else: - self.api = Twython(twitter_consumer_key, - twitter_consumer_secret, - user.twitter_token, - user.twitter_token_secret) + self.api = Twython( + twitter_consumer_key, + twitter_consumer_secret, + user.twitter_token, + user.twitter_token_secret + ) self.baseurl = "https://www.feedcrunch.io/@"+user.username+"/redirect/" - except Exception as e: + except Exception: self.api = False def connection_status(self): diff --git a/oauth/urls.py b/oauth/urls.py index 2b59e23..b737a60 100644 --- a/oauth/urls.py +++ b/oauth/urls.py @@ -3,11 +3,8 @@ from __future__ import unicode_literals -from django.conf.urls import include, url -from django.conf import settings - -#from .admin import admin_site -from .views import * +from django.conf.urls import url +from oauth.views import * urlpatterns = [ url(r'^twitter/get_callback/$', twitter_callback, name='twitter_callback'), diff --git a/oauth/views.py b/oauth/views.py index e800ba0..c2949b1 100644 --- a/oauth/views.py +++ b/oauth/views.py @@ -3,7 +3,6 @@ from django.http import JsonResponse from django.shortcuts import render -from django.urls import reverse from datetime import datetime, timedelta @@ -14,6 +13,7 @@ from feedcrunch.models import SlackIntegration + def twitter_callback(request): try: @@ -43,6 +43,7 @@ def twitter_callback(request): return JsonResponse(data) + def facebook_callback(request): try: @@ -71,6 +72,7 @@ def facebook_callback(request): return JsonResponse(data) + def linkedin_callback(request): try: @@ -99,6 +101,7 @@ def linkedin_callback(request): return JsonResponse(data) + def slack_callback(request): try: