Skip to content

Commit

Permalink
Replace table retrieval with DB call.
Browse files Browse the repository at this point in the history
  • Loading branch information
scossu committed Aug 27, 2024
1 parent 9577312 commit 5b3b757
Show file tree
Hide file tree
Showing 4 changed files with 132 additions and 22 deletions.
16 changes: 4 additions & 12 deletions scriptshifter/rest_api.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import logging

from base64 import b64encode
from copy import deepcopy
from email.message import EmailMessage
from json import dumps
from os import environ, urandom
Expand All @@ -15,7 +14,7 @@
GIT_COMMIT, GIT_TAG,
SMTP_HOST, SMTP_PORT)
from scriptshifter.exceptions import ApiError
from scriptshifter.tables import list_tables, load_table
from scriptshifter.tables import list_tables, get_language
from scriptshifter.trans import transliterate


Expand Down Expand Up @@ -89,24 +88,17 @@ def list_languages():
@app.route("/table/<lang>")
def dump_table(lang):
"""
Dump parsed transliteration table for a language.
Dump a language configuration from the DB.
"""
tbl = deepcopy(load_table(lang))
for sec_name in ("roman_to_script", "script_to_roman"):
if sec_name in tbl:
for hname, fn_defs in tbl[sec_name].get("hooks", {}).items():
tbl[sec_name]["hooks"][hname] = [
(fn.__name__, kw) for (fn, kw) in fn_defs]

return jsonify(tbl)
return get_language(lang)


@app.route("/options/<lang>", methods=["GET"])
def get_options(lang):
"""
Get extra options for a table.
"""
tbl = load_table(lang)
tbl = get_language(lang)

return jsonify(tbl.get("options", []))

Expand Down
135 changes: 126 additions & 9 deletions scriptshifter/tables/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,8 @@
import re
import sqlite3

from functools import cache
from importlib import import_module
from json import dumps
from json import dumps as jdumps, loads as jloads
from os import R_OK, access, environ, makedirs, path, unlink
from shutil import move

Expand Down Expand Up @@ -223,7 +222,7 @@ def populate_table(conn, tid, tname):
) VALUES (?, ?, ?, ?, ?, ?)""",
(
tid, t_dir, k, i,
hook_data[0].__name__, dumps(hook_data[1:])))
hook_data[0].__name__, jdumps(hook_data[1:])))

# Ignore rules (R2S only).
for row in sec.get("ignore", []):
Expand Down Expand Up @@ -262,14 +261,15 @@ def populate_table(conn, tid, tname):
for opt in data.get("options", []):
conn.execute(
"""INSERT INTO tbl_option (
lang_id, name, label, description, dtype, default_v
) VALUES (?, ?, ?, ?, ?, ?)""",
lang_id, name, label, description, dtype,
options, default_v
) VALUES (?, ?, ?, ?, ?, ?, ?)""",
(
tid, opt["id"], opt["label"], opt["description"],
opt["type"], opt["default"]))
opt["type"], jdumps(opt.get("options")),
opt["default"]))


@cache
def list_tables():
"""
List all the indexed tables.
Expand Down Expand Up @@ -297,10 +297,9 @@ def list_tables():
return tdata


@cache
def load_table(tname):
"""
Load one transliteration table and possible parents.
Parse one transliteration table and possible parents from YML files.
The table file is parsed into an in-memory configuration that contains
the language & script metadata and parsing rules.
Expand Down Expand Up @@ -467,3 +466,121 @@ def load_hook_fn(cname, sec):
hook_fn[cfg_hook].append((fn, fn_kwargs))

return hook_fn


def get_language(lang):
""" Get all language options from the DB. """

conn = sqlite3.connect(DB_PATH)

with conn:
lang_q = conn.execute(
"""SELECT id, name, label, features, marc_code, description
FROM tbl_language WHERE name = ?""", (lang,))
lang_data = lang_q.fetchone()
lang_id = lang_data[0]

data = {
"name": lang_data[1],
"label": lang_data[2],
"has_s2r": bool(lang_data[3] & FEAT_S2R),
"has_r2s": bool(lang_data[3] & FEAT_R2S),
"case_sensitive": not (lang_data[3] & FEAT_CASEI),
"marc_code": lang_data[4],
"description": lang_data[5],
}

# Normalization.

norm_q = conn.execute(
"""SELECT src, dest FROM tbl_normalize
WHERE lang_id = ?""",
(lang_id,))
norm_data = {row[0]: row[1] for row in norm_q}
if len(norm_data):
data["normalize"] = norm_data

# Script to Roman map and hooks.

if data["has_s2r"]:
data["script_to_roman"] = {}
s2r_q = conn.execute(
"""SELECT src, dest FROM tbl_trans_map
WHERE lang_id = ? AND dir = ?""",
(lang_id, FEAT_S2R))
s2r_map = tuple((row[0], row[1]) for row in s2r_q)
if len(s2r_map):
data["script_to_roman"]["map"] = s2r_map

hooks_q = conn.execute(
"""SELECT name, fn, signature
FROM tbl_hook WHERE lang_id = ? AND dir = ?
ORDER BY sort""",
(lang_id, FEAT_S2R))
s2r_hooks = [
{
"name": row[0],
"fn": row[1],
"signature": jloads(row[2]),
} for row in hooks_q
]
if len(s2r_hooks):
data["script_to_roman"]["hooks"] = s2r_hooks

# Roman to script map, ignore list, and hooks.

if data["has_r2s"]:
data["roman_to_script"] = {}
r2s_q = conn.execute(
"""SELECT src, dest FROM tbl_trans_map
WHERE lang_id = ? AND dir = ?""",
(lang_id, FEAT_R2S))
r2s_map = tuple((row[0], row[1]) for row in r2s_q)
if len(r2s_map):
data["roman_to_script"]["map"] = r2s_map

ignore_q = conn.execute(
"""SELECT rule, features FROM tbl_ignore
WHERE lang_id = ?""",
(lang_id,))
# Features (regular expressions) not implemented yet.
r2s_ignore = tuple(row[0] for row in ignore_q)
if len(r2s_ignore):
data["roman_to_script"]["ignore"] = r2s_ignore

hooks_q = conn.execute(
"""SELECT name, fn, signature
FROM tbl_hook WHERE lang_id = ? AND dir = ?
ORDER BY sort""",
(lang_id, FEAT_R2S))
r2s_hooks = [
{
"name": row[0],
"fn": row[1],
"signature": jloads(row[2]),
} for row in hooks_q
]
if len(r2s_hooks):
data["roman_to_script"]["hooks"] = r2s_hooks

options_q = conn.execute(
"""SELECT name, label, description, dtype, options, default_v
FROM tbl_option
WHERE lang_id = ?""",
(lang_id,))

opt_data = tuple(
{
"id": row[0],
"label": row[1],
"description": row[2],
"type": row[3],
"options": jloads(row[4]) if row[4] else None,
"default": row[5],
}
for row in options_q
)
if len(opt_data):
data["options"] = opt_data

return data
2 changes: 1 addition & 1 deletion scriptshifter/tables/data/yiddish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ general:
options:
- id: loshn_koydesh
label: Loshn Koydesh
description: "[TODO]"
description: "Apply Loshn Koydesh vocalization."
type: boolean
default: false

Expand Down
1 change: 1 addition & 0 deletions scriptshifter/tables/init.sql
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,7 @@ CREATE TABLE tbl_option (
label TEXT NOT NULL,
description TEXT,
dtype TEXT,
options TEXT,
default_v TEXT,

FOREIGN KEY (lang_id) REFERENCES tbl_language(id) ON DELETE CASCADE
Expand Down

0 comments on commit 5b3b757

Please sign in to comment.