164 lines
4.3 KiB
Python
164 lines
4.3 KiB
Python
# -*- coding: utf-8 -*-
|
|
|
|
import os, sys, time
|
|
import json
|
|
from datetime import datetime
|
|
from flask import (
|
|
Flask,
|
|
render_template,
|
|
jsonify,
|
|
current_app,
|
|
Response,
|
|
redirect,
|
|
url_for,
|
|
request,
|
|
g,
|
|
session,
|
|
send_file,
|
|
send_from_directory,
|
|
abort,
|
|
)
|
|
from werkzeug.utils import secure_filename
|
|
from revprox import ReverseProxied
|
|
from utils import (
|
|
random_token,
|
|
db_store_file,
|
|
file_details,
|
|
file_list,
|
|
db_add_download,
|
|
db_get_file,
|
|
db_delete_file,
|
|
)
|
|
|
|
__MINI_FLEES_VERSION__ = "20230818.0"
|
|
app = Flask(__name__)
|
|
app.config.from_object(__name__)
|
|
app.config.from_prefixed_env()
|
|
app.debug = True
|
|
app.secret_key = app.config["APP_SECRET_KEY"]
|
|
app.wsgi_app = ReverseProxied(app.wsgi_app)
|
|
|
|
|
|
@app.route("/")
|
|
def index():
|
|
return "", 200
|
|
|
|
|
|
@app.route("/upload", methods=["POST"])
|
|
def upload():
|
|
if request.method == "POST":
|
|
file = request.files.get("file")
|
|
name = request.headers.get("Name", None)
|
|
if name is None:
|
|
return "Name required", 500
|
|
secret = request.headers.get("Secret", "")
|
|
if secret != app.config["ACCESS_TOKEN"]:
|
|
return "Error", 401
|
|
max_dl = request.headers.get("Max-Downloads", app.config["DEFAULT_MAX_DL"])
|
|
expires = int(time.time()) + int(app.config["DEFAULT_EXPIRE"])
|
|
if "Expires-days" in request.headers:
|
|
expires = int(time.time()) + 24 * 3600 * int(
|
|
request.headers.get("Expires-days")
|
|
)
|
|
if "Expires-hours" in request.headers:
|
|
expires = int(time.time()) + 3600 * int(
|
|
request.headers.get("Expires-hours")
|
|
)
|
|
|
|
if file:
|
|
safe_filename = secure_filename(name)
|
|
token = random_token()
|
|
folder = os.path.join(app.config["DATAFOLDER"], token)
|
|
os.mkdir(folder)
|
|
filename = os.path.join(folder, safe_filename)
|
|
file.save(filename)
|
|
db_store_file(token, safe_filename, expires, max_dl)
|
|
download_url = f"{app.config['PUBLIC_URL']}/dl/{token}/{safe_filename}"
|
|
return "File uploaded\n%s\n" % (download_url,), 200
|
|
else:
|
|
return "Use the 'file' variable to upload\n", 400
|
|
|
|
|
|
@app.route("/details/<token>/<name>", methods=["GET"])
|
|
def details(token, name):
|
|
secret = request.headers.get("Secret", "")
|
|
if secret != app.config["ACCESS_TOKEN"]:
|
|
return "Error", 401
|
|
details = file_details(token, name)
|
|
return jsonify(details), 200
|
|
|
|
|
|
@app.route("/delete/<token>/<name>", methods=["GET"])
|
|
def delete_file(name, token):
|
|
secret = request.headers.get("Secret", "")
|
|
if secret != app.config["ACCESS_TOKEN"]:
|
|
return "Error", 401
|
|
try:
|
|
os.remove(os.path.join(os.getenv("DATAFOLDER"), token, name))
|
|
except Exception:
|
|
pass
|
|
db_delete_file(token, name)
|
|
return "OK", 200
|
|
|
|
|
|
@app.route("/ls", methods=["GET"])
|
|
def ls():
|
|
secret = request.headers.get("Secret", "")
|
|
if secret != app.config["ACCESS_TOKEN"]:
|
|
return "Error", 401
|
|
return "\n".join(file_list()), 200
|
|
|
|
|
|
|
|
|
|
@app.route("/dl/<token>/<name>", methods=["GET"])
|
|
def download(name, token):
|
|
return download_file(token, name)
|
|
|
|
|
|
@app.route("/script/client", methods=["GET"])
|
|
def script_client():
|
|
return render_template(
|
|
"client.py", name=name, token=token, rooturl=request.url_root
|
|
)
|
|
|
|
|
|
@app.route("/script/flip", methods=["GET"])
|
|
def script_flip():
|
|
return render_template(
|
|
"flip",
|
|
name=name,
|
|
token=token,
|
|
rooturl=request.url_root,
|
|
version=__FLEES_VERSION__,
|
|
)
|
|
|
|
|
|
def download_file(token, name):
|
|
full_path = os.path.join(os.getenv("FLASK_DATAFOLDER"), token, name)
|
|
if not os.path.exists(full_path):
|
|
return "Error", 404
|
|
db_stat = db_get_file(token, name)
|
|
if db_stat:
|
|
added, expires, downloads, max_dl = db_stat
|
|
else:
|
|
return "Error", 404
|
|
if downloads >= max_dl:
|
|
return "Expired", 401
|
|
if expires < time.time():
|
|
return "Expired", 401
|
|
db_add_download(token, name)
|
|
return send_from_directory(
|
|
directory=os.path.join(os.getenv("FLASK_DATAFOLDER"), token), path=name
|
|
)
|
|
|
|
|
|
def print_debug(s):
|
|
if app.config["DEBUG"]:
|
|
sys.stderr.write(str(s) + "\n")
|
|
sys.stderr.flush()
|
|
|
|
|
|
if __name__ == "__main__":
|
|
app.run(debug=True)
|