support excluding feeds from the front page
and some style/UI tweaks
This commit is contained in:
parent
190bb1eb55
commit
bca07e2178
11 changed files with 77 additions and 28 deletions
|
@ -99,7 +99,9 @@ class Subscription(db.Model):
|
|||
# user-editable name of this subscribed feed
|
||||
name = db.Column(db.String(256))
|
||||
tags = db.Column(db.String(256))
|
||||
|
||||
# exclude from the front page
|
||||
exclude = db.Column(db.Boolean, default=False)
|
||||
|
||||
user = db.relationship(User, backref='subscriptions')
|
||||
feed = db.relationship(Feed, backref='subscriptions')
|
||||
|
||||
|
|
|
@ -64,15 +64,16 @@ $(function(){
|
|||
function attachListeners() {
|
||||
$("#older-link").off('click').click(clickOlderLink);
|
||||
$(".micropub-form button[type='submit']").off('click').click(submitMicropubForm);
|
||||
$(".reply-area").hide();
|
||||
$(".reply-area.closed").hide();
|
||||
|
||||
$("article").off('click').click(function(evt) {
|
||||
var $target = $(evt.target);
|
||||
if ($target.closest("form, a, video, audio").length == 0) {
|
||||
|
||||
$(".reply-area", this).toggleClass("closed");
|
||||
$(".reply-area", this).slideToggle(200);
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -360,7 +360,8 @@ th {
|
|||
/* Subtlety of Hue */
|
||||
body {
|
||||
font: 12pt Helvetica, Arial, sans-serif;
|
||||
background: #ecebf0;
|
||||
/*background: $athens-gray;*/
|
||||
background: #f4f4f4;
|
||||
padding-top: 1em; }
|
||||
|
||||
a {
|
||||
|
@ -410,12 +411,13 @@ ul#navigation {
|
|||
|
||||
article {
|
||||
margin-bottom: 2em;
|
||||
box-shadow: 0 0 2px #687d77;
|
||||
background-color: white;
|
||||
/*box-shadow: $box-shadow;
|
||||
background-color: white;*/
|
||||
padding: 0.5em; }
|
||||
article.reply-context {
|
||||
margin-bottom: 0;
|
||||
background-color: #f3f3f3; }
|
||||
background-color: #e0e0e0;
|
||||
color: #555; }
|
||||
article.reply-context .content img {
|
||||
max-height: 240px;
|
||||
max-width: 240px; }
|
||||
|
|
|
@ -17,7 +17,8 @@ $box-shadow: 0 0 2px $sirocco;
|
|||
|
||||
body {
|
||||
font: 12pt $body-font;
|
||||
background: $athens-gray;
|
||||
/*background: $athens-gray;*/
|
||||
background: #f4f4f4;
|
||||
padding-top: 1em;
|
||||
}
|
||||
|
||||
|
@ -86,13 +87,14 @@ ul#navigation {
|
|||
|
||||
article {
|
||||
margin-bottom: 2em;
|
||||
box-shadow: $box-shadow;
|
||||
background-color: white;
|
||||
/*box-shadow: $box-shadow;
|
||||
background-color: white;*/
|
||||
padding: 0.5em;
|
||||
|
||||
&.reply-context {
|
||||
margin-bottom: 0;
|
||||
background-color: #f3f3f3;
|
||||
background-color: #e0e0e0;
|
||||
color: #555;
|
||||
.content img {
|
||||
max-height: 240px;
|
||||
max-width: 240px;
|
||||
|
@ -246,10 +248,10 @@ button {
|
|||
.reply-area {
|
||||
text-align: center;
|
||||
margin-top: 0.5em;
|
||||
|
||||
|
||||
.content {
|
||||
height: 4em;
|
||||
}
|
||||
}
|
||||
|
||||
.reply-link {
|
||||
display: inline-block;
|
||||
|
|
|
@ -18,8 +18,20 @@ $(function() {
|
|||
}).fail(function failure() {
|
||||
$(".save-status", form).html("Save Failed!");
|
||||
});
|
||||
});
|
||||
|
||||
$("form.poll-now").submit(function(evt) {
|
||||
var form = $(this);
|
||||
evt.preventDefault();
|
||||
|
||||
$(".poll-status", form).html("");
|
||||
|
||||
$.post(form.attr('action'), form.serialize(), function success(){
|
||||
$(".poll-status", form).html("Poll Requested.");
|
||||
}).fail(function failure() {
|
||||
$(".poll-status", form).html("Polling Failed!");
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
|
|
|
@ -311,8 +311,13 @@ def notify_feed_updated(app, feed_id, entry_ids):
|
|||
'subscription': s.id,
|
||||
'entries': rendered,
|
||||
})
|
||||
for topic in ('user:{}'.format(s.user.id),
|
||||
'subsc:{}'.format(s.id)):
|
||||
|
||||
topics = []
|
||||
if not s.exclude:
|
||||
topics.append('user:{}'.format(s.user.id))
|
||||
topics.append('subsc:{}'.format(s.id))
|
||||
|
||||
for topic in topics:
|
||||
redis.publish('woodwind_notify:{}'.format(topic), message)
|
||||
|
||||
|
||||
|
|
|
@ -73,7 +73,7 @@
|
|||
| {% for synd in entry.get_property('syndication') %} <a href="{{ synd }}">{{ synd | domain_for_url}}</a>{% endfor %}
|
||||
{% endif %}
|
||||
|
||||
<div class="reply-area">
|
||||
<div class="reply-area closed">
|
||||
{% include '_reply.jinja2' with context %}
|
||||
</div>
|
||||
</footer>
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
<link rel="shortcut icon" href="{{ url_for('static', filename='logo.png') }}"/>
|
||||
<link rel="apple-touch-icon" href="{{ url_for('static', filename='logo.png') }}"/>
|
||||
|
||||
<link rel="stylesheet" href="{{ url_for('static', filename='style.css', version='2015-10-07') }}"/>
|
||||
<link rel="stylesheet" href="{{ url_for('static', filename='style.css', version='2015-11-25') }}"/>
|
||||
<link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/font-awesome/4.3.0/css/font-awesome.min.css"/>
|
||||
<script src="//code.jquery.com/jquery-2.1.3.min.js"></script>
|
||||
<script src="{{ url_for('static', filename='moment.min.js') }}"></script>
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
{% if ws_topic %}
|
||||
<script>var WS_TOPIC = "{{ ws_topic }}";</script>
|
||||
{% endif %}
|
||||
<script src="{{url_for('static', filename='feed.js', version='2015-10-08')}}"></script>
|
||||
<script src="{{url_for('static', filename='feed.js', version='2015-11-06')}}"></script>
|
||||
|
||||
{% if current_user and current_user.settings
|
||||
and current_user.settings.get('reply-method') == 'indie-config' %}
|
||||
|
|
|
@ -38,6 +38,12 @@
|
|||
<input type="text" name="tags" value="{{ s.tags or ''}}"/>
|
||||
<label>URL</label>
|
||||
<input type="text" name="feed" value="{{ s.feed.feed }}" readonly />
|
||||
|
||||
<label style="display: block; font-weight: normal;">
|
||||
<input type="checkbox" name="exclude" value="true" {% if s.exclude %}checked{% endif %} />
|
||||
Exclude from primary feed
|
||||
</label>
|
||||
|
||||
<button type="submit">Save Edits</button> <span class="save-status"></span>
|
||||
</form>
|
||||
|
||||
|
@ -63,14 +69,14 @@
|
|||
</div>
|
||||
|
||||
|
||||
<form action="{{ url_for('.update_feed') }}" method="POST" style="display:inline">
|
||||
<form class="poll-now" action="{{ url_for('.update_feed') }}" method="POST" style="display:inline">
|
||||
<input type="hidden" name="id" value="{{ s.feed.id }}"/>
|
||||
<button type="submit">Poll Now</button>
|
||||
<button type="submit">Poll Now</button> <span class="poll-status"></span>
|
||||
</form>
|
||||
|
||||
<form action="{{ url_for('.unsubscribe') }}" method="POST" style="display:inline">
|
||||
<form class="unsubscribe" action="{{ url_for('.unsubscribe') }}" method="POST" style="display:inline">
|
||||
<input type="hidden" name="id" value="{{ s.id }}"/>
|
||||
<button type="submit">Unsubscribe</button>
|
||||
<button type="submit">Unsubscribe</button> <span class="unsubscribe-status"></span>
|
||||
</form>
|
||||
|
||||
|
||||
|
|
|
@ -2,7 +2,8 @@ from . import tasks, util
|
|||
from .extensions import db, login_mgr, micropub
|
||||
from .models import Feed, Entry, User, Subscription
|
||||
import flask.ext.login as flask_login
|
||||
import binascii
|
||||
|
||||
import base64
|
||||
import bs4
|
||||
import datetime
|
||||
import feedparser
|
||||
|
@ -74,6 +75,7 @@ def index():
|
|||
entry_query = entry_query.filter(
|
||||
sqlalchemy.sql.expression.cast(Entry.properties['jam'], sqlalchemy.TEXT) == 'true')
|
||||
else:
|
||||
entry_query = entry_query.filter(Subscription.exclude == False)
|
||||
ws_topic = 'user:{}'.format(flask_login.current_user.id)
|
||||
|
||||
entry_query = entry_query.order_by(Entry.retrieved.desc(),
|
||||
|
@ -226,6 +228,7 @@ def edit_subscription():
|
|||
subsc.tags = ' '.join(t.strip() for t in tag_list if t.strip())
|
||||
else:
|
||||
subsc.tags = None
|
||||
subsc.exclude = flask.request.form.get('exclude') == 'true'
|
||||
|
||||
db.session.commit()
|
||||
flask.flash('Edited {}'.format(subsc.name))
|
||||
|
@ -609,13 +612,29 @@ def add_preview(content):
|
|||
|
||||
@views.app_template_filter()
|
||||
def proxy_image(url):
|
||||
proxy_url = flask.current_app.config.get('IMAGEPROXY_URL')
|
||||
proxy_key = flask.current_app.config.get('IMAGEPROXY_KEY')
|
||||
if proxy_url and proxy_key:
|
||||
sig = base64.urlsafe_b64encode(
|
||||
hmac.new(proxy_key.encode(), url.encode(), hashlib.sha256).digest()
|
||||
).decode()
|
||||
return '/'.join((proxy_url.rstrip('/'), 's' + sig, url))
|
||||
|
||||
pilbox_url = flask.current_app.config.get('PILBOX_URL')
|
||||
pilbox_key = flask.current_app.config.get('PILBOX_KEY')
|
||||
if pilbox_url and pilbox_key:
|
||||
query = urllib.parse.urlencode({'url': url, 'op': 'noop'})
|
||||
sig = hmac.new(pilbox_key.encode(), query.encode(), hashlib.sha1).hexdigest()
|
||||
query += '&sig=' + sig
|
||||
return pilbox_url + '?' + query
|
||||
|
||||
camo_url = flask.current_app.config.get('CAMO_URL')
|
||||
camo_key = flask.current_app.config.get('CAMO_KEY')
|
||||
if not camo_url or not camo_key:
|
||||
return url
|
||||
digest = hmac.new(camo_key.encode(), url.encode(), hashlib.sha1).hexdigest()
|
||||
return (urllib.parse.urljoin(camo_url, digest)
|
||||
+ '?url=' + urllib.parse.quote_plus(url))
|
||||
if camo_url and camo_key:
|
||||
digest = hmac.new(camo_key.encode(), url.encode(), hashlib.sha1).hexdigest()
|
||||
return (urllib.parse.urljoin(camo_url, digest)
|
||||
+ '?url=' + urllib.parse.quote_plus(url))
|
||||
return url
|
||||
|
||||
|
||||
@views.app_template_filter()
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue