RESPONSIBILTIY'S COOL

This commit is contained in:
codl 2017-08-01 20:57:15 +02:00
parent fffb38bc9a
commit 0f80fc74a0
No known key found for this signature in database
GPG Key ID: 6CD7C8891ED1233A
8 changed files with 142 additions and 20 deletions

View File

@ -1 +1,3 @@
from .auth import require_auth
from .interval import decompose_interval
from .interval import SCALES as interval_scales

50
lib/interval.py Normal file
View File

@ -0,0 +1,50 @@
from datetime import timedelta
SCALES = [
('seconds', timedelta(seconds=1)),
('minutes', timedelta(minutes=1)),
('hours', timedelta(hours=1)),
('days', timedelta(days=1)),
('months', timedelta(days=30)),
('years', timedelta(days=365)),
]
def decompose_interval(attrname):
scales = [scale[1] for scale in SCALES]
scales.reverse()
def decorator(cls):
scl_name = '{}_scale'.format(attrname)
sig_name = '{}_significand'.format(attrname)
@property
def scale(self):
for m in scales:
if getattr(self, attrname) % m == timedelta(0):
return m
return timedelta(seconds=1)
@scale.setter
def scale(self, value):
print(value)
if(type(value) != timedelta):
value = timedelta(seconds=float(value))
print(value)
setattr(self, attrname, getattr(self, sig_name) * value)
@property
def significand(self):
return int(getattr(self, attrname) / getattr(self, scl_name))
@significand.setter
def significand(self, value):
setattr(self, attrname, int(value) * getattr(self, scl_name))
setattr(cls, scl_name, scale)
setattr(cls, sig_name, significand)
return cls
return decorator

View File

@ -0,0 +1,32 @@
"""empty message
Revision ID: 9fab742962ef
Revises: 711770097f06
Create Date: 2017-08-01 00:33:59.183437
"""
from alembic import op
import sqlalchemy as sa
# revision identifiers, used by Alembic.
revision = '9fab742962ef'
down_revision = '711770097f06'
branch_labels = None
depends_on = None
def upgrade():
# ### commands auto generated by Alembic - please adjust! ###
op.add_column('accounts', sa.Column('policy_delete_every', sa.Interval(), server_default='0', nullable=True))
op.add_column('accounts', sa.Column('policy_keep_latest', sa.Integer(), server_default='0', nullable=True))
op.add_column('accounts', sa.Column('policy_keep_younger', sa.Interval(), server_default='0', nullable=True))
# ### end Alembic commands ###
def downgrade():
# ### commands auto generated by Alembic - please adjust! ###
op.drop_column('accounts', 'policy_keep_younger')
op.drop_column('accounts', 'policy_keep_latest')
op.drop_column('accounts', 'policy_delete_every')
# ### end Alembic commands ###

View File

@ -4,6 +4,7 @@ from app import db
from twitter import Twitter, OAuth
import secrets
from lib import decompose_interval
class TimestampMixin(object):
created_at = db.Column(db.DateTime, server_default=db.func.now())
@ -33,15 +34,17 @@ class RemoteIDMixin(object):
class Account(db.Model, TimestampMixin, RemoteIDMixin):
@decompose_interval('policy_delete_every')
@decompose_interval('policy_keep_younger')
class Account(TimestampMixin, RemoteIDMixin):
__tablename__ = 'accounts'
id = db.Column(db.String, primary_key=True)
policy_enabled = db.Column(db.Boolean, server_default='FALSE', nullable=False)
# policy_keep_younger = db.Column(db.Interval)
# policy_keep_latest = db.Column(db.Integer)
# policy_delete_every = db.Column(db.Interval)
policy_keep_latest = db.Column(db.Integer, server_default='0')
policy_ignore_favourites = db.Column(db.Boolean, server_default='TRUE')
policy_delete_every = db.Column(db.Interval, server_default='0', default=0)
policy_keep_younger = db.Column(db.Interval, server_default='0', default=0)
remote_display_name = db.Column(db.String)
remote_screen_name = db.Column(db.String)
@ -61,6 +64,11 @@ class Account(db.Model, TimestampMixin, RemoteIDMixin):
def post_count(self):
return Post.query.filter(Post.author_id == self.id).count()
class Account(Account, db.Model):
pass
class OAuthToken(db.Model, TimestampMixin):
__tablename__ = 'oauth_tokens'

View File

@ -2,6 +2,7 @@ from app import app
from flask import render_template, url_for, redirect, request, g, Response
from datetime import datetime
import lib.twitter
import lib
from lib import require_auth
from model import Account, Session, Post, TwitterArchive
from app import db
@ -46,7 +47,7 @@ def twitter_login_step2():
db.session.add(session)
db.session.commit()
tasks.fetch_acc.s(token.account_id).delay()
tasks.fetch_acc.s(token.account_id).apply_async(routing_key='high')
resp = Response(status=302, headers={"location": url_for('index')})
resp.set_cookie('forget_sid', session.id,
@ -63,7 +64,7 @@ def upload_tweet_archive():
db.session.add(ta)
db.session.commit()
tasks.import_twitter_archive.s(ta.id).apply_async()
tasks.import_twitter_archive.s(ta.id).apply_async(routing_key='high')
return render_template('upload_tweet_archive.html')
@ -71,13 +72,20 @@ def upload_tweet_archive():
@require_auth
def settings():
if request.method == 'POST':
for attr in ('policy_enabled', 'policy_ignore_favourites'):
for attr in ('policy_enabled',
'policy_ignore_favourites',
'policy_keep_latest',
'policy_delete_every_significand',
'policy_delete_every_scale',
'policy_keep_younger_significand',
'policy_keep_younger_scale',
):
if attr in request.form:
setattr(g.viewer.account, attr, request.form[attr])
db.session.commit()
return render_template('settings.html')
return render_template('settings.html', scales=lib.interval_scales)

View File

@ -10,8 +10,17 @@ from datetime import timedelta, datetime
from zipfile import ZipFile
from io import BytesIO, TextIOWrapper
import json
from kombu import Queue
app = Celery('tasks', broker=flaskapp.config['CELERY_BROKER'], task_serializer='pickle')
app.conf.task_queues = (
Queue('default', routing_key='celery'),
Queue('high_prio', routing_key='high'),
Queue('higher_prio', routing_key='higher'),
)
app.conf.task_default_queue = 'default'
app.conf.task_default_exchange = 'celery'
app.conf.task_default_exchange_type = 'direct'
@app.task(autoretry_for=(TwitterError, URLError))
def fetch_acc(id, cursor=None):

View File

@ -0,0 +1,15 @@
{% macro interval_input(obj, attrname, scales) -%}
<input type=number name={{attrname}}_significand
value={{obj[attrname + '_significand']}}
style='max-width:8ch' min=0 step=1>
<select name={{attrname}}_scale>
{%- for scale in scales %}
<option value="{{scale[1].total_seconds()}}"
{{- ' selected' if scale[1] == obj[attrname + '_scale'] -}}
>{{scale[0]}}</option>
{% endfor -%}
</select>
{%- endmacro %}

View File

@ -9,21 +9,19 @@
<label><input type=radio name=policy_enabled value=true {{ "checked" if g.viewer.account.policy_enabled }}> Enabled</label>
<label><input type=radio name=policy_enabled value=false {{ "checked" if not g.viewer.account.policy_enabled }}> Disabled</label>
</p>
{#
{%- from 'lib/interval.html' import interval_input %}
<p>Delete one post every
{{interval_input(g.viewer.account, 'policy_delete_every', scales)}}
</p>
<p>Keep posts less than
<input type=number name=policy_keep_younger min=0 step=1 max=30>
<select name=policy_keep_younger_multiplier>
<option name=1>seconds</option>
<option name=60>minutes</option>
<option name=3600>hours</option>
<option name=86400>days</option>
<option name=2635200>months</option>
<option name=31536000>years</option>
</select>
{{interval_input(g.viewer.account, 'policy_keep_younger', scales)}}
old
</p>
#}
<p>Keep posts that you have favourited:
<p>Keep my
<input type=number name=policy_keep_latest min=0 step=1 style='max-width:8ch' value={{g.viewer.account.policy_keep_latest}}>
latest posts
</p>
<p>Keep posts that I have favourited
<label><input type=radio name=policy_ignore_favourites value=true {{ "checked" if g.viewer.account.policy_ignore_favourites }}> Yes</label>
<label><input type=radio name=policy_ignore_favourites value=false {{ "checked" if not g.viewer.account.policy_ignore_favourites }}> No</label>
</p>