diff --git a/feedler/migrations/0008_auto_20171013_2342.py b/feedler/migrations/0008_auto_20171013_2342.py new file mode 100644 index 0000000..f958257 --- /dev/null +++ b/feedler/migrations/0008_auto_20171013_2342.py @@ -0,0 +1,30 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.11.6 on 2017-10-13 21:42 +from __future__ import unicode_literals + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('feedler', '0007_auto_20171013_1515'), + ] + + operations = [ + migrations.AddField( + model_name='feedlysettings', + name='refresh', + field=models.CharField(blank=True, help_text='Refresh Token for automatic update (pro account)', max_length=1024), + ), + migrations.AlterField( + model_name='feedlysettings', + name='token', + field=models.CharField(blank=True, help_text='Access Token from feedly.com/v3/auth/dev', max_length=1024), + ), + migrations.AlterField( + model_name='stream', + name='ident', + field=models.CharField(help_text='Example: enterprise/myuser/tag/abcd...', max_length=255), + ), + ] diff --git a/feedler/models/admin.py b/feedler/models/admin.py index 43c5972..8cf5429 100644 --- a/feedler/models/admin.py +++ b/feedler/models/admin.py @@ -17,8 +17,10 @@ from feedler.refresh import refresh_streams class FeedlySettings(BaseSetting): streams = models.ManyToManyField(Stream, help_text='Which streams to update') - token = models.CharField(max_length=255, blank=True, - help_text='Access Token from developer.feedly.com') + token = models.CharField(max_length=1024, blank=True, + help_text='Access Token from feedly.com/v3/auth/dev') + refresh = models.CharField(max_length=1024, blank=True, + help_text='Refresh Token for automatic update (pro account)') class Meta: verbose_name = 'Feedly' diff --git a/feedler/models/models.py b/feedler/models/models.py index a1f9a82..ae79926 100644 --- a/feedler/models/models.py +++ b/feedler/models/models.py @@ -10,7 +10,8 @@ from wagtail.wagtailcore.fields import RichTextField class Stream(models.Model): title = models.CharField(max_length=255) - ident = models.CharField(max_length=255) + ident = models.CharField(max_length=255, + help_text='Example: enterprise/myuser/tag/abcd...') def __str__(self): return self.title diff --git a/feedler/refresh.py b/feedler/refresh.py index e361358..abd0181 100644 --- a/feedler/refresh.py +++ b/feedler/refresh.py @@ -4,6 +4,7 @@ import requests, json, codecs import logging logger = logging.getLogger('feedler') +logger.setLevel(logging.DEBUG) from .models import Entry from feedler import feedparser @@ -14,30 +15,29 @@ API_TOKENS = API_BASEURL + 'auth/token' def refresh_streams(settings): # Iterate through all saved streams - logger.warn("Refreshing all streams") + logger.debug("Refreshing all streams") for stream in settings.streams.all(): if not refresh_stream(stream, settings): return False return True -def get_headers(settings): - return { - 'Authorization': 'OAuth ' + settings.token - } - def refresh_token(settings): # Request a new token url = API_TOKENS - logger.warn("Refreshing Feedly access token") + if not settings.refresh: + logger.warn("No Refresh token available") + return False + logger.info("Refreshing Feedly access token") payload = { - 'refresh_token': settings.token, + 'refresh_token': settings.refresh, 'client_id': 'feedlydev', 'client_secret': 'feedlydev', 'grant_type': 'refresh_token' } - contents = requests.get(url, data=payload, headers=get_headers(settings)).json() + contents = requests.post(url, data=payload).json() if not 'access_token' in contents or not contents['access_token']: - logger.error("Access token could not be refreshed.") + logger.warn("Access token could not be refreshed.") + logger.debug(contents) return False settings.token = contents['access_token'] settings.save() @@ -45,12 +45,14 @@ def refresh_token(settings): def refresh_stream(stream, settings, retry=False): # Start a request to download the feed for a particular stream - logger.warn("Processing stream %s" % stream.title) + logger.info("Processing stream %s" % stream.title) url = API_STREAMS + stream.ident - contents = requests.get(url, headers=get_headers(settings)).json() + headers = { 'Authorization': 'OAuth ' + settings.token } + contents = requests.get(url, headers=headers).json() if 'errorMessage' in contents: # Usually this is a token expired if 'token expired' in contents['errorMessage'] or 'unauthorized' in contents['errorMessage']: + logger.debug(contents['errorMessage']) if not refresh_token(settings): return False # Make another attempt if retry or not refresh_stream(stream, settings, True):