Spaces:
Sleeping
Sleeping
from src.routes.trailer import trailerBP | |
from src.routes.subtitledownload import subtitledownloadBP | |
from src.routes.streammap import streammapBP | |
from src.routes.signup import signupBP | |
from src.routes.restart import restartBP | |
from src.routes.redirectdownload import redirectdownloadBP | |
from src.routes.rebuild import rebuildBP | |
from src.routes.ping import pingBP | |
from src.routes.metadata import metadataBP | |
from src.routes.image import imageBP | |
from src.routes.environment import environmentBP | |
from src.routes.download import downloadBP | |
from src.routes.debug import debugBP | |
from src.routes.config import configBP | |
from src.routes.auth import authBP | |
import datetime | |
import io | |
import json | |
import logging | |
import os | |
import sys | |
import threading | |
import apscheduler.schedulers.background | |
import bs4 | |
import colorama | |
import flask | |
import flask_cors | |
import googleapiclient | |
import requests | |
import src.functions.config | |
import src.functions.credentials | |
import src.functions.metadata | |
import src.functions.tests | |
colorama.init() | |
print( | |
"====================================================\n\033[96m libDrive - v1.4.7\033[94m\n @eliasbenb\033[0m\n====================================================\n" | |
) | |
print("\033[32mREADING CONFIG...\033[0m") | |
if os.getenv("LIBDRIVE_CONFIG"): | |
config_str = os.getenv("LIBDRIVE_CONFIG") | |
with open("config.json", "w+") as w: | |
json.dump(obj=json.loads(config_str), fp=w, sort_keys=True, indent=4) | |
config = src.functions.config.readConfig() | |
print("DONE.\n") | |
print("\033[32mREADING METADATA...\033[0m") | |
metadata = src.functions.metadata.readMetadata(config) | |
if os.getenv("LIBDRIVE_CLOUD") and config.get("refresh_token"): | |
config, drive = src.functions.credentials.refreshCredentials(config) | |
params = { | |
"supportsAllDrives": True, | |
"includeItemsFromAllDrives": True, | |
"fields": "files(id,name)", | |
"q": "'%s' in parents and trashed = false and mimeType = 'application/json'" | |
% (os.getenv("LIBDRIVE_CLOUD")), | |
} | |
files = drive.files().list(**params).execute()["files"] | |
config_file = next((i for i in files if i["name"] == "config.json"), None) | |
metadata_file = next((i for i in files if i["name"] == "metadata.json"), None) | |
if config_file: | |
request = drive.files().get_media(fileId=config_file["id"]) | |
fh = io.BytesIO() | |
downloader = googleapiclient.http.MediaIoBaseDownload(fh, request) | |
done = False | |
while done is False: | |
status, done = downloader.next_chunk() | |
config = json.loads(fh.getvalue()) | |
config, drive = src.functions.credentials.refreshCredentials(config) | |
src.functions.config.updateConfig(config) | |
if metadata_file: | |
request = drive.files().get_media(fileId=metadata_file["id"]) | |
fh = io.BytesIO() | |
downloader = googleapiclient.http.MediaIoBaseDownload(fh, request) | |
done = False | |
while done is False: | |
status, done = downloader.next_chunk() | |
metadata = json.loads(fh.getvalue()) | |
with open("metadata.json", "w+") as w: | |
json.dump(metadata, w) | |
print("DONE.\n") | |
if not config.get("account_list"): | |
config["account_list"] = [] | |
if config.get("account_list") == [] and config.get("signup") == False: | |
config["auth"] = False | |
if not config.get("auth"): | |
config["auth"] = False | |
if not config.get("build_interval"): | |
config["build_interval"] = 360 | |
if not config.get("build_type"): | |
config["build_type"] = "hybrid" | |
if not config.get("category_list"): | |
config["category_list"] = [] | |
if not config.get("cloudflare"): | |
config["cloudflare"] = "" | |
if not config.get("prefer_mkv"): | |
config["prefer_mkv"] = False | |
if not config.get("prefer_mp4"): | |
config["prefer_mp4"] = True | |
if not config.get("service_accounts"): | |
config["service_accounts"] = [] | |
if not config.get("signup"): | |
config["signup"] = False | |
if not config.get("subtitles"): | |
config["subtitles"] = False | |
if not config.get("transcoded"): | |
config["transcoded"] = False | |
if not config.get("ui_config"): | |
config["ui_config"] = {} | |
with open("config.json", "w+") as w: | |
json.dump(obj=config, fp=w, sort_keys=True, indent=4) | |
print("\033[32mTESTING YOUR CONFIG...\033[0m") | |
# src.functions.tests.tmdb_test(config) | |
# src.functions.tests.category_list_test(config) | |
# src.functions.tests.account_list_test(config) | |
# src.functions.tests.cloudflare_test(config) | |
print("DONE.\n") | |
def threaded_metadata(): | |
for thread in threading.enumerate(): | |
if thread.name == "metadata_thread": | |
print("DONE.\n") | |
return ( | |
{ | |
"code": 500, | |
"content": None, | |
"message": "libDrive is already building metadata, please wait.", | |
"success": False, | |
}, | |
500, | |
) | |
config = src.functions.config.readConfig() | |
if len(config.get("category_list")) > 0: | |
metadata_thread = threading.Thread( | |
target=src.functions.metadata.writeMetadata, | |
args=(config,), | |
daemon=True, | |
name="metadata_thread", | |
) | |
metadata_thread.start() | |
else: | |
with open("./metadata.json", "w+") as w: | |
w.write(json.dumps([])) | |
return ( | |
{ | |
"code": 200, | |
"content": None, | |
"message": "libDrive is building your new metadata.", | |
"success": True, | |
}, | |
200, | |
) | |
def create_app(): | |
if os.path.exists("./build"): | |
LIBDRIVE_DEBUG = os.getenv("LIBDRIVE_DEBUG") | |
if LIBDRIVE_DEBUG: | |
if LIBDRIVE_DEBUG.lower() == "true": | |
LIBDRIVE_DEBUG = True | |
else: | |
LIBDRIVE_DEBUG = False | |
else: | |
LIBDRIVE_DEBUG = False | |
r = open("./build/index.html", "r") | |
soup = bs4.BeautifulSoup(r.read(), features="html.parser") | |
if config.get("ui_config", {}).get("icon"): | |
try: | |
soup.find("meta", {"id": "@ld-meta-og-image"})["content"] = config.get( | |
"ui_config", {} | |
).get("icon") | |
except: | |
pass | |
try: | |
soup.find("link", {"id": "@ld-link-icon"})["href"] = config.get( | |
"ui_config", {} | |
).get("icon") | |
except: | |
pass | |
else: | |
try: | |
soup.find("meta", {"id": "@ld-meta-og-image"})[ | |
"content" | |
] = "/images/icons/icon-512x512.png" | |
except: | |
pass | |
try: | |
soup.find("link", {"id": "@ld-link-icon"})["href"] = "/favicon.ico" | |
except: | |
pass | |
if config.get("ui_config", {}).get("title"): | |
try: | |
soup.find("meta", {"id": "@ld-meta-og-title"})["content"] = config.get( | |
"ui_config", {} | |
).get("title") | |
except: | |
pass | |
try: | |
soup.find("meta", {"id": "@ld-meta-og-site_name"})[ | |
"content" | |
] = config.get("ui_config", {}).get("title") | |
except: | |
pass | |
try: | |
soup.find("title", {"id": "@ld-title"}).string = config.get( | |
"ui_config", {} | |
).get("title") | |
except: | |
pass | |
else: | |
try: | |
soup.find("meta", {"id": "@ld-meta-og-title"})["content"] = "libDrive" | |
except: | |
pass | |
try: | |
soup.find("meta", {"id": "@ld-meta-og-site_name"})[ | |
"content" | |
] = "libDrive" | |
except: | |
pass | |
try: | |
soup.find("title", {"id": "@ld-title"}).string = "libDrive" | |
except: | |
pass | |
if ( | |
config.get("arcio") | |
and config.get("arcio") != "" | |
and LIBDRIVE_DEBUG == False | |
): | |
req = requests.get("https://arc.io/arc-sw.js") | |
with open("./build/arc-sw.js", "wb") as wb: | |
wb.write(req.content) | |
code = config.get("arcio") | |
if code == "dev": | |
code = "tUUqUjhw" | |
soup.find("script", {"id": "@ld-script-arcio"})[ | |
"src" | |
] = "//arc.io/widget.min.js#%s" % (code) | |
else: | |
if os.path.exists("./build/arc-sw.js"): | |
os.remove("./build/arc-sw.js") | |
soup.find("script", {"id": "@ld-script-arcio"})["src"] = "" | |
with open("./build/index.html", "w+") as w: | |
w.write(str(soup)) | |
r.close() | |
app = flask.Flask(__name__, static_folder="build") | |
build_interval = config.get("build_interval") | |
if not build_interval: | |
build_interval = 360 | |
if build_interval != 0: | |
print("\033[32mCREATING CRON JOB...\033[0m") | |
sched = apscheduler.schedulers.background.BackgroundScheduler(daemon=True) | |
sched.add_job( | |
threaded_metadata, | |
"interval", | |
minutes=build_interval, | |
) | |
sched.start() | |
print("DONE.\n") | |
config_categories = [d["id"] for d in config["category_list"]] | |
metadata_categories = [d["id"] for d in metadata] | |
if len(metadata) > 0 and sorted(config_categories) == sorted(metadata_categories): | |
if build_interval == 0: | |
return app | |
elif datetime.datetime.utcnow() <= datetime.datetime.strptime( | |
metadata[-1]["buildTime"], "%Y-%m-%d %H:%M:%S.%f" | |
) + datetime.timedelta(minutes=build_interval): | |
return app | |
else: | |
threaded_metadata() | |
else: | |
threaded_metadata() | |
return app | |
app = create_app() | |
flask_cors.CORS(app) | |
app.secret_key = config.get("secret_key") | |
app.register_blueprint(authBP) | |
app.register_blueprint(configBP) | |
app.register_blueprint(debugBP) | |
app.register_blueprint(downloadBP) | |
app.register_blueprint(environmentBP) | |
app.register_blueprint(imageBP) | |
app.register_blueprint(metadataBP) | |
app.register_blueprint(pingBP) | |
# app.register_blueprint(rebuildBP) | |
app.register_blueprint(redirectdownloadBP) | |
app.register_blueprint(restartBP) | |
app.register_blueprint(signupBP) | |
app.register_blueprint(streammapBP) | |
app.register_blueprint(subtitledownloadBP) | |
app.register_blueprint(trailerBP) | |
async def serve(path): | |
if (path != "") and os.path.exists("%s/%s" % (app.static_folder, path)): | |
return flask.send_from_directory(app.static_folder, path) | |
else: | |
return flask.send_from_directory(app.static_folder, "index.html") | |
if __name__ == "__main__": | |
print("\033[32mSERVING SERVER...\033[0m") | |
LIBDRIVE_DEBUG = os.getenv("LIBDRIVE_DEBUG") | |
if LIBDRIVE_DEBUG: | |
if LIBDRIVE_DEBUG.lower() == "true": | |
LIBDRIVE_DEBUG = True | |
else: | |
LIBDRIVE_DEBUG = False | |
else: | |
LIBDRIVE_DEBUG = False | |
print("DONE.\n") | |
app.run( | |
host="0.0.0.0", | |
port=7860, | |
threaded=True, | |
debug=LIBDRIVE_DEBUG, | |
) | |
else: | |
print("\033[32mINITIALIZING LOGGER...\033[0m") | |
if not os.path.exists("./logs"): | |
os.mkdir("./logs") | |
logs_path = os.path.abspath("./logs") | |
logs_max_files = 5 | |
def sorted_ls(path): | |
def mtime(f): return os.stat(os.path.join(path, f)).st_mtime | |
return list(sorted(os.listdir(path), key=mtime)) | |
del_list = sorted_ls(logs_path)[0: (len(sorted_ls(logs_path)) - logs_max_files)] | |
for del_file in del_list: | |
try: | |
os.remove(os.path.join(logs_path, del_file)) | |
except: | |
pass | |
logging.getLogger("googleapiclient").setLevel(logging.WARNING) | |
logging.getLogger("oauth2client").setLevel(logging.WARNING) | |
logging.getLogger("waitress").setLevel(logging.INFO) | |
logging.basicConfig( | |
filename="./logs/%s.log" | |
% (datetime.datetime.utcnow().strftime("%Y%m%d-%H%M%S")), | |
level=logging.INFO, | |
) | |
console_logger = logging.getLogger() | |
console_logger.setLevel(logging.INFO) | |
console_handler = logging.StreamHandler(sys.stdout) | |
console_handler.setLevel(logging.INFO) | |
console_logger.addHandler(console_handler) | |
print("DONE.\n") | |