(init): Keys and Prefix Management
This commit is contained in:
@@ -0,0 +1,2 @@
|
||||
data
|
||||
*/__pycache__
|
||||
@@ -0,0 +1,27 @@
|
||||
import os
|
||||
from pathlib import Path
|
||||
import sqlite3
|
||||
|
||||
tam_data_dir = os.getenv("TAM_DATA_DIR", "./data")
|
||||
|
||||
def session():
|
||||
data_dir = Path(tam_data_dir)
|
||||
if not data_dir.is_dir():
|
||||
data_dir.mkdir(parents=True)
|
||||
db_file = data_dir / "tam-remote.db"
|
||||
conn = sqlite3.connect(db_file)
|
||||
cur = conn.cursor()
|
||||
return conn, cur
|
||||
|
||||
def init_db():
|
||||
conn, cur = session()
|
||||
cur.execute("CREATE TABLE IF NOT EXISTS auth_keys (auth_key TEXT PRIMARY KEY, description TEXT)")
|
||||
cur.execute("CREATE TABLE IF NOT EXISTS prefixes (prefix TEXT PRIMARY KEY, color TEXT, weight INTEGER)")
|
||||
conn.commit()
|
||||
conn.close()
|
||||
|
||||
class RepoTemplate:
|
||||
def __init__(self):
|
||||
self.conn, self.cur = session()
|
||||
def __del__(self):
|
||||
self.conn.close()
|
||||
@@ -0,0 +1,31 @@
|
||||
from dataclasses import dataclass
|
||||
from db import init_db
|
||||
from fastapi import FastAPI, Header
|
||||
import os
|
||||
from routers import imp_routers
|
||||
from system.auth import AuthRepo
|
||||
|
||||
tam_env = os.getenv("TAM_ENV", "prod")
|
||||
|
||||
@dataclass
|
||||
class MainRoute:
|
||||
whoami: str = "TAM Server"
|
||||
authenticated: bool = False
|
||||
healthy: bool = True
|
||||
|
||||
init_db()
|
||||
|
||||
app = FastAPI(
|
||||
title="TAM Server",
|
||||
description="Server for Ticket Auction Manager",
|
||||
version="0.0.1",
|
||||
docs_url=None if tam_env == "prod" else "/docs",
|
||||
redoc_url=None,
|
||||
openapi_url=None if tam_env == "prod" else "/openapi.json"
|
||||
)
|
||||
|
||||
@app.get("/api")
|
||||
def get_main_route(tam_key: str = Header("")):
|
||||
return MainRoute(authenticated=AuthRepo().check_key(tam_key))
|
||||
|
||||
imp_routers(app)
|
||||
@@ -0,0 +1,7 @@
|
||||
from fastapi import FastAPI
|
||||
from system.auth import auth_router
|
||||
from system.prefixes import prefix_router
|
||||
|
||||
def imp_routers(app: FastAPI):
|
||||
app.include_router(auth_router)
|
||||
app.include_router(prefix_router)
|
||||
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,83 @@
|
||||
from dataclasses import dataclass
|
||||
from db import RepoTemplate
|
||||
from fastapi import APIRouter, Header, HTTPException, status
|
||||
import os
|
||||
import random
|
||||
import string
|
||||
|
||||
tam_pwd = os.getenv("TAM_PWD", "dbob16")
|
||||
ex_pwd = HTTPException(status.HTTP_401_UNAUTHORIZED, "Invalid Password")
|
||||
ex_key = HTTPException(status.HTTP_401_UNAUTHORIZED, "Invalid Key")
|
||||
rdm_str_choice = string.ascii_uppercase + string.digits
|
||||
|
||||
def check_pw(in_pw: str):
|
||||
if tam_pwd != in_pw:
|
||||
raise ex_pwd
|
||||
|
||||
def gen_key():
|
||||
return "".join(random.choice(rdm_str_choice) for _ in range(32))
|
||||
|
||||
@dataclass
|
||||
class AuthReq:
|
||||
description: str = ""
|
||||
|
||||
@dataclass
|
||||
class AuthKey:
|
||||
auth_key: str = ""
|
||||
description: str = ""
|
||||
|
||||
class AuthRepo(RepoTemplate):
|
||||
def get_all_keys(self):
|
||||
self.cur.execute("SELECT * FROM auth_keys ORDER BY description, auth_key")
|
||||
results = self.cur.fetchall()
|
||||
return [AuthKey(*r) for r in results]
|
||||
def create_key(self, desciption: str = ""):
|
||||
while True:
|
||||
new_key = gen_key()
|
||||
self.cur.execute("SELECT * FROM auth_keys WHERE auth_key = ?", (new_key,))
|
||||
results = self.cur.fetchall()
|
||||
if len(results) == 0:
|
||||
break
|
||||
self.cur.execute("INSERT INTO auth_keys VALUES (?, ?) RETURNING *", (new_key, desciption))
|
||||
rtn_key = self.cur.fetchone()
|
||||
self.conn.commit()
|
||||
return AuthKey(*rtn_key)
|
||||
def del_key(self, auth_key: str = ""):
|
||||
self.cur.execute("DELETE FROM auth_keys WHERE auth_key = ? RETURNING *", (auth_key,))
|
||||
results = self.cur.fetchall()
|
||||
self.conn.commit()
|
||||
if len(results) > 0:
|
||||
return AuthKey(*results[0])
|
||||
else:
|
||||
return AuthKey(auth_key, "")
|
||||
def check_key(self, auth_key: str = ""):
|
||||
self.cur.execute("SELECT * FROM auth_keys WHERE auth_key = ?", (auth_key,))
|
||||
results = self.cur.fetchall()
|
||||
if results:
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
def verify_key(self, auth_key: str = ""):
|
||||
self.cur.execute("SELECT * FROM auth_keys WHERE auth_key = ?", (auth_key,))
|
||||
results = self.cur.fetchone()
|
||||
if results:
|
||||
return True
|
||||
else:
|
||||
raise ex_key
|
||||
|
||||
auth_router = APIRouter(prefix="/api/auth")
|
||||
|
||||
@auth_router.get("")
|
||||
def get_auth_keys(tam_pw: str = Header("")) -> list[AuthKey]:
|
||||
check_pw(tam_pw)
|
||||
return AuthRepo().get_all_keys()
|
||||
|
||||
@auth_router.post("")
|
||||
def create_auth_key(auth_req: AuthReq, tam_pw: str = Header("")) -> AuthKey:
|
||||
check_pw(tam_pw)
|
||||
return AuthRepo().create_key(auth_req.description)
|
||||
|
||||
@auth_router.delete("")
|
||||
def delete_auth_key(key_to_del: str, tam_pw: str = Header("")) -> AuthKey:
|
||||
check_pw(tam_pw)
|
||||
return AuthRepo().del_key(key_to_del)
|
||||
@@ -0,0 +1,48 @@
|
||||
from dataclasses import dataclass
|
||||
from db import RepoTemplate
|
||||
from .auth import AuthRepo
|
||||
from fastapi import APIRouter, Header
|
||||
|
||||
@dataclass
|
||||
class Prefix:
|
||||
prefix: str
|
||||
color: str = ""
|
||||
weight: int = 0
|
||||
|
||||
class PrefixRepo(RepoTemplate):
|
||||
def get_all_prefixes(self):
|
||||
self.cur.execute("SELECT * FROM prefixes ORDER BY weight, prefix")
|
||||
results = self.cur.fetchall()
|
||||
return [Prefix(*r) for r in results]
|
||||
def post_prefixes(self, ps: list[Prefix]):
|
||||
for p in ps:
|
||||
self.cur.execute("""INSERT INTO prefixes VALUES (?, ?, ?)
|
||||
ON CONFLICT (prefix) DO UPDATE SET
|
||||
color = EXCLUDED.color, weight = EXCLUDED.weight""", (p.prefix, p.color, p.weight))
|
||||
self.conn.commit()
|
||||
return ps
|
||||
def del_prefix(self, p: str):
|
||||
self.cur.execute("DELETE FROM prefixes WHERE prefix = ? RETURNING *", (p,))
|
||||
result = self.cur.fetchone()
|
||||
self.conn.commit()
|
||||
if result:
|
||||
return Prefix(*result)
|
||||
else:
|
||||
return Prefix(p, "gray", 1)
|
||||
|
||||
prefix_router = APIRouter(prefix="/api/prefixes")
|
||||
|
||||
@prefix_router.get("")
|
||||
def get_all_prefixes(tam_key: str = Header("")):
|
||||
AuthRepo().verify_key(tam_key)
|
||||
return PrefixRepo().get_all_prefixes()
|
||||
|
||||
@prefix_router.post("")
|
||||
def post_prefixes(ps: list[Prefix], tam_key: str = Header("")):
|
||||
AuthRepo().verify_key(tam_key)
|
||||
return PrefixRepo().post_prefixes(ps)
|
||||
|
||||
@prefix_router.delete("")
|
||||
def delete_prefixes(p: str, tam_key: str = Header("")):
|
||||
AuthRepo().verify_key(tam_key)
|
||||
return PrefixRepo().del_prefix(p)
|
||||
@@ -0,0 +1 @@
|
||||
TAM_ENV=dev fastapi dev app/main.py
|
||||
Reference in New Issue
Block a user