import random, time, threading

from flask import Flask, jsonify, request
app = Flask(__name__)

from redis import StrictRedis as Redis
redis = Redis("redis", decode_responses=True)

import ruamel.yaml as yaml
with open("config.yaml", "r") as f:
    config = yaml.safe_load(f)

    if not config:
        exit("Missing configuration!")

def err(msg):
    print("err: " + msg)
    return jsonify({
        "status": 1,
        "error": msg
    })

@app.route("/upload", methods=["POST"])
def index():
    if request.form["secret"] not in config["passwords"]:
        return err("Invalid password")

    if "file" not in request.files:
        return err("No file part")

    f = request.files["file"]

    if f.filename == "":
        return err("Empty file")

    if "." not in f.filename:
        return err("No file extension")

    file_ext = f.filename.rsplit(".", 1)[1].lower()
    if file_ext not in config["allowed_extensions"]:
        return err("File extension not allowed!")

    filename = str()
    while True:
        filename = "_"
        for x in range(0, config["filename"]["length"]):
            filename += random.choice(config["filename"]["characters"])

        filename += "." + file_ext

        if redis.zscore("files", filename) == None:
            break

    f.save("/files/{}".format(filename))

    file_id = redis.incr("file_id")
    now = time.time()

    redis.zadd("files", now, file_id)

    hashkey = "file:" + str(file_id)
    redis.hset(hashkey, "filename", filename)
    redis.hset(hashkey, "uploader_ip", request.environ["REMOTE_ADDR"])
    redis.hset(hashkey, "time", now)
    redis.hset(hashkey, "password", request.form["secret"])

    print("Uploaded {}".format(filename))

    return jsonify({
        "status": 0,
        "uploaded_name": filename
    })

def clean_old_files():
    threading.Timer(60, clean_old_files).start()
    n = redis.zremrangebyscore("files", 0, time.time() - config["max_time"])
    print("Cleaned {} files".format(n))

clean_old_files()

@@ -23,16 +23,20 @@
 hreading
+, os
 %0A%0Afrom f
@@ -444,16 +444,125 @@
     %7D)%0A%0A
+def filepath(filename):%0A    return %22/files/%22 + filename%0A%0Adef hashkey(file_id):%0A    return %22file:%22 + file_id%0A%0A
 @app.rou
@@ -1405,26 +1405,16 @@
 ave(
-%22/
 file
-s/%7B%7D%22.form
+p
 at
+h
 (fil
@@ -1528,28 +1528,22 @@
     
-hash
 key = 
-%22file:%22 + 
+hashkey(
 str(
@@ -1550,16 +1550,17 @@
 file_id)
+)
 %0A    red
@@ -1563,28 +1563,24 @@
  redis.hset(
-hash
 key, %22filena
@@ -1605,28 +1605,24 @@
  redis.hset(
-hash
 key, %22upload
@@ -1672,28 +1672,24 @@
  redis.hset(
-hash
 key, %22time%22,
@@ -1709,20 +1709,16 @@
 is.hset(
-hash
 key, %22pa
@@ -1954,17 +1954,21 @@
 t()%0A    
-n
+files
  = redis
@@ -1974,11 +1974,8 @@
 s.zr
-emr
 ange
@@ -2043,34 +2043,250 @@
 nt(%22
-Cleaned %7B%7D files%22.format(n
+%7B%7D files have expired, removing...%22.format(len(files)))%0A%0A    for f in files:%0A        filename = redis.hget(hashkey(f), %22filename%22)%0A        redis.zrem(%22files%22, f)%0A        os.remove(filepath(filename))%0A        print(%22Removed %7B%7D%22.format(filename
 ))%0A%0A

Implement removing files