Compare commits

...

2 Commits

Author SHA1 Message Date
Derek 333dbf9faa
Implement basic ratelimiting 2018-07-26 14:30:23 -07:00
Derek d729ab8ef0
Fix various css bugs
Fixes
+ Responsive layout down to 320px width
+ waifu drawing over file list
+ filename wrapping
2018-07-26 13:45:19 -07:00
5 changed files with 40 additions and 1 deletions

View File

@ -11,6 +11,7 @@ flask-sqlalchemy = "*"
bcrypt = "*" bcrypt = "*"
flask-migrate = "*" flask-migrate = "*"
click = "*" click = "*"
flask-limiter = "*"
[dev-packages] [dev-packages]

16
Pipfile.lock generated
View File

@ -1,7 +1,7 @@
{ {
"_meta": { "_meta": {
"hash": { "hash": {
"sha256": "294652d06b03e0498836999c31a5a8e12c60ddb8074f2a5499604ab0f6abfb3b" "sha256": "0d5dbb20521ef4c84be501e1e8244c768893c4b70ecf958bf657e9825c212d09"
}, },
"pipfile-spec": 6, "pipfile-spec": 6,
"requires": { "requires": {
@ -116,6 +116,13 @@
"index": "pypi", "index": "pypi",
"version": "==1.0.2" "version": "==1.0.2"
}, },
"flask-limiter": {
"hashes": [
"sha256:8cce98dcf25bf2ddbb824c2b503b4fc8e1a139154240fd2c60d9306bad8a0db8"
],
"index": "pypi",
"version": "==1.0.1"
},
"flask-login": { "flask-login": {
"hashes": [ "hashes": [
"sha256:c815c1ac7b3e35e2081685e389a665f2c74d7e077cb93cecabaea352da4752ec" "sha256:c815c1ac7b3e35e2081685e389a665f2c74d7e077cb93cecabaea352da4752ec"
@ -160,6 +167,13 @@
], ],
"version": "==2.10" "version": "==2.10"
}, },
"limits": {
"hashes": [
"sha256:9df578f4161017d79f5188609f1d65f6b639f8aad2914c3960c9252e56a0ff95",
"sha256:a017b8d9e9da6761f4574642149c337f8f540d4edfe573fb91ad2c4001a2bc76"
],
"version": "==1.3"
},
"mako": { "mako": {
"hashes": [ "hashes": [
"sha256:4e02fde57bd4abb5ec400181e4c314f56ac3e49ba4fb8b0d50bba18cb27d25ae" "sha256:4e02fde57bd4abb5ec400181e4c314f56ac3e49ba4fb8b0d50bba18cb27d25ae"

View File

@ -2,6 +2,8 @@ from flask import Flask, render_template, flash, send_from_directory, redirect,
from flask_sqlalchemy import SQLAlchemy from flask_sqlalchemy import SQLAlchemy
from flask_migrate import Migrate from flask_migrate import Migrate
from flask_login import LoginManager, current_user, login_user, logout_user, login_required from flask_login import LoginManager, current_user, login_user, logout_user, login_required
from flask_limiter import Limiter
import flask_limiter.util
from operator import itemgetter from operator import itemgetter
import os import os
@ -23,6 +25,8 @@ login_manager.login_view = "login"
def load_user(id): def load_user(id):
return User.query.get(id) return User.query.get(id)
limiter = Limiter(app, key_func=flask_limiter.util.get_ipaddr, headers_enabled=True)
@app.route('/') @app.route('/')
def index(): def index():
if current_user.is_authenticated: if current_user.is_authenticated:
@ -31,6 +35,7 @@ def index():
return redirect(url_for('login')) return redirect(url_for('login'))
@app.route('/login', methods=['GET', 'POST']) @app.route('/login', methods=['GET', 'POST'])
@limiter.limit("8/minute;1/second", exempt_when=lambda : request.method == 'GET')
def login(): def login():
if request.method == 'GET': if request.method == 'GET':
if current_user.is_authenticated: if current_user.is_authenticated:
@ -60,6 +65,7 @@ def login():
return redirect(request.path) return redirect(request.path)
@app.route('/signup', methods=['GET', 'POST']) @app.route('/signup', methods=['GET', 'POST'])
@limiter.limit("5/minute;1/second", exempt_when=lambda : request.method == 'GET')
def signup(): def signup():
referal_key = request.args.get('referalkey') referal_key = request.args.get('referalkey')
if not referal_key: if not referal_key:
@ -99,6 +105,7 @@ def logout():
#FIXME: make this functionality avalible in a settings/admin view #FIXME: make this functionality avalible in a settings/admin view
@app.route('/newreferal') @app.route('/newreferal')
@login_required @login_required
@limiter.limit("50/hour;2/second", key_func=lambda : current_user)
def newreferal(): def newreferal():
referal = Referal(current_user) referal = Referal(current_user)
db.session.add(referal) db.session.add(referal)
@ -147,5 +154,9 @@ def page_not_found(e):
def internal_error(e): def internal_error(e):
return render_template('500.html'), 500 return render_template('500.html'), 500
@app.errorhandler(429)
def rate_limit(e):
return render_template('429.html', back=request.path), 429
if __name__ == "__main__": if __name__ == "__main__":
app.run() app.run()

View File

@ -33,11 +33,13 @@ body {
position: sticky; position: sticky;
top: 0px; top: 0px;
max-width: 600px; max-width: 600px;
min-width: 320px;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
flex: auto; flex: auto;
padding: 8px 16px; padding: 8px 16px;
margin: auto; margin: auto;
box-sizing: border-box;
} }
#contentarea > *:not(:last-child) { #contentarea > *:not(:last-child) {
margin-top: 0px; margin-top: 0px;
@ -141,6 +143,9 @@ button:active {
.item-name { .item-name {
flex: auto; flex: auto;
min-width: 1%;
word-wrap: break-word;
padding-right: 8px;
} }
.item-size { .item-size {
white-space: nowrap; white-space: nowrap;
@ -205,6 +210,7 @@ button.nostyle {
position: fixed; position: fixed;
bottom: 0px; bottom: 0px;
right: 0px; right: 0px;
z-index: -1;
max-width: 30vw; max-width: 30vw;
max-height: 100vh; max-height: 100vh;
} }

7
templates/429.html Normal file
View File

@ -0,0 +1,7 @@
{% extends 'error.html' %}
{% block head %}
sTOP IT
{% endblock %}
{% block disc %}
Whoa buddy calm down, you're going too fast. Go drink some tea and then <a href="{{ back }}">try again.</a>
{% endblock %}