feat: complete table population
This commit is contained in:
parent
f7b7cc5144
commit
f7dea32866
5 changed files with 82 additions and 22 deletions
|
@ -8,8 +8,5 @@ class Controller:
|
|||
try:
|
||||
entries = self.parse_file_service.parse_source_directory()
|
||||
self.sqlite_service.populate_tables(entries)
|
||||
except Exception as e:
|
||||
raise Exception(e)
|
||||
|
||||
finally:
|
||||
self.database_service.disconnect()
|
||||
|
|
5
src/models/tag.py
Normal file
5
src/models/tag.py
Normal file
|
@ -0,0 +1,5 @@
|
|||
from typing import List, TypedDict
|
||||
|
||||
|
||||
class Tag(TypedDict):
|
||||
name: str
|
|
@ -14,7 +14,7 @@ class ParseFileService:
|
|||
self.parse_markdown_service = ParseMarkdownService()
|
||||
|
||||
def __get_title(self, file):
|
||||
return os.path.basename(file)
|
||||
return os.path.splitext(os.path.basename(file))[0]
|
||||
|
||||
def __parse_file(self, file) -> Entry:
|
||||
markdown_data = self.parse_markdown_service.parse(file)
|
||||
|
@ -29,7 +29,7 @@ class ParseFileService:
|
|||
"body": markdown_data.get("body", []),
|
||||
}
|
||||
|
||||
def parse_source_directory(self):
|
||||
def parse_source_directory(self) -> list[Entry]:
|
||||
print(colored("INFO Indexing entries in source directory", "light_blue"))
|
||||
parsed_entries = []
|
||||
with os.scandir(self.source_directory) as dir:
|
||||
|
|
|
@ -19,7 +19,10 @@ class ParseMarkdownService:
|
|||
internal_link = re.findall(link_rgx, line)
|
||||
if internal_link:
|
||||
internal_links.append(
|
||||
[os.path.basename(link) for link in internal_link]
|
||||
[
|
||||
os.path.splitext(os.path.basename(link))[0]
|
||||
for link in internal_link
|
||||
]
|
||||
)
|
||||
return [item for row in internal_links for item in row]
|
||||
|
||||
|
|
|
@ -1,8 +1,10 @@
|
|||
import sqlite3
|
||||
from typing import Optional
|
||||
|
||||
from termcolor import colored
|
||||
|
||||
from models.entry import Entry
|
||||
from sql.create_tables import tables
|
||||
from src.models.entry import Entry
|
||||
|
||||
|
||||
class SqliteService:
|
||||
|
@ -10,31 +12,84 @@ class SqliteService:
|
|||
self.connection = connection
|
||||
self.cursor = connection.cursor()
|
||||
|
||||
def __query(self, sql, errorMessage: Optional[str] = None):
|
||||
def __query(self, sql, params=None, errorMessage: Optional[str] = None):
|
||||
try:
|
||||
self.cursor.execute(sql)
|
||||
if params:
|
||||
self.cursor.execute(sql, params)
|
||||
else:
|
||||
self.cursor.execute(sql)
|
||||
self.connection.commit()
|
||||
|
||||
except sqlite3.Error as sqliteError:
|
||||
raise Exception(f"ERROR SQLite: {sqliteError}")
|
||||
|
||||
except Exception as e:
|
||||
if errorMessage:
|
||||
raise Exception(f"ERROR {errorMessage}: {e}")
|
||||
else:
|
||||
raise Exception(f"ERROR Problem with database operation: {e}")
|
||||
raise
|
||||
|
||||
def create_tables(self):
|
||||
def __create_tables(self):
|
||||
for table in tables:
|
||||
self.__query(
|
||||
table["create_statement"], f"Problem creating table {table['name']}"
|
||||
table["create_statement"],
|
||||
errorMessage=f"Problem creating table {table['name']}",
|
||||
)
|
||||
print("INFO Created tables")
|
||||
print(colored("INFO Created tables", "light_blue"))
|
||||
|
||||
def truncate_tables(self):
|
||||
for table in tables:
|
||||
def __drop_tables(self):
|
||||
# Reverse the order of `tables` list to avoid foreign key violation when
|
||||
# deleting
|
||||
for table in reversed(tables):
|
||||
self.__query(
|
||||
f"DELETE FROM {table['name']}",
|
||||
f"Problem truncating table {table['name']}",
|
||||
f"DROP TABLE IF EXISTS {table['name']}",
|
||||
errorMessage=f"Problem truncating table {table['name']}",
|
||||
)
|
||||
print("INFO Cleared tables")
|
||||
print(colored("INFO Cleared tables", "light_blue"))
|
||||
|
||||
def __entry_exists(self, title) -> bool:
|
||||
self.__query("SELECT 1 FROM entries WHERE title = :title", {"title": title})
|
||||
result = self.cursor.fetchone()
|
||||
return result is not None
|
||||
|
||||
def __populate_base_tables(self, entries: list[Entry]):
|
||||
for entry in entries:
|
||||
self.__query(
|
||||
"INSERT INTO entries (title, last_modified, size, body) VALUES (:title, :last_modified, :size, :body)",
|
||||
entry,
|
||||
errorMessage=f"The following entry could not be added to `entries` table: {entry}",
|
||||
)
|
||||
tags = entry.get("tags")
|
||||
if tags:
|
||||
for tag in tags:
|
||||
self.__query(
|
||||
"INSERT OR IGNORE INTO tags (name) VALUES (:tag_name)",
|
||||
{"tag_name": tag},
|
||||
)
|
||||
|
||||
print(colored("INFO Base tables populated", "light_blue"))
|
||||
|
||||
def __populate_junction_tables(self, entries: list[Entry]):
|
||||
for entry in entries:
|
||||
tags = entry.get("tags")
|
||||
links = entry.get("links")
|
||||
if tags:
|
||||
for tag in tags:
|
||||
self.__query(
|
||||
"INSERT INTO entries_tags (entry_title, tag_name) VALUES (:entry_title, :tag_name)",
|
||||
{"entry_title": entry.get("title"), "tag_name": tag},
|
||||
)
|
||||
if links:
|
||||
for link in links:
|
||||
if self.__entry_exists(link):
|
||||
self.__query(
|
||||
"INSERT OR IGNORE INTO backlinks (source_entry_title, target_entry_title) VALUES (:source_entry_title, :target_entry_title)",
|
||||
{
|
||||
"source_entry_title": entry.get("title"),
|
||||
"target_entry_title": link,
|
||||
},
|
||||
)
|
||||
|
||||
print(colored("INFO Junction tables populated", "light_blue"))
|
||||
|
||||
def populate_tables(self, entries: list[Entry]):
|
||||
self.__drop_tables()
|
||||
self.__create_tables()
|
||||
self.__populate_base_tables(entries)
|
||||
self.__populate_junction_tables(entries)
|
||||
|
|
Loading…
Add table
Reference in a new issue