text2sql-assistant / src /t2s /data /schema.py
Ashoksainibadu's picture
Upload folder using huggingface_hub
388137e verified
Raw History Blame Contribute Delete
2.95 kB
"""SQLite schema reader and DDL serializer."""
import sqlite3
from pathlib import Path
from typing import List
def get_sqlite_schema_ddl(
db_path: str, include_sample_rows: bool = False, num_sample_rows: int = 3
) -> str:
path = Path(db_path)
if not path.exists():
raise FileNotFoundError(f"Database file not found: {db_path}")
conn = sqlite3.connect(f"file:{path}?mode=ro", uri=True)
cursor = conn.cursor()
# Get sorted table names (excluding internal sqlite tables)
cursor.execute(
"SELECT name FROM sqlite_master WHERE type='table' AND name NOT LIKE 'sqlite_%' ORDER BY name;"
)
tables = [row[0] for row in cursor.fetchall()]
ddl_statements: List[str] = []
for table in tables:
# Get column info: cid, name, type, notnull, dflt_value, pk
cursor.execute(f"PRAGMA table_info('{table}');")
col_info = cursor.fetchall()
if not col_info:
continue
columns_def: List[str] = []
pk_cols: List[str] = []
for col in col_info:
col_name = col[1]
col_type = col[2] if col[2] else "TEXT"
is_pk = col[5]
if is_pk:
pk_cols.append(col_name)
columns_def.append(f" {col_name} {col_type}")
# Get foreign keys: id, seq, table, from, to, on_update, on_delete, match
cursor.execute(f"PRAGMA foreign_key_list('{table}');")
fk_info = cursor.fetchall()
fk_defs: List[str] = []
for fk in fk_info:
from_col = fk[3]
target_table = fk[2]
to_col = fk[4]
if from_col and target_table and to_col:
fk_defs.append(f" FOREIGN KEY ({from_col}) REFERENCES {target_table}({to_col})")
if pk_cols:
pk_str = ", ".join(pk_cols)
columns_def.append(f" PRIMARY KEY ({pk_str})")
columns_def.extend(fk_defs)
table_ddl = f"CREATE TABLE {table} (\n" + ",\n".join(columns_def) + "\n);"
if include_sample_rows:
try:
cursor.execute(f"SELECT * FROM '{table}' LIMIT {num_sample_rows};")
sample_rows = cursor.fetchall()
if sample_rows:
sample_comments = ["-- Example rows:"]
for row in sample_rows:
row_str = ", ".join(
"NULL"
if val is None
else f"'{str(val)[:50]}'"
if isinstance(val, str)
else str(val)
for val in row
)
sample_comments.append(f"-- ({row_str})")
table_ddl += "\n" + "\n".join(sample_comments)
except Exception:
pass
ddl_statements.append(table_ddl)
conn.close()
return "\n\n".join(ddl_statements)