Molodetz blogrol volgens DPP-template
This commit is contained in:
@@ -0,0 +1,116 @@
|
||||
# retoor <retoor@molodetz.nl>
|
||||
import logging
|
||||
import re
|
||||
from datetime import datetime, timezone
|
||||
|
||||
import dataset
|
||||
import sqlalchemy
|
||||
import uuid_utils
|
||||
from sqlalchemy.pool import NullPool
|
||||
|
||||
from molodetz import config
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
ON_CONNECT_STATEMENTS = [
|
||||
"PRAGMA journal_mode=WAL",
|
||||
"PRAGMA synchronous=NORMAL",
|
||||
"PRAGMA busy_timeout=30000",
|
||||
"PRAGMA cache_size=-8000",
|
||||
"PRAGMA temp_store=MEMORY",
|
||||
"PRAGMA mmap_size=268435456",
|
||||
]
|
||||
|
||||
config.ensure_data_dirs()
|
||||
|
||||
db = dataset.connect(
|
||||
config.DATABASE_URL,
|
||||
engine_kwargs={
|
||||
"connect_args": {"timeout": 30, "check_same_thread": False},
|
||||
"poolclass": NullPool,
|
||||
},
|
||||
on_connect_statements=ON_CONNECT_STATEMENTS,
|
||||
)
|
||||
|
||||
|
||||
def generate_uid():
|
||||
return str(uuid_utils.uuid7())
|
||||
|
||||
|
||||
def now_iso():
|
||||
return datetime.now(timezone.utc).isoformat()
|
||||
|
||||
|
||||
def parse_iso(value):
|
||||
if not value:
|
||||
return None
|
||||
try:
|
||||
parsed = datetime.fromisoformat(str(value))
|
||||
except ValueError:
|
||||
return None
|
||||
if parsed.tzinfo is None:
|
||||
parsed = parsed.replace(tzinfo=timezone.utc)
|
||||
return parsed
|
||||
|
||||
|
||||
def refresh_snapshot():
|
||||
try:
|
||||
if getattr(db.local, "tx", None):
|
||||
return
|
||||
conn = db.executable
|
||||
if conn.in_transaction():
|
||||
conn.commit()
|
||||
except Exception as exc:
|
||||
logger.warning("refresh_snapshot failed: %s", exc)
|
||||
|
||||
|
||||
def table_exists(name):
|
||||
return name in db.tables
|
||||
|
||||
|
||||
def in_clause(values, prefix="v"):
|
||||
params = {f"{prefix}{index}": value for index, value in enumerate(values)}
|
||||
placeholders = ", ".join(f":{key}" for key in params)
|
||||
return placeholders, params
|
||||
|
||||
|
||||
def atomic_update(sql, **params):
|
||||
with db:
|
||||
result = db.executable.execute(sqlalchemy.text(sql), params)
|
||||
return result.rowcount
|
||||
|
||||
|
||||
def run_write(sql, **params):
|
||||
with db:
|
||||
db.query(sql, **params)
|
||||
|
||||
|
||||
def slugify(text):
|
||||
lowered = (text or "").lower()
|
||||
replaced = re.sub(r"[^a-z0-9-]", "-", lowered)
|
||||
return re.sub(r"-+", "-", replaced).strip("-")
|
||||
|
||||
|
||||
def make_combined_slug(text, uid):
|
||||
tail = uid.replace("-", "")[-12:]
|
||||
slug = slugify(text)
|
||||
return f"{slug}-{tail}" if slug else tail
|
||||
|
||||
|
||||
def shard_path(uid):
|
||||
tail = uid.replace("-", "")
|
||||
return f"{tail[-2:]}/{tail[-4:-2]}"
|
||||
|
||||
|
||||
def resolve_by_slug(table_name, slug, include_deleted=False):
|
||||
if table_name not in db.tables:
|
||||
return None
|
||||
table = db[table_name]
|
||||
for key in ("slug", "uid"):
|
||||
criteria = {key: slug}
|
||||
if not include_deleted:
|
||||
criteria["deleted_at"] = None
|
||||
row = table.find_one(**criteria)
|
||||
if row:
|
||||
return row
|
||||
return None
|
||||
Reference in New Issue
Block a user