mirror of
ssh://git.janware.com/srv/git/janware/proj/jw-python
synced 2026-01-15 01:52:56 +01:00
db.query: Add Query, QueryResult, Queries
Signed-off-by: Jan Lindemann <jan@janware.com>
This commit is contained in:
parent
2b061a6dc4
commit
4cc9906055
4 changed files with 217 additions and 0 deletions
4
tools/python/jwutils/db/query/Makefile
Normal file
4
tools/python/jwutils/db/query/Makefile
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
TOPDIR = ../../../../..
|
||||
|
||||
include $(TOPDIR)/make/proj.mk
|
||||
include $(JWBDIR)/make/py-mod.mk
|
||||
93
tools/python/jwutils/db/query/Queries.py
Normal file
93
tools/python/jwutils/db/query/Queries.py
Normal file
|
|
@ -0,0 +1,93 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
|
||||
from typing import Any
|
||||
|
||||
import abc
|
||||
|
||||
from jwutils.log import *
|
||||
from jwutils.misc import load_classes
|
||||
from jwutils.Cmds import Cmds
|
||||
from jwutils.db.DataBase import DataBase
|
||||
from jwutils.db.query.Query import Query as QueryBase
|
||||
from jwutils.db.query.QueryResult import QueryResult
|
||||
from jwutils.db.schema.Schema import Schema
|
||||
|
||||
class Queries(abc.ABC): # export
|
||||
|
||||
class Query(QueryBase):
|
||||
|
||||
def __init__(self: Any, query: QueryBase, name: str, location: str, func: Any):
|
||||
self.__query = query
|
||||
self.__func = func
|
||||
self.__location = location
|
||||
self.__name = name
|
||||
|
||||
# -- implement API
|
||||
|
||||
def _run(self, *args, **kwargs) -> QueryResult:
|
||||
return self.__func(*args, **kwargs)
|
||||
|
||||
def _register(self):
|
||||
raise Exception('Can\'t call register on this object')
|
||||
|
||||
def _column_names(self) -> list[str]:
|
||||
return self.__query.column_names
|
||||
|
||||
@property
|
||||
def name(self):
|
||||
return self.__name
|
||||
|
||||
def __init__(self, db: DataBase) -> None:
|
||||
assert(isinstance(db, DataBase))
|
||||
self.__db = db
|
||||
self.__queries: dict[str, Any] = dict()
|
||||
|
||||
def __getitem__(self, name) -> Query:
|
||||
try:
|
||||
return self.__queries[name]
|
||||
except Exception as e:
|
||||
slog(ERR, f'Failed to retrieve query {name} ({e})')
|
||||
slog_m(ERR, '\n'.join(self.__queries.keys()))
|
||||
raise
|
||||
|
||||
@property
|
||||
def db(self) -> DataBase:
|
||||
return self.__db
|
||||
|
||||
@property
|
||||
def app(self) -> Cmds:
|
||||
return self.__db.app
|
||||
|
||||
def load(self, modules: list[str], cls=QueryBase):
|
||||
for path in modules:
|
||||
slog(INFO, f'Loading modules from {path}')
|
||||
for c in load_classes(path, cls):
|
||||
c(self).register()
|
||||
|
||||
@property
|
||||
def schema(self) -> Schema:
|
||||
return self.__db.schema
|
||||
|
||||
def add(self, query: QueryBase, query_name: str, location: str, func: Any):
|
||||
slog(INFO, f'Adding query "{query_name}" on location "{location}"')
|
||||
assert(isinstance(query_name, str))
|
||||
assert(isinstance(location, str))
|
||||
#ret = self.Query(query, func)
|
||||
ret = self.Query(query, query_name, location, func)
|
||||
#setattr(ret, 'name', name)
|
||||
self.__queries[query_name] = ret
|
||||
self._add(ret)
|
||||
|
||||
# To be overriden in case the derived class wants to keep track
|
||||
def _add(self, query):
|
||||
pass
|
||||
|
||||
# def register(self):
|
||||
# return self._register()
|
||||
#
|
||||
# def query(self, *args, **kwargs):
|
||||
# return self.app.query(*args, **kwargs)
|
||||
#
|
||||
# def pages(self, *args, **kwargs):
|
||||
# return self.app.pages(*args, **kwargs)
|
||||
#
|
||||
64
tools/python/jwutils/db/query/Query.py
Normal file
64
tools/python/jwutils/db/query/Query.py
Normal file
|
|
@ -0,0 +1,64 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
|
||||
from typing import Any
|
||||
|
||||
import abc
|
||||
|
||||
from jwutils.log import *
|
||||
from jwutils.misc import load_classes
|
||||
from jwutils.Cmds import Cmds
|
||||
from jwutils.db.DataBase import DataBase
|
||||
from jwutils.db.query.QueryResult import QueryResult
|
||||
#from jwutils.db.query.Queries import Queries
|
||||
|
||||
class Query(abc.ABC): # export
|
||||
|
||||
def __init__(self, parent: Any) -> None:
|
||||
self.__parent = parent
|
||||
|
||||
# -- pure virtuals
|
||||
|
||||
@abc.abstractmethod
|
||||
def _run(self, *args, **kwargs) -> QueryResult:
|
||||
raise Exception('Called pure virtual _run()')
|
||||
|
||||
@abc.abstractmethod
|
||||
def _register(self):
|
||||
raise Exception('Called pure virtual _register()')
|
||||
|
||||
@abc.abstractmethod
|
||||
def _column_names(self) -> list[str]:
|
||||
raise Exception('Called pure virtual _column()')
|
||||
|
||||
# -- used by Queries class
|
||||
|
||||
def register(self):
|
||||
return self._register()
|
||||
|
||||
# -- to be used
|
||||
|
||||
def _add(self, query_name: str, location: str, func: Any):
|
||||
return self.__parent.add(self, query_name, location, func)
|
||||
|
||||
def run(self, *args, **kwargs) -> QueryResult:
|
||||
return self._run(*args, **kwargs)
|
||||
|
||||
@property
|
||||
def parent(self):
|
||||
return self.__parent
|
||||
|
||||
@property
|
||||
def db(self) -> DataBase:
|
||||
return self.__parent.db
|
||||
|
||||
@property
|
||||
def schema(self):
|
||||
return self.__parent.db.schema
|
||||
|
||||
@property
|
||||
def app(self) -> Cmds:
|
||||
return self.__parent.app
|
||||
|
||||
@property
|
||||
def column_names(self) -> list[str]:
|
||||
return self._column_names()
|
||||
56
tools/python/jwutils/db/query/QueryResult.py
Normal file
56
tools/python/jwutils/db/query/QueryResult.py
Normal file
|
|
@ -0,0 +1,56 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
|
||||
from typing import Any, Union
|
||||
|
||||
import abc
|
||||
from enum import Enum, auto
|
||||
|
||||
from jwutils.log import *
|
||||
from jwutils.Cmds import Cmds
|
||||
from jwutils.db.DataBase import DataBase
|
||||
|
||||
class ResType(Enum): # export
|
||||
Statement = auto()
|
||||
Scalars = auto()
|
||||
One = auto()
|
||||
First = auto()
|
||||
Pages = auto()
|
||||
|
||||
class QueryResult(abc.ABC): # export
|
||||
|
||||
def __init__(self, query: Any) -> None:
|
||||
self.__query = query
|
||||
|
||||
@property
|
||||
def app(self) -> Cmds:
|
||||
return self.__query.app
|
||||
|
||||
@property
|
||||
def db(self) -> DataBase:
|
||||
return self.__query.db
|
||||
|
||||
@property
|
||||
def schema(self):
|
||||
return self.__query.db.schema
|
||||
|
||||
def rows(self) -> list[Any]:
|
||||
return self._cast(ResType.Scalars)
|
||||
|
||||
def pages(self, per_page=20) -> Any:
|
||||
return self._cast(ResType.Pages, per_page=per_page)
|
||||
|
||||
def one(self) -> Any:
|
||||
return self._cast(ResType.One)
|
||||
|
||||
def first(self) -> Any:
|
||||
return self._cast(ResType.First)
|
||||
|
||||
@property
|
||||
def statement(self) -> Any:
|
||||
return self._cast(ResType.Statement)
|
||||
|
||||
# -- pure virtuals
|
||||
|
||||
@abc.abstractmethod
|
||||
def _cast(self, res_type: ResType, **kwargs) -> Union[Any|list[Any]]:
|
||||
pass
|
||||
Loading…
Add table
Add a link
Reference in a new issue