docstrings
This commit is contained in:
parent
259b128af0
commit
8b9c6da2b7
226
app.py
226
app.py
@ -1,19 +1,24 @@
|
|||||||
# app.py
|
# app.py
|
||||||
from flask import Flask, render_template, request, redirect, url_for, session, send_file, jsonify
|
from flask import (Flask, render_template, request, redirect, url_for, session,
|
||||||
|
send_file, jsonify, send_from_directory, Response)
|
||||||
from flask_caching import Cache
|
from flask_caching import Cache
|
||||||
import requests.auth
|
import requests.auth
|
||||||
import os
|
import os
|
||||||
from lib.datetime import filter_accounts_next_30_days, filter_accounts_expired
|
|
||||||
from lib.reqs import get_urls, get_user_accounts, add_user_account, delete_user_account, get_stream_names
|
|
||||||
from flask import send_from_directory
|
|
||||||
import requests
|
|
||||||
import base64
|
import base64
|
||||||
from flask import Flask
|
from typing import Dict, Any, Tuple, Union
|
||||||
from config import DevelopmentConfig, ProductionConfig
|
|
||||||
from paddleocr import PaddleOCR
|
|
||||||
from PIL import Image
|
|
||||||
import numpy as np
|
|
||||||
|
|
||||||
|
from lib.datetime import filter_accounts_next_30_days, filter_accounts_expired
|
||||||
|
from lib.reqs import (get_urls, get_user_accounts, add_user_account,
|
||||||
|
delete_user_account, get_stream_names)
|
||||||
|
from config import DevelopmentConfig, ProductionConfig
|
||||||
|
|
||||||
|
try:
|
||||||
|
from paddleocr import PaddleOCR
|
||||||
|
from PIL import Image
|
||||||
|
import numpy as np
|
||||||
|
OCR_AVAILABLE = True
|
||||||
|
except ImportError:
|
||||||
|
OCR_AVAILABLE = False
|
||||||
|
|
||||||
os.environ["OMP_NUM_THREADS"] = "1"
|
os.environ["OMP_NUM_THREADS"] = "1"
|
||||||
os.environ["MKL_NUM_THREADS"] = "1"
|
os.environ["MKL_NUM_THREADS"] = "1"
|
||||||
@ -24,18 +29,26 @@ if os.environ.get("FLASK_ENV") == "production":
|
|||||||
app.config.from_object(ProductionConfig)
|
app.config.from_object(ProductionConfig)
|
||||||
else:
|
else:
|
||||||
app.config.from_object(DevelopmentConfig)
|
app.config.from_object(DevelopmentConfig)
|
||||||
|
|
||||||
cache = Cache(app, config={"CACHE_TYPE": "SimpleCache"})
|
cache = Cache(app, config={"CACHE_TYPE": "SimpleCache"})
|
||||||
|
|
||||||
if app.config.get("OCR_ENABLED"):
|
if app.config.get("OCR_ENABLED") and OCR_AVAILABLE:
|
||||||
ocr = PaddleOCR(use_angle_cls=True, lang='en') # Adjust language if needed
|
ocr = PaddleOCR(use_angle_cls=True, lang='en')
|
||||||
|
else:
|
||||||
|
app.config["OCR_ENABLED"] = False
|
||||||
|
|
||||||
app.config["SESSION_COOKIE_SECURE"] = not app.config["DEBUG"]
|
app.config["SESSION_COOKIE_SECURE"] = not app.config["DEBUG"]
|
||||||
app.config['SESSION_COOKIE_HTTPONLY'] = True # Prevent JavaScript access
|
app.config['SESSION_COOKIE_HTTPONLY'] = True
|
||||||
app.config['SESSION_COOKIE_SAMESITE'] = 'Lax' # Adjust for cross-site requests
|
app.config['SESSION_COOKIE_SAMESITE'] = 'Lax'
|
||||||
app.config['PERMANENT_SESSION_LIFETIME'] = 60 * 60 * 24 * 365 # 1 year in seconds
|
app.config['PERMANENT_SESSION_LIFETIME'] = 60 * 60 * 24 * 365 # 1 year
|
||||||
cache.clear() # Clears all cache entries
|
cache.clear()
|
||||||
|
|
||||||
def get_version():
|
def get_version() -> str:
|
||||||
|
"""Retrieves the application version from the VERSION file.
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
The version string, or 'dev' if the file is not found.
|
||||||
|
"""
|
||||||
try:
|
try:
|
||||||
with open('VERSION', 'r') as f:
|
with open('VERSION', 'r') as f:
|
||||||
return f.read().strip()
|
return f.read().strip()
|
||||||
@ -43,109 +56,102 @@ def get_version():
|
|||||||
return 'dev'
|
return 'dev'
|
||||||
|
|
||||||
@app.context_processor
|
@app.context_processor
|
||||||
def inject_version():
|
def inject_version() -> Dict[str, str]:
|
||||||
|
"""Injects the version into all templates."""
|
||||||
return dict(version=get_version())
|
return dict(version=get_version())
|
||||||
|
|
||||||
@app.before_request
|
@app.before_request
|
||||||
def make_session_permanent():
|
def make_session_permanent() -> None:
|
||||||
|
"""Makes the user session permanent."""
|
||||||
session.permanent = True
|
session.permanent = True
|
||||||
|
|
||||||
@app.route('/site.webmanifest')
|
@app.route('/site.webmanifest')
|
||||||
def serve_manifest():
|
def serve_manifest() -> Response:
|
||||||
return send_from_directory(os.path.join(app.root_path, 'static'), 'site.webmanifest', mimetype='application/manifest+json')
|
"""Serves the site manifest file."""
|
||||||
|
return send_from_directory(
|
||||||
|
os.path.join(app.root_path, 'static'),
|
||||||
|
'site.webmanifest',
|
||||||
|
mimetype='application/manifest+json'
|
||||||
|
)
|
||||||
|
|
||||||
@app.route("/favicon.ico")
|
@app.route("/favicon.ico")
|
||||||
def favicon():
|
def favicon() -> Response:
|
||||||
|
"""Serves the favicon."""
|
||||||
return send_from_directory(
|
return send_from_directory(
|
||||||
os.path.join(app.root_path, "static"),
|
os.path.join(app.root_path, "static"),
|
||||||
"favicon.ico",
|
"favicon.ico",
|
||||||
mimetype="image/vnd.microsoft.icon",
|
mimetype="image/vnd.microsoft.icon",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@app.route("/")
|
@app.route("/")
|
||||||
def index():
|
def index() -> Union[Response, str]:
|
||||||
# If the user is logged in, redirect to a protected page like /accounts
|
"""Renders the index page or redirects to home if logged in."""
|
||||||
if session.get("logged_in"):
|
if session.get("logged_in"):
|
||||||
return redirect(url_for("home"))
|
return redirect(url_for("home"))
|
||||||
return render_template("index.html")
|
return render_template("index.html")
|
||||||
|
|
||||||
|
|
||||||
@app.route("/home")
|
@app.route("/home")
|
||||||
@cache.cached(timeout=60) # cache for 120 seconds
|
@cache.cached(timeout=60)
|
||||||
def home():
|
def home() -> str:
|
||||||
|
"""Renders the home page with account statistics."""
|
||||||
if session.get("logged_in"):
|
if session.get("logged_in"):
|
||||||
base_url = app.config["BASE_URL"] # Access base_url from the config
|
base_url = app.config["BASE_URL"]
|
||||||
all_accounts = get_user_accounts(base_url, session["auth_credentials"])
|
all_accounts = get_user_accounts(base_url, session["auth_credentials"])
|
||||||
count = len(all_accounts)
|
|
||||||
current_month_accounts = filter_accounts_next_30_days(all_accounts)
|
|
||||||
expired_accounts = filter_accounts_expired(all_accounts)
|
|
||||||
return render_template(
|
return render_template(
|
||||||
"home.html",
|
"home.html",
|
||||||
username=session["username"],
|
username=session["username"],
|
||||||
accounts=count,
|
accounts=len(all_accounts),
|
||||||
current_month_accounts=current_month_accounts,
|
current_month_accounts=filter_accounts_next_30_days(all_accounts),
|
||||||
expired_accounts=expired_accounts,
|
expired_accounts=filter_accounts_expired(all_accounts),
|
||||||
ocr_enabled=app.config.get("OCR_ENABLED"),
|
ocr_enabled=app.config.get("OCR_ENABLED"),
|
||||||
)
|
)
|
||||||
return render_template("index.html")
|
return render_template("index.html")
|
||||||
|
|
||||||
|
|
||||||
@app.route("/login", methods=["POST"])
|
@app.route("/login", methods=["POST"])
|
||||||
def login():
|
def login() -> Union[Response, str]:
|
||||||
|
"""Handles user login."""
|
||||||
username = request.form["username"]
|
username = request.form["username"]
|
||||||
password = request.form["password"]
|
password = request.form["password"]
|
||||||
|
|
||||||
# Encode the username and password in Base64
|
|
||||||
credentials = f"{username}:{password}"
|
credentials = f"{username}:{password}"
|
||||||
encoded_credentials = base64.b64encode(credentials.encode()).decode()
|
encoded_credentials = base64.b64encode(credentials.encode()).decode()
|
||||||
|
base_url = app.config["BASE_URL"]
|
||||||
|
login_url = f"{base_url}/Login"
|
||||||
|
|
||||||
base_url = app.config["BASE_URL"] # Access base_url from the config
|
try:
|
||||||
login_url = f"{base_url}/Login" # Construct the full URL
|
response = requests.get(
|
||||||
|
login_url, auth=requests.auth.HTTPBasicAuth(username, password)
|
||||||
# Send GET request to the external login API with Basic Auth
|
)
|
||||||
response = requests.get(
|
response.raise_for_status()
|
||||||
login_url, auth=requests.auth.HTTPBasicAuth(username, password)
|
if response.json().get("auth") == "Success":
|
||||||
)
|
session["logged_in"] = True
|
||||||
|
session["username"] = username
|
||||||
# Check if login was successful
|
session["auth_credentials"] = encoded_credentials
|
||||||
if response.status_code == 200 and response.json().get("auth") == "Success":
|
return redirect(url_for("home"))
|
||||||
# Set session variable to indicate the user is logged in
|
except requests.exceptions.RequestException:
|
||||||
session["logged_in"] = True
|
pass # Fall through to error
|
||||||
session["username"] = username
|
|
||||||
session["auth_credentials"] = encoded_credentials
|
|
||||||
return redirect(url_for("home")) # Redirect to the Accounts page
|
|
||||||
else:
|
|
||||||
# Show error on the login page
|
|
||||||
error = "Invalid username or password. Please try again."
|
|
||||||
return render_template("index.html", error=error)
|
|
||||||
|
|
||||||
|
error = "Invalid username or password. Please try again."
|
||||||
|
return render_template("index.html", error=error)
|
||||||
|
|
||||||
@app.route("/urls", methods=["GET"])
|
@app.route("/urls", methods=["GET"])
|
||||||
@cache.cached(timeout=300) # cache for 5 minutes
|
@cache.cached(timeout=300)
|
||||||
def urls():
|
def urls() -> Union[Response, str]:
|
||||||
# Check if the user is logged in
|
"""Renders the URLs page."""
|
||||||
if not session.get("logged_in"):
|
if not session.get("logged_in"):
|
||||||
return redirect(url_for("home"))
|
return redirect(url_for("home"))
|
||||||
# Placeholder content for Accounts page
|
base_url = app.config["BASE_URL"]
|
||||||
base_url = app.config["BASE_URL"] # Access base_url from the config
|
|
||||||
return render_template(
|
return render_template(
|
||||||
"urls.html", urls=get_urls(base_url, session["auth_credentials"])
|
"urls.html", urls=get_urls(base_url, session["auth_credentials"])
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@app.route("/accounts", methods=["GET"])
|
@app.route("/accounts", methods=["GET"])
|
||||||
def user_accounts():
|
def user_accounts() -> Union[Response, str]:
|
||||||
# Check if the user is logged in
|
"""Renders the user accounts page."""
|
||||||
if not session.get("logged_in"):
|
if not session.get("logged_in"):
|
||||||
return redirect(url_for("home"))
|
return redirect(url_for("home"))
|
||||||
# Placeholder content for Accounts page
|
base_url = app.config["BASE_URL"]
|
||||||
base_url = app.config["BASE_URL"] # Access base_url from the config
|
|
||||||
user_accounts_data = get_user_accounts(base_url, session["auth_credentials"])
|
user_accounts_data = get_user_accounts(base_url, session["auth_credentials"])
|
||||||
|
|
||||||
# Clear the cache for 'user_accounts' view specifically
|
|
||||||
cache.delete_memoized(user_accounts)
|
cache.delete_memoized(user_accounts)
|
||||||
|
|
||||||
return render_template(
|
return render_template(
|
||||||
"user_accounts.html",
|
"user_accounts.html",
|
||||||
username=session["username"],
|
username=session["username"],
|
||||||
@ -153,9 +159,9 @@ def user_accounts():
|
|||||||
auth=session["auth_credentials"],
|
auth=session["auth_credentials"],
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@app.route("/accounts/add", methods=["GET", "POST"])
|
@app.route("/accounts/add", methods=["GET", "POST"])
|
||||||
def add_account():
|
def add_account() -> Union[Response, str]:
|
||||||
|
"""Handles adding a new user account."""
|
||||||
base_url = app.config["BASE_URL"]
|
base_url = app.config["BASE_URL"]
|
||||||
shared_text = request.args.get('shared_text')
|
shared_text = request.args.get('shared_text')
|
||||||
|
|
||||||
@ -163,72 +169,84 @@ def add_account():
|
|||||||
username = request.form["username"]
|
username = request.form["username"]
|
||||||
password = request.form["password"]
|
password = request.form["password"]
|
||||||
stream = request.form["stream"]
|
stream = request.form["stream"]
|
||||||
|
|
||||||
if add_user_account(
|
if add_user_account(
|
||||||
base_url, session["auth_credentials"], username, password, stream
|
base_url, session["auth_credentials"], username, password, stream
|
||||||
):
|
):
|
||||||
cache.clear()
|
cache.clear()
|
||||||
return redirect(url_for("user_accounts"))
|
return redirect(url_for("user_accounts"))
|
||||||
return render_template("add_account.html", ocr_enabled=app.config.get("OCR_ENABLED"), text_input_enabled=app.config.get("TEXT_INPUT_ENABLED"), shared_text=shared_text)
|
|
||||||
|
|
||||||
return render_template("add_account.html", ocr_enabled=app.config.get("OCR_ENABLED"), text_input_enabled=app.config.get("TEXT_INPUT_ENABLED"), shared_text=shared_text)
|
|
||||||
|
|
||||||
|
return render_template(
|
||||||
|
"add_account.html",
|
||||||
|
ocr_enabled=app.config.get("OCR_ENABLED"),
|
||||||
|
text_input_enabled=app.config.get("TEXT_INPUT_ENABLED"),
|
||||||
|
shared_text=shared_text
|
||||||
|
)
|
||||||
|
|
||||||
@app.route("/accounts/delete", methods=["POST"])
|
@app.route("/accounts/delete", methods=["POST"])
|
||||||
def delete_account():
|
def delete_account() -> Response:
|
||||||
|
"""Handles deleting a user account."""
|
||||||
stream = request.form.get("stream")
|
stream = request.form.get("stream")
|
||||||
username = request.form.get("username")
|
username = request.form.get("username")
|
||||||
base_url = app.config["BASE_URL"]
|
base_url = app.config["BASE_URL"]
|
||||||
|
delete_user_account(base_url, session["auth_credentials"], stream, username)
|
||||||
if delete_user_account(base_url, session["auth_credentials"], stream, username):
|
|
||||||
return redirect(url_for("user_accounts"))
|
|
||||||
return redirect(url_for("user_accounts"))
|
return redirect(url_for("user_accounts"))
|
||||||
|
|
||||||
|
|
||||||
@app.route("/validateAccount", methods=["POST"])
|
@app.route("/validateAccount", methods=["POST"])
|
||||||
def validate_account():
|
def validate_account() -> Tuple[Response, int]:
|
||||||
|
"""Forwards account validation requests to the backend."""
|
||||||
base_url = app.config["BASE_URL"]
|
base_url = app.config["BASE_URL"]
|
||||||
validate_url = f"{base_url}/validateAccount"
|
validate_url = f"{base_url}/validateAccount"
|
||||||
|
|
||||||
# Forward the request to the backend API
|
|
||||||
credentials = base64.b64decode(session["auth_credentials"]).decode()
|
credentials = base64.b64decode(session["auth_credentials"]).decode()
|
||||||
username, password = credentials.split(":", 1)
|
username, password = credentials.split(":", 1)
|
||||||
response = requests.post(
|
|
||||||
validate_url,
|
|
||||||
auth=requests.auth.HTTPBasicAuth(username, password),
|
|
||||||
json=request.get_json()
|
|
||||||
)
|
|
||||||
|
|
||||||
return jsonify(response.json()), response.status_code
|
|
||||||
|
|
||||||
|
try:
|
||||||
|
response = requests.post(
|
||||||
|
validate_url,
|
||||||
|
auth=requests.auth.HTTPBasicAuth(username, password),
|
||||||
|
json=request.get_json()
|
||||||
|
)
|
||||||
|
response.raise_for_status()
|
||||||
|
return jsonify(response.json()), response.status_code
|
||||||
|
except requests.exceptions.RequestException as e:
|
||||||
|
return jsonify({"error": str(e)}), 500
|
||||||
|
|
||||||
@app.route("/get_stream_names", methods=["GET"])
|
@app.route("/get_stream_names", methods=["GET"])
|
||||||
def stream_names():
|
def stream_names() -> Union[Response, str]:
|
||||||
|
"""Fetches and returns stream names as JSON."""
|
||||||
if not session.get("logged_in"):
|
if not session.get("logged_in"):
|
||||||
return redirect(url_for("home"))
|
return redirect(url_for("home"))
|
||||||
base_url = app.config["BASE_URL"]
|
base_url = app.config["BASE_URL"]
|
||||||
stream_names = get_stream_names(base_url, session["auth_credentials"])
|
return jsonify(get_stream_names(base_url, session["auth_credentials"]))
|
||||||
return jsonify(stream_names)
|
|
||||||
|
|
||||||
|
|
||||||
if app.config.get("OCR_ENABLED"):
|
if app.config.get("OCR_ENABLED"):
|
||||||
@app.route('/OCRupload', methods=['POST'])
|
@app.route('/OCRupload', methods=['POST'])
|
||||||
def OCRupload():
|
def ocr_upload() -> Union[Response, str, Tuple[Response, int]]:
|
||||||
|
"""Handles image uploads for OCR processing."""
|
||||||
if 'image' not in request.files:
|
if 'image' not in request.files:
|
||||||
return jsonify({"error": "No image file found"}), 400
|
return jsonify({"error": "No image file found"}), 400
|
||||||
# Get the uploaded file
|
|
||||||
file = request.files['image']
|
file = request.files['image']
|
||||||
try:
|
try:
|
||||||
image = Image.open(file.stream)
|
image = Image.open(file.stream)
|
||||||
image_np = np.array(image)
|
image_np = np.array(image)
|
||||||
result = ocr.ocr(image_np)
|
result = ocr.ocr(image_np)
|
||||||
# Extract text
|
extracted_text = [line[1][0] for line in result[0]]
|
||||||
extracted_text = []
|
# Basic validation
|
||||||
for line in result[0]:
|
if len(extracted_text) >= 4:
|
||||||
extracted_text.append(line[1][0])
|
return render_template(
|
||||||
return render_template("add_account.html", username=extracted_text[2], password=extracted_text[3], ocr_enabled=app.config.get("OCR_ENABLED"), text_input_enabled=app.config.get("TEXT_INPUT_ENABLED"))
|
"add_account.html",
|
||||||
|
username=extracted_text[2],
|
||||||
|
password=extracted_text[3],
|
||||||
|
ocr_enabled=True,
|
||||||
|
text_input_enabled=app.config.get("TEXT_INPUT_ENABLED")
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
return jsonify({"error": "Could not extract required fields from image"}), 400
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
return jsonify({"error": str(e)}), 500
|
return jsonify({"error": str(e)}), 500
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
app.run(debug=app.config["DEBUG"], host=app.config["HOST"], port=app.config["PORT"])
|
app.run(
|
||||||
|
debug=app.config["DEBUG"],
|
||||||
|
host=app.config["HOST"],
|
||||||
|
port=app.config["PORT"]
|
||||||
|
)
|
||||||
|
@ -1,13 +1,16 @@
|
|||||||
from datetime import datetime, timedelta
|
from datetime import datetime, timedelta
|
||||||
from typing import List, Dict
|
from typing import List, Dict, Any
|
||||||
|
|
||||||
|
def filter_accounts_next_30_days(accounts: List[Dict[str, Any]]) -> List[Dict[str, Any]]:
|
||||||
|
"""Filters accounts expiring within the next 30 days.
|
||||||
|
|
||||||
def filter_accounts_next_30_days(accounts: List[Dict[str, int]]) -> List[Dict[str, int]]:
|
|
||||||
"""Filter accounts whose expiry date falls within the next 30 days.
|
|
||||||
Args:
|
Args:
|
||||||
accounts (List[Dict[str, int]]): A list of account dictionaries, each containing
|
accounts: A list of account dictionaries, each with an 'expiaryDate'
|
||||||
an 'expiaryDate' key with an epoch timestamp as its value.
|
(epoch timestamp).
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
List[Dict[str, int]]: A list of accounts expiring within the next 30 days.
|
A list of accounts expiring within the next 30 days, with added
|
||||||
|
'expiaryDate_rendered' and 'days_to_expiry' keys.
|
||||||
"""
|
"""
|
||||||
now = datetime.now()
|
now = datetime.now()
|
||||||
thirty_days_later = now + timedelta(days=30)
|
thirty_days_later = now + timedelta(days=30)
|
||||||
@ -26,18 +29,18 @@ def filter_accounts_next_30_days(accounts: List[Dict[str, int]]) -> List[Dict[st
|
|||||||
result.append(account)
|
result.append(account)
|
||||||
return result
|
return result
|
||||||
|
|
||||||
def filter_accounts_expired(accounts: List[Dict[str, int]]) -> List[Dict[str, int]]:
|
def filter_accounts_expired(accounts: List[Dict[str, Any]]) -> List[Dict[str, Any]]:
|
||||||
"""Filter accounts whose expiry date has passed.
|
"""Filters accounts that have already expired.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
accounts (List[Dict[str, int]]): A list of account dictionaries, each containing
|
accounts: A list of account dictionaries, each with an 'expiaryDate'
|
||||||
an 'expiaryDate' key with an epoch timestamp as its value.
|
(epoch timestamp).
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
List[Dict[str, int]]: A list of accounts that have expired.
|
A list of expired accounts with an added 'expiaryDate_rendered' key.
|
||||||
"""
|
"""
|
||||||
# Get the current epoch timestamp
|
|
||||||
current_timestamp = int(datetime.now().timestamp())
|
current_timestamp = int(datetime.now().timestamp())
|
||||||
|
|
||||||
# Filter accounts where the current date is greater than the expiryDate
|
|
||||||
expired_accounts = []
|
expired_accounts = []
|
||||||
for account in accounts:
|
for account in accounts:
|
||||||
if account['expiaryDate'] < current_timestamp:
|
if account['expiaryDate'] < current_timestamp:
|
||||||
|
89
lib/reqs.py
89
lib/reqs.py
@ -5,106 +5,101 @@ from typing import List, Dict, Any
|
|||||||
|
|
||||||
|
|
||||||
def get_urls(base_url: str, auth: str) -> List[Dict[str, Any]]:
|
def get_urls(base_url: str, auth: str) -> List[Dict[str, Any]]:
|
||||||
"""Retrieve user account streams from the specified base URL.
|
"""Retrieves user account streams from the API.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
base_url (str): The base URL of the API.
|
base_url: The base URL of the API.
|
||||||
auth (str): The authorization token for accessing the API.
|
auth: The authorization token.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
List[Dict[str, Any]]: A list of user account streams.
|
A list of user account streams.
|
||||||
"""
|
"""
|
||||||
url = f"{base_url}/getUserAccounts/streams"
|
url = f"{base_url}/getUserAccounts/streams"
|
||||||
payload = {}
|
|
||||||
headers = {"Authorization": f"Basic {auth}"}
|
headers = {"Authorization": f"Basic {auth}"}
|
||||||
|
response = requests.get(url, headers=headers)
|
||||||
response = requests.request("GET", url, headers=headers, data=payload)
|
response.raise_for_status()
|
||||||
return json.loads(response.text)
|
return response.json()
|
||||||
|
|
||||||
|
|
||||||
def get_user_accounts(base_url: str, auth: str) -> List[Dict[str, Any]]:
|
def get_user_accounts(base_url: str, auth: str) -> List[Dict[str, Any]]:
|
||||||
"""Retrieve user accounts from the specified base URL.
|
"""Retrieves user accounts from the API.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
base_url (str): The base URL of the API.
|
base_url: The base URL of the API.
|
||||||
auth (str): The authorization token for accessing the API.
|
auth: The authorization token.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
List[Dict[str, Any]]: A list of user accounts with their expiration dates rendered.
|
A list of user accounts with 'expiaryDate_rendered' added.
|
||||||
"""
|
"""
|
||||||
url = f"{base_url}/getUserAccounts"
|
url = f"{base_url}/getUserAccounts"
|
||||||
payload = {}
|
|
||||||
headers = {"Authorization": f"Basic {auth}"}
|
headers = {"Authorization": f"Basic {auth}"}
|
||||||
|
response = requests.get(url, headers=headers)
|
||||||
|
response.raise_for_status()
|
||||||
|
accounts = response.json()
|
||||||
|
|
||||||
response = requests.request("GET", url, headers=headers, data=payload)
|
for account in accounts:
|
||||||
res_json = json.loads(response.text)
|
|
||||||
|
|
||||||
for account in res_json:
|
|
||||||
account["expiaryDate_rendered"] = datetime.utcfromtimestamp(
|
account["expiaryDate_rendered"] = datetime.utcfromtimestamp(
|
||||||
account["expiaryDate"]
|
account["expiaryDate"]
|
||||||
).strftime("%d/%m/%Y")
|
).strftime("%d/%m/%Y")
|
||||||
|
|
||||||
return res_json
|
return accounts
|
||||||
|
|
||||||
|
|
||||||
def delete_user_account(base_url: str, auth: str, stream: str, username: str) -> bool:
|
def delete_user_account(base_url: str, auth: str, stream: str, username: str) -> bool:
|
||||||
"""Delete a user account from the specified base URL.
|
"""Deletes a user account via the API.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
base_url (str): The base URL of the API.
|
base_url: The base URL of the API.
|
||||||
auth (str): The authorization token for accessing the API.
|
auth: The authorization token.
|
||||||
stream (str): The name of the stream associated with the user account.
|
stream: The stream associated with the account.
|
||||||
username (str): The username of the account to delete.
|
username: The username of the account to delete.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
bool: True if the account was deleted successfully, False otherwise.
|
True if the account was deleted successfully, False otherwise.
|
||||||
"""
|
"""
|
||||||
url = f"{base_url}/deleteAccount"
|
url = f"{base_url}/deleteAccount"
|
||||||
payload = {"stream": stream, "user": username}
|
payload = {"stream": stream, "user": username}
|
||||||
headers = {"Authorization": f"Basic {auth}"}
|
headers = {"Authorization": f"Basic {auth}"}
|
||||||
|
response = requests.post(url, headers=headers, data=payload)
|
||||||
response = requests.request("POST", url, headers=headers, data=payload)
|
response.raise_for_status()
|
||||||
return "Deleted" in response.text
|
return "Deleted" in response.text
|
||||||
|
|
||||||
|
|
||||||
def add_user_account(base_url: str, auth: str, username: str, password: str, stream: str) -> bool:
|
def add_user_account(base_url: str, auth: str, username: str, password: str, stream: str) -> bool:
|
||||||
"""Add a user account to the specified base URL.
|
"""Adds a user account via the API.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
base_url (str): The base URL of the API.
|
base_url: The base URL of the API.
|
||||||
auth (str): The authorization token for accessing the API.
|
auth: The authorization token.
|
||||||
username (str): The username of the account to add.
|
username: The username of the new account.
|
||||||
password (str): The password of the account to add.
|
password: The password for the new account.
|
||||||
stream (str): The name of the stream associated with the user account.
|
stream: The stream to associate with the new account.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
bool: True if the account was added successfully, False otherwise.
|
True if the account was added successfully, False otherwise.
|
||||||
"""
|
"""
|
||||||
url = f"{base_url}/addAccount"
|
url = f"{base_url}/addAccount"
|
||||||
payload = {"username": username, "password": password, "stream": stream}
|
payload = {"username": username, "password": password, "stream": stream}
|
||||||
headers = {"Authorization": f"Basic {auth}"}
|
headers = {"Authorization": f"Basic {auth}"}
|
||||||
|
response = requests.post(url, headers=headers, data=payload)
|
||||||
response = requests.request("POST", url, headers=headers, data=payload)
|
|
||||||
return response.status_code == 200
|
return response.status_code == 200
|
||||||
|
|
||||||
|
|
||||||
def get_stream_names(base_url: str, auth: str) -> List[str]:
|
def get_stream_names(base_url: str, auth: str) -> List[str]:
|
||||||
"""Get a list of stream names from the API.
|
"""Retrieves a list of stream names from the API.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
base_url (str): The base URL of the API.
|
base_url: The base URL of the API.
|
||||||
auth (str): The authorization token.
|
auth: The authorization token.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
List[str]: A list of stream names.
|
A list of stream names, or an empty list if an error occurs.
|
||||||
"""
|
"""
|
||||||
url = f"{base_url}/getStreamNames"
|
url = f"{base_url}/getStreamNames"
|
||||||
payload = {}
|
|
||||||
headers = {"Authorization": f"Basic {auth}"}
|
headers = {"Authorization": f"Basic {auth}"}
|
||||||
response = requests.request("GET", url, headers=headers, data=payload)
|
try:
|
||||||
if response.status_code == 200 and response.text:
|
response = requests.get(url, headers=headers)
|
||||||
try:
|
response.raise_for_status()
|
||||||
return json.loads(response.text)
|
return response.json()
|
||||||
except json.JSONDecodeError:
|
except (requests.exceptions.RequestException, json.JSONDecodeError):
|
||||||
return []
|
return []
|
||||||
return []
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user