- Импортирован модуль logging для отладки. - Закомментированы строки логирования запросов и результатов в методе fetch_vin_info. - Добавлены кнопки для взаимодействия с пользователем после успешной оплаты.
125 lines
6.0 KiB
Python
125 lines
6.0 KiB
Python
# db.py
|
|
import oracledb
|
|
from typing import Optional, Tuple
|
|
import logging
|
|
|
|
|
|
class OracleDatabase:
|
|
def __init__(self, user: str, password: str, dsn: str):
|
|
self._user = user
|
|
self._password = password
|
|
self._dsn = dsn
|
|
self._pool: Optional[oracledb.ConnectionPool] = None
|
|
|
|
async def connect(self):
|
|
# Oracle does not support true async I/O; use threaded connection pool
|
|
self._pool = oracledb.create_pool(
|
|
user=self._user,
|
|
password=self._password,
|
|
dsn=self._dsn,
|
|
min=1,
|
|
max=4,
|
|
increment=1,
|
|
getmode=oracledb.POOL_GETMODE_WAIT
|
|
)
|
|
|
|
async def close(self):
|
|
if self._pool:
|
|
self._pool.close()
|
|
|
|
async def fetch_user(self, user_id: int):
|
|
# Manual async wrapper since oracledb is synchronous (threaded)
|
|
def _query():
|
|
with self._pool.acquire() as conn:
|
|
with conn.cursor() as cur:
|
|
cur.execute("SELECT id, name FROM users WHERE id = :id", {"id": user_id})
|
|
return cur.fetchone()
|
|
import asyncio
|
|
return await asyncio.to_thread(_query)
|
|
|
|
async def fetch_vin_info(self, vin: str) -> Tuple[str, str, str, int]:
|
|
# Manual async wrapper since oracledb is synchronous (threaded)
|
|
def _query():
|
|
with self._pool.acquire() as conn:
|
|
with conn.cursor() as cur:
|
|
query = """
|
|
select 'None',
|
|
COALESCE((select value from salvagedb.m_JSONS_FROM_NHTSA v3 where v3.svin =s.svin and v3.variableid ='26'),
|
|
(select val from salvagedb.vind2 where svin = substr(s.vin, 1, 8) || '*' || substr(s.vin, 10, 2) and varb = 'Make'),'UNKNOWN') make,
|
|
COALESCE((select value from salvagedb.m_JSONS_FROM_NHTSA v3 where v3.svin =s.svin and v3.variableid ='28'),
|
|
(select val from salvagedb.vind2 where svin = substr(s.vin, 1, 8) || '*' || substr(s.vin, 10, 2) and varb = 'Model'),'UNKNOWN') model,
|
|
COALESCE((select value from salvagedb.m_JSONS_FROM_NHTSA v3 where v3.svin =s.svin and v3.variableid ='29'),
|
|
(select val from salvagedb.vind2 where svin = substr(s.vin, 1, 8) || '*' || substr(s.vin, 10, 2) and varb = 'Model Year'),'UNKNOWN') year,
|
|
(select count(*) from salvagedb.m_JSONS_FROM_NHTSA v3 where v3.svin =s.svin) cnt
|
|
from (select substr(:vin,1,10) svin, :vin vin from dual) s
|
|
"""
|
|
cur.execute(query, {"vin": vin})
|
|
result = cur.fetchone()
|
|
if result:
|
|
return result[1], result[2], result[3], result[4] # make, model, year, cnt
|
|
return "UNKNOWN", "UNKNOWN", "UNKNOWN", 0
|
|
import asyncio
|
|
return await asyncio.to_thread(_query)
|
|
|
|
async def fetch_detailed_vin_info(self, vin: str) -> dict:
|
|
# Manual async wrapper since oracledb is synchronous (threaded)
|
|
def _query():
|
|
with self._pool.acquire() as conn:
|
|
with conn.cursor() as cur:
|
|
query = """
|
|
select dp.parameter_name,
|
|
dp.category_name,
|
|
d.value,
|
|
dp.endesc
|
|
from salvagedb.m_JSONS_FROM_NHTSA d
|
|
left join salvagedb.decode_params dp
|
|
on d.variableid = dp.parameter_id
|
|
where svin = substr(:vin, 1, 10)
|
|
order by dp.category_level
|
|
"""
|
|
# logging.info(f"Query: {query}")
|
|
cur.execute(query, {"vin": vin})
|
|
results = cur.fetchall()
|
|
# logging.info(f"Results: {results}")
|
|
|
|
|
|
# Organize data by categories
|
|
detailed_info = {
|
|
'basic_characteristics': {},
|
|
'engine_and_powertrain': {},
|
|
'active_safety': {},
|
|
'transmission': {},
|
|
'passive_safety': {},
|
|
'dimensions_and_construction': {},
|
|
'brake_system': {},
|
|
'lighting': {},
|
|
'additional_features': {},
|
|
'manufacturing_and_localization': {},
|
|
'ncsa_data': {},
|
|
'technical_information_and_errors': {},
|
|
'all_params': {} # Flat dictionary for easy access
|
|
}
|
|
|
|
for row in results:
|
|
param_name, category_name, value, description = row
|
|
if param_name and value:
|
|
# Create key from parameter name (lowercase, spaces to underscores)
|
|
key = param_name.lower().replace(' ', '_').replace('(', '').replace(')', '').replace('/', '_').replace('-', '_')
|
|
|
|
# Add to flat dictionary
|
|
detailed_info['all_params'][key] = value
|
|
|
|
# Add to category-specific dictionary
|
|
if category_name:
|
|
category_key = category_name.lower().replace(' ', '_').replace('(', '').replace(')', '').replace('/', '_').replace('-', '_')
|
|
if category_key in detailed_info:
|
|
detailed_info[category_key][key] = {
|
|
'value': value,
|
|
'description': description,
|
|
'param_name': param_name
|
|
}
|
|
|
|
return detailed_info
|
|
import asyncio
|
|
return await asyncio.to_thread(_query)
|