diff --git a/workers.py b/workers.py index 6d28a17..9af9a35 100644 --- a/workers.py +++ b/workers.py @@ -1,9 +1,10 @@ import datetime +import re import dateparser import requests from bs4 import BeautifulSoup, Tag -from PySide6.QtCore import QThread +from PySide6.QtCore import QDateTime, QThread from PySide6.QtSql import QSqlDatabase, QSqlQuery from lib.utils import query_error @@ -20,10 +21,11 @@ def update_proceedings( while len(trs) > 0: tr = trs.pop(0) assert isinstance(tr, Tag) - print(tr.contents) td = tr.contents[0] assert isinstance(td, Tag) and isinstance(td.string, str) - date = dateparser.parse(td.string) + tmp = dateparser.parse(td.string) + assert isinstance(tmp, datetime.datetime) + date = QDateTime.fromSecsSinceEpoch(int(tmp.timestamp())) td = tr.contents[1] # # When a case is GVRed, the will contain which means that @@ -38,8 +40,7 @@ def update_proceedings( ) query.bindValue(":cid", case_id) query.bindValue(":text", text) - assert isinstance(date, datetime.date) - query.bindValue(":date", date.timestamp()) + query.bindValue(":date", date) if not query.exec(): query_error(query) if not query.next(): @@ -47,7 +48,7 @@ def update_proceedings( "INSERT INTO entries (case_id, date, text) VALUES (:cid,:date,:text)" ) query.bindValue(":cid", case_id) - query.bindValue(":date", date.timestamp()) + query.bindValue(":date", date) query.bindValue(":text", text) if not query.exec(): query_error(query) @@ -80,12 +81,24 @@ def update_proceedings( query_error(query) assert isinstance(text, str) print(f"text: {text.lower()}") - result = not text.lower() in [ - "petition denied.", - "rehearing denied.", - # "judgement issued.", - ] - return result + # + # If cert is denied, a petion for rehearing can be requested. + # The petitioner has 40 days to file for a rehearing. + # + # Translation, if the last entry is "petition denied\..*$" and 40 days + # have passed, the case is final + active = True + text = text.lower() + if text.startswith("rehearing denied.") or text.startswith( + "judgment issued." + ): + active = False + if text.startswith("petition denied."): + assert isinstance(date, QDateTime) + delta = date.daysTo(QDateTime.currentDateTime()) + if delta > 40: + active = False + return active def update_db(case_id: str, db: QSqlDatabase) -> int: @@ -94,6 +107,12 @@ def update_db(case_id: str, db: QSqlDatabase) -> int: # # We assume that case_id == docket_id at this point. If it does not, # then we will build out from the request we get + print(f"Updating {case_id}") + matches = re.match(r"(\d\d)[-A](\d+)(.*)$", case_id) + if matches is None: + raise Exception(f"Not a match {case_id}") + else: + case_id = matches.group() query = QSqlQuery(db) query.prepare("SELECT * FROM cases WHERE docket_id = :did") @@ -135,8 +154,11 @@ def update_db(case_id: str, db: QSqlDatabase) -> int: assert span is not None and isinstance(span, Tag) tmp = span.contents[0] assert isinstance(tmp, str) - docket_id = tmp.strip() - docket_id = docket_id.replace("No. ", "") + matches = re.match(r"(No.)?\s*(\d+[-A]\d+).*$", tmp) + assert matches is not None + print(matches,matches.groups()) + docket_id = matches.group(2) + print(f"Found {docket_id}") # # Title is second row, first column @@ -165,9 +187,14 @@ def update_db(case_id: str, db: QSqlDatabase) -> int: tr = di.contents[2] assert isinstance(tr, Tag) and isinstance(tr.contents[1], Tag) td = tr.contents[1] - assert isinstance(td, Tag) and td.string is not None - docket_date = td.string.strip() - date = dateparser.parse(docket_date) + assert isinstance(td, Tag) + if td.string is None: + tmp = datetime.datetime(year=1776, month=7, day=4) + else: + docket_date = td.string.strip() + tmp = dateparser.parse(docket_date) + assert isinstance(tmp, datetime.datetime) + date = QDateTime.fromSecsSinceEpoch(int(tmp.timestamp())) # # linked case is row 3, column 0 @@ -176,44 +203,55 @@ def update_db(case_id: str, db: QSqlDatabase) -> int: linked = tr.contents[0].string # - # if it does not exists, create it. This stops a recursion loop. + # if this case does not exists, create it. This stops a recursion loop. # if not exists: query.prepare( - "INSERT INTO cases (docket_id, petitioners, respondents, date, active, linked) " - "VALUES (:did, :pet, :resp, :date, 1, NULL)" + "INSERT INTO cases (docket_id, petitioners, respondents, date, active) " + "VALUES (:did, :pet, :resp, :date, 1)" ) query.bindValue(":did", docket_id) query.bindValue(":pet", petitioners) query.bindValue(":resp", respondent) - assert isinstance(date, datetime.date) - query.bindValue(":date", date.timestamp()) + query.bindValue(":date", date) if not query.exec(): query_error(query) case_id = query.lastInsertId() - linked_id = None else: case_id = query.value(0) - linked_id = query.value("linked") assert isinstance(case_id, int) # # If there is a linked case, we need to get the ID for that case. if linked is not None: linked = linked.replace("Linked with ", "") - query.prepare("SELECT * FROM cases WHERE docket_id = :did") - query.bindValue(":did", linked) - if not query.exec(): - query_error(query) - if not query.next(): - new_id = update_db(linked, db) - else: - new_id = query.value(0) - if new_id != linked_id: - query.prepare("UPDATE cases SET linked=:lid WHERE case_id = :cid") - query.bindValue(":lid", new_id) - query.bindValue(":cid", case_id) + for did in linked.split(','): + did = did.strip() + query.prepare("SELECT * FROM cases WHERE docket_id = :did") + query.bindValue(":did", linked) if not query.exec(): query_error(query) + if not query.next(): + linked_id = update_db(did, db) + if linked_id <= 0: + raise Exception(f"Unable to create linked case: {did}") + else: + linked_id = query.value('case_id') + # + # + + query.prepare("SELECT * FROM cases_cases WHERE lhs = :lhs " + "AND rhs = :rhs") + query.bindValue(':lhs', case_id) + query.bindValue(':rhs', linked_id) + if not query.exec(): + query_error(query) + if not query.next(): + query.prepare("INSERT INTO cases_cases (lhs, rhs) " + "VALUES ( :lhs, :rhs)") + query.bindValue(":lhs", case_id) + query.bindValue(":rhs", linked_id) + if not query.exec(): + query_error(query) # # XXX - Process lower courts # @@ -258,8 +296,7 @@ class loadCases(QThread): db = QSqlDatabase.cloneDatabase("qt_sql_default_connection", "load") if not db.open(): raise Exception("db.open()") - dt = datetime.datetime.now() - year = dt.strftime("%y") + year = QDateTime.currentDateTime().toString("yy") query = QSqlQuery(db) query.prepare("SELECT * FROM history WHERE year = :year") print(f"year = {year}") @@ -291,7 +328,6 @@ class loadCases(QThread): else: docket_id = f"{year}-{number}" query.bindValue(":did", docket_id) - print(f"Loading {docket_id}") if not query.exec(): query_error(query) if query.next(): @@ -303,13 +339,14 @@ class loadCases(QThread): print(f"result: {result}") if result < 0: year = f"{int(year) - 1:02d}" - query.prepare( - "UPDATE history set number = :number WHERE history_id=:hid" - ) - query.bindValue(":number", number - 1) - query.bindValue(":hid", history_id) - if not query.exec(): - query_error(query) + if number > 1: + query.prepare( + "UPDATE history set number = :number WHERE history_id=:hid" + ) + query.bindValue(":number", number - 1) + query.bindValue(":hid", history_id) + if not query.exec(): + query_error(query) query.prepare("SELECT * FROM history WHERE year = :year") print(f"year = {year}") @@ -336,7 +373,14 @@ class loadCases(QThread): number += 1 count += 1 - + if number > 1: + query.prepare( + "UPDATE history SET number= :number WHERE year = :year" + ) + query.bindValue(":number", number) + query.bindValue(":year", year) + if not query.exec(): + query_error(query) db.close() del db QSqlDatabase.removeDatabase("load")