Compare commits

...

2 Commits

Author SHA1 Message Date
58dbd3ed1e Cleanup for mysql
All checks were successful
Build on push / prepare (push) Successful in 8s
Build on push / core (push) Successful in 19s
Build on push / query (push) Successful in 18s
Build on push / translation (push) Successful in 15s
Build on push / mail (push) Successful in 17s
2025-09-16 20:21:33 +02:00
cd7dfaf2b4 Fixed spinner thread & remove log thread
All checks were successful
Build on push / prepare (push) Successful in 8s
Build on push / core (push) Successful in 18s
Build on push / query (push) Successful in 19s
Build on push / translation (push) Successful in 18s
Build on push / mail (push) Successful in 18s
2025-09-16 18:41:57 +02:00
33 changed files with 153 additions and 294 deletions

View File

@@ -1,6 +1,6 @@
from abc import ABC, abstractmethod
from cpl.dependency.service_collection_abc import ServiceCollectionABC
from cpl.dependency.service_collection import ServiceCollection
class AsyncStartupABC(ABC):
@@ -15,9 +15,9 @@ class AsyncStartupABC(ABC):
r"""Creates configuration of application"""
@abstractmethod
async def configure_services(self, service: ServiceCollectionABC):
async def configure_services(self, service: ServiceCollection):
r"""Creates service provider
Parameter:
services: :class:`cpl.dependency.service_collection_abc`
services: :class:`cpl.dependency.service_collection`
"""

View File

@@ -1,7 +1,7 @@
from abc import ABC, abstractmethod
from cpl.core.configuration.configuration import Configuration
from cpl.dependency.service_collection_abc import ServiceCollectionABC
from cpl.dependency.service_collection import ServiceCollection
from cpl.core.environment.environment import Environment
@@ -22,10 +22,10 @@ class AsyncStartupExtensionABC(ABC):
"""
@abstractmethod
async def configure_services(self, service: ServiceCollectionABC, env: Environment):
async def configure_services(self, service: ServiceCollection, env: Environment):
r"""Creates service provider
Parameter:
services: :class:`cpl.dependency.service_collection_abc`
services: :class:`cpl.dependency.service_collection`
env: :class:`cpl.core.environment.application_environment_abc`
"""

View File

@@ -1,7 +1,7 @@
from abc import ABC, abstractmethod
from cpl.core.configuration import Configuration
from cpl.dependency.service_collection_abc import ServiceCollectionABC
from cpl.dependency.service_collection import ServiceCollection
from cpl.core.environment import Environment
@@ -22,10 +22,10 @@ class StartupABC(ABC):
"""
@abstractmethod
def configure_services(self, service: ServiceCollectionABC, env: Environment):
def configure_services(self, service: ServiceCollection, env: Environment):
r"""Creates service provider
Parameter:
services: :class:`cpl.dependency.service_collection_abc`
services: :class:`cpl.dependency.service_collection`
env: :class:`cpl.core.environment.application_environment_abc`
"""

View File

@@ -2,7 +2,7 @@ from abc import ABC, abstractmethod
from cpl.core.configuration import Configuration
from cpl.dependency.service_collection_abc import ServiceCollectionABC
from cpl.dependency.service_collection import ServiceCollection
from cpl.core.environment.environment import Environment
@@ -24,10 +24,10 @@ class StartupExtensionABC(ABC):
"""
@abstractmethod
def configure_services(self, service: ServiceCollectionABC, env: Environment):
def configure_services(self, service: ServiceCollection, env: Environment):
r"""Creates service provider
Parameter:
services: :class:`cpl.dependency.service_collection_abc`
services: :class:`cpl.dependency.service_collection`
env: :class:`cpl.core.environment.application_environment_abc`
"""

View File

@@ -1,5 +1,4 @@
from .background_color_enum import BackgroundColorEnum
from .console import Console
from .console_call import ConsoleCall
from ._call import ConsoleCall
from .foreground_color_enum import ForegroundColorEnum
from .spinner_thread import SpinnerThread

View File

@@ -1,7 +1,8 @@
import os
import sys
import threading
import multiprocessing
import time
from multiprocessing import Process
from termcolor import colored
@@ -9,8 +10,8 @@ from cpl.core.console.background_color_enum import BackgroundColorEnum
from cpl.core.console.foreground_color_enum import ForegroundColorEnum
class SpinnerThread(threading.Thread):
r"""Thread to show spinner in terminal
class Spinner(Process):
r"""Process to show spinner in terminal
Parameter:
msg_len: :class:`int`
@@ -22,7 +23,7 @@ class SpinnerThread(threading.Thread):
"""
def __init__(self, msg_len: int, foreground_color: ForegroundColorEnum, background_color: BackgroundColorEnum):
threading.Thread.__init__(self)
Process.__init__(self)
self._msg_len = msg_len
self._foreground_color = foreground_color
@@ -50,29 +51,26 @@ class SpinnerThread(threading.Thread):
return color_args
def run(self) -> None:
r"""Entry point of thread, shows the spinner"""
r"""Entry point of process, shows the spinner"""
columns = 0
if sys.platform == "win32":
columns = os.get_terminal_size().columns
else:
term_rows, term_columns = os.popen("stty size", "r").read().split()
values = os.popen("stty size", "r").read().split()
term_rows, term_columns = values if len(values) == 2 else (0, 0)
columns = int(term_columns)
end_msg = "done"
end_msg_pos = columns - self._msg_len - len(end_msg)
if end_msg_pos > 0:
print(f'{"" : >{end_msg_pos}}', end="")
padding = columns - self._msg_len - len(end_msg)
if padding > 0:
print(f'{"" : >{padding}}', end="")
else:
print("", end="")
first = True
spinner = self._spinner()
while self._is_spinning:
if first:
first = False
print(colored(f"{next(spinner): >{len(end_msg) - 1}}", *self._get_color_args()), end="")
else:
print(colored(f"{next(spinner): >{len(end_msg)}}", *self._get_color_args()), end="")
print(colored(f"{next(spinner): >{len(end_msg)}}", *self._get_color_args()), end="")
time.sleep(0.1)
back = ""
for i in range(0, len(end_msg)):
@@ -84,9 +82,10 @@ class SpinnerThread(threading.Thread):
if not self._exit:
print(colored(end_msg, *self._get_color_args()), end="")
def stop_spinning(self):
def stop(self):
r"""Stops the spinner"""
self._is_spinning = False
super().terminate()
time.sleep(0.1)
def exit(self):

View File

@@ -10,9 +10,9 @@ from tabulate import tabulate
from termcolor import colored
from cpl.core.console.background_color_enum import BackgroundColorEnum
from cpl.core.console.console_call import ConsoleCall
from cpl.core.console._call import ConsoleCall
from cpl.core.console.foreground_color_enum import ForegroundColorEnum
from cpl.core.console.spinner_thread import SpinnerThread
from cpl.core.console._spinner import Spinner
class Console:
@@ -464,7 +464,7 @@ class Console:
cls.set_hold_back(True)
spinner = None
if not cls._disabled:
spinner = SpinnerThread(len(message), spinner_foreground_color, spinner_background_color)
spinner = Spinner(len(message), spinner_foreground_color, spinner_background_color)
spinner.start()
return_value = None
@@ -476,7 +476,7 @@ class Console:
cls.close()
if spinner is not None:
spinner.stop_spinning()
spinner.stop()
cls.set_hold_back(False)
cls.set_foreground_color(ForegroundColorEnum.default)

View File

@@ -1,92 +0,0 @@
import multiprocessing
import os
from datetime import datetime
from typing import Self
from cpl.core.console import Console
from cpl.core.log.log_level_enum import LogLevelEnum
class LogWriter:
_instance = None
# ANSI color codes for different log levels
_COLORS = {
LogLevelEnum.trace: "\033[37m", # Light Gray
LogLevelEnum.debug: "\033[94m", # Blue
LogLevelEnum.info: "\033[92m", # Green
LogLevelEnum.warning: "\033[93m", # Yellow
LogLevelEnum.error: "\033[91m", # Red
LogLevelEnum.fatal: "\033[95m", # Magenta
}
def __init__(self, file_prefix: str, level: LogLevelEnum = LogLevelEnum.info):
self._file_prefix = file_prefix
self._level = level
self._queue = multiprocessing.Queue()
self._process = multiprocessing.Process(target=self._log_worker, daemon=True)
self._create_log_dir()
self._process.start()
@property
def level(self) -> LogLevelEnum:
return self._level
@level.setter
def level(self, value: LogLevelEnum):
assert isinstance(value, LogLevelEnum), "Log level must be an instance of LogLevelEnum"
self._level = value
@classmethod
def get_instance(cls, file_prefix: str, level: LogLevelEnum = LogLevelEnum.info) -> Self:
if cls._instance is None:
cls._instance = LogWriter(file_prefix, level)
return cls._instance
@staticmethod
def _create_log_dir():
if os.path.exists("logs"):
return
os.makedirs("logs")
def _log_worker(self):
"""Worker process that writes log messages from the queue to the file."""
while True:
content = self._queue.get()
if content is None: # Shutdown signal
break
self._write_log_to_file(content)
Console.write_line(f"{self._COLORS.get(self._level, '\033[0m')}{content}\033[0m")
@property
def log_file(self):
return f"logs/{self._file_prefix}_{datetime.now().strftime('%Y-%m-%d')}.log"
def _ensure_file_size(self):
log_file = self.log_file
if not os.path.exists(log_file) or os.path.getsize(log_file) <= 0.5 * 1024 * 1024:
return
# if exists and size is greater than 300MB, create a new file
os.rename(
log_file,
f"{log_file.split('.log')[0]}_{datetime.now().strftime('%H-%M-%S')}.log",
)
def _write_log_to_file(self, content: str):
self._ensure_file_size()
with open(self.log_file, "a") as log_file:
log_file.write(content + "\n")
log_file.close()
def log(self, content: str):
"""Enqueue log message without blocking main app."""
self._queue.put(content)
def close(self):
"""Gracefully stop the logging process."""
self._queue.put(None)
self._process.join()

View File

@@ -3,7 +3,6 @@ import traceback
from datetime import datetime
from cpl.core.console import Console
from cpl.core.log._log_writer import LogWriter
from cpl.core.log.log_level_enum import LogLevelEnum
from cpl.core.log.logger_abc import LoggerABC
from cpl.core.typing import Messages, Source
@@ -13,6 +12,16 @@ class Logger(LoggerABC):
_level = LogLevelEnum.info
_levels = [x for x in LogLevelEnum]
# ANSI color codes for different log levels
_COLORS = {
LogLevelEnum.trace: "\033[37m", # Light Gray
LogLevelEnum.debug: "\033[94m", # Blue
LogLevelEnum.info: "\033[92m", # Green
LogLevelEnum.warning: "\033[93m", # Yellow
LogLevelEnum.error: "\033[91m", # Red
LogLevelEnum.fatal: "\033[95m", # Magenta
}
def __init__(self, source: Source, file_prefix: str = None):
LoggerABC.__init__(self)
assert source is not None and source != "", "Source cannot be None or empty"
@@ -22,7 +31,18 @@ class Logger(LoggerABC):
file_prefix = "app"
self._file_prefix = file_prefix
self._writer = LogWriter.get_instance(self._file_prefix)
self._create_log_dir()
@property
def log_file(self):
return f"logs/{self._file_prefix}_{datetime.now().strftime('%Y-%m-%d')}.log"
@staticmethod
def _create_log_dir():
if os.path.exists("logs"):
return
os.makedirs("logs")
@classmethod
def set_level(cls, level: LogLevelEnum):
@@ -31,6 +51,24 @@ class Logger(LoggerABC):
else:
raise ValueError(f"Invalid log level: {level}")
@staticmethod
def _ensure_file_size(log_file: str):
if not os.path.exists(log_file) or os.path.getsize(log_file) <= 0.5 * 1024 * 1024:
return
# if exists and size is greater than 300MB, create a new file
os.rename(
log_file,
f"{log_file.split('.log')[0]}_{datetime.now().strftime('%H-%M-%S')}.log",
)
def _write_log_to_file(self, content: str):
file = self.log_file
self._ensure_file_size(file)
with open(file, "a") as log_file:
log_file.write(content + "\n")
log_file.close()
def _log(self, level: LogLevelEnum, *messages: Messages):
try:
if self._levels.index(level) < self._levels.index(self._level):
@@ -39,7 +77,8 @@ class Logger(LoggerABC):
timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S.%f")
formatted_message = self._format_message(level.value, timestamp, *messages)
self._writer.log(formatted_message)
self._write_log_to_file(formatted_message)
Console.write_line(f"{self._COLORS.get(self._level, '\033[0m')}{formatted_message}\033[0m")
except Exception as e:
print(f"Error while logging: {e} -> {traceback.format_exc()}")

View File

@@ -1,3 +1,23 @@
from .database_settings_name_enum import DatabaseSettingsNameEnum
from cpl.dependency import ServiceCollection as _ServiceCollection
from . import mysql
from .database_settings import DatabaseSettings
from .database_settings_name_enum import DatabaseSettingsNameEnum
from .mysql.context import DatabaseContextABC, DatabaseContext
from .table_abc import TableABC
def add_mysql(collection: _ServiceCollection):
from cpl.core.console import Console
from cpl.core.configuration import Configuration
try:
collection.add_singleton(DatabaseContextABC, DatabaseContext)
database_context = collection.build_service_provider().get_service(DatabaseContextABC)
db_settings: DatabaseSettings = Configuration.get(DatabaseSettings)
database_context.connect(db_settings)
except ImportError as e:
Console.error("cpl-translation is not installed", str(e))
_ServiceCollection.with_module(add_mysql, mysql.__name__)

View File

@@ -4,7 +4,7 @@ import mysql.connector as sql
from mysql.connector.abstracts import MySQLConnectionAbstract
from mysql.connector.cursor import MySQLCursorBuffered
from cpl.database.connection.database_connection_abc import DatabaseConnectionABC
from cpl.database.mysql.connection.database_connection_abc import DatabaseConnectionABC
from cpl.database.database_settings import DatabaseSettings
from cpl.core.utils.credential_manager import CredentialManager

View File

@@ -1,9 +1,9 @@
from typing import Optional
from cpl.database.connection.database_connection import DatabaseConnection
from cpl.database.connection.database_connection_abc import DatabaseConnectionABC
from cpl.database.context.database_context_abc import DatabaseContextABC
from cpl.database.mysql.connection.database_connection import DatabaseConnection
from cpl.database.mysql.connection.database_connection_abc import DatabaseConnectionABC
from cpl.database.mysql.context.database_context_abc import DatabaseContextABC
from cpl.database.database_settings import DatabaseSettings
from mysql.connector.cursor import MySQLCursorBuffered

View File

@@ -1,7 +1,6 @@
from .scope import Scope
from .scope_abc import ScopeABC
from .service_collection import ServiceCollection
from .service_collection_abc import ServiceCollectionABC
from .service_descriptor import ServiceDescriptor
from .service_lifetime_enum import ServiceLifetimeEnum
from .service_provider import ServiceProvider

View File

@@ -1,24 +1,26 @@
from typing import Union, Type, Callable, Optional
from cpl.database.context.database_context_abc import DatabaseContextABC
from cpl.database.database_settings import DatabaseSettings
from cpl.dependency.service_collection_abc import ServiceCollectionABC
from cpl.dependency.service_descriptor import ServiceDescriptor
from cpl.dependency.service_lifetime_enum import ServiceLifetimeEnum
from cpl.dependency.service_provider import ServiceProvider
from cpl.dependency.service_provider_abc import ServiceProviderABC
from cpl.core.log.logger import Logger
from cpl.core.log.logger_abc import LoggerABC
from cpl.core.pipes.pipe_abc import PipeABC
from cpl.core.typing import T, Service
from cpl.dependency.service_descriptor import ServiceDescriptor
from cpl.dependency.service_lifetime_enum import ServiceLifetimeEnum
from cpl.dependency.service_provider import ServiceProvider
from cpl.dependency.service_provider_abc import ServiceProviderABC
class ServiceCollection(ServiceCollectionABC):
class ServiceCollection:
r"""Representation of the collection of services"""
_modules: dict[str, Callable] = {}
@classmethod
def with_module(cls, func: Callable, name: str = None):
cls._modules[func.__name__ if name is None else name] = func
return cls
def __init__(self):
ServiceCollectionABC.__init__(self)
self._database_context: Optional[DatabaseContextABC] = None
self._service_descriptors: list[ServiceDescriptor] = []
def _add_descriptor(self, service: Union[type, object], lifetime: ServiceLifetimeEnum, base_type: Callable = None):
@@ -44,10 +46,19 @@ class ServiceCollection(ServiceCollectionABC):
return self
def add_db_context(self, db_context_type: Type[DatabaseContextABC], db_settings: DatabaseSettings):
self.add_singleton(DatabaseContextABC, db_context_type)
self._database_context = self.build_service_provider().get_service(DatabaseContextABC)
self._database_context.connect(db_settings)
def add_module(self, module: str | object):
if not isinstance(module, str):
module = module.__name__
if module not in self._modules:
raise ValueError(f"Module {module} not found")
self._modules[module](self)
# def add_mysql(self, db_context_type: Type[DatabaseContextABC], db_settings: DatabaseSettings):
# self.add_singleton(DatabaseContextABC, db_context_type)
# self._database_context = self.build_service_provider().get_service(DatabaseContextABC)
# self._database_context.connect(db_settings)
def add_logging(self):
self.add_transient(LoggerABC, Logger)
@@ -71,6 +82,6 @@ class ServiceCollection(ServiceCollectionABC):
return self
def build_service_provider(self) -> ServiceProviderABC:
sp = ServiceProvider(self._service_descriptors, self._database_context)
sp = ServiceProvider(self._service_descriptors)
ServiceProviderABC.set_global_provider(sp)
return sp

View File

@@ -1,90 +0,0 @@
from abc import abstractmethod, ABC
from typing import Type
from cpl.database.context.database_context_abc import DatabaseContextABC
from cpl.database.database_settings import DatabaseSettings
from cpl.dependency.service_provider_abc import ServiceProviderABC
from cpl.core.typing import T, Source
class ServiceCollectionABC(ABC):
r"""ABC for the class :class:`cpl.dependency.service_collection.ServiceCollection`"""
@abstractmethod
def __init__(self):
pass
@abstractmethod
def add_db_context(self, db_context_type: Type[DatabaseContextABC], db_settings: DatabaseSettings):
r"""Adds database context
Parameter:
db_context: Type[:class:`cpl.database.context.database_context_abc.DatabaseContextABC`]
Database context
"""
@abstractmethod
def add_logging(self):
r"""Adds the CPL internal logger"""
@abstractmethod
def add_pipes(self):
r"""Adds the CPL internal pipes as transient"""
def add_translation(self):
r"""Adds the CPL translation"""
raise NotImplementedError("You should install and use the cpl-translation package")
def add_mail(self):
r"""Adds the CPL mail"""
raise NotImplementedError("You should install and use the cpl-mail package")
@abstractmethod
def add_transient(self, service_type: T, service: T = None) -> "ServiceCollectionABC":
r"""Adds a service with transient lifetime
Parameter:
service_type: :class:`Type`
Type of the service
service: :class:`Callable`
Object of the service
Returns:
self: :class:`cpl.dependency.service_collection_abc.ServiceCollectionABC`
"""
@abstractmethod
def add_scoped(self, service_type: T, service: T = None) -> "ServiceCollectionABC":
r"""Adds a service with scoped lifetime
Parameter:
service_type: :class:`Type`
Type of the service
service: :class:`Callable`
Object of the service
Returns:
self: :class:`cpl.dependency.service_collection_abc.ServiceCollectionABC`
"""
@abstractmethod
def add_singleton(self, service_type: T, service: T = None) -> "ServiceCollectionABC":
r"""Adds a service with singleton lifetime
Parameter:
service_type: :class:`Type`
Type of the service
service: :class:`Callable`
Object of the service
Returns:
self: :class:`cpl.dependency.service_collection_abc.ServiceCollectionABC`
"""
@abstractmethod
def build_service_provider(self) -> ServiceProviderABC:
r"""Creates instance of the service provider
Returns:
Object of type :class:`cpl.dependency.service_provider_abc.ServiceProviderABC`
"""

View File

@@ -5,7 +5,6 @@ from typing import Optional
from cpl.core.configuration import Configuration
from cpl.core.configuration.configuration_model_abc import ConfigurationModelABC
from cpl.database.context.database_context_abc import DatabaseContextABC
from cpl.core.environment import Environment
from cpl.core.typing import T, R, Source
from cpl.dependency.scope_abc import ScopeABC
@@ -31,12 +30,10 @@ class ServiceProvider(ServiceProviderABC):
def __init__(
self,
service_descriptors: list[ServiceDescriptor],
db_context: Optional[DatabaseContextABC],
):
ServiceProviderABC.__init__(self)
self._service_descriptors: list[ServiceDescriptor] = service_descriptors
self._database_context = db_context
self._scope: Optional[ScopeABC] = None
def _find_service(self, service_type: type) -> Optional[ServiceDescriptor]:
@@ -95,9 +92,6 @@ class ServiceProvider(ServiceProviderABC):
elif issubclass(parameter.annotation, Environment):
params.append(Environment)
elif issubclass(parameter.annotation, DatabaseContextABC):
params.append(self._database_context)
elif issubclass(parameter.annotation, ConfigurationModelABC):
params.append(Configuration.get(parameter.annotation))

View File

@@ -1,3 +1,4 @@
from cpl.dependency import ServiceCollection as _ServiceCollection
from .abc.email_client_abc import EMailClientABC
from .email_client import EMailClient
from .email_client_settings import EMailClientSettings
@@ -6,21 +7,15 @@ from .email_model import EMail
from .mail_logger import MailLogger
def add_mail(self):
def add_mail(collection: _ServiceCollection):
from cpl.core.console import Console
from cpl.core.log import LoggerABC
try:
self.add_singleton(EMailClientABC, EMailClient)
self.add_transient(LoggerABC, MailLogger)
collection.add_singleton(EMailClientABC, EMailClient)
collection.add_transient(LoggerABC, MailLogger)
except ImportError as e:
Console.error("cpl-translation is not installed", str(e))
def init():
from cpl.dependency import ServiceCollection
ServiceCollection.add_mail = add_mail
init()
_ServiceCollection.with_module(add_mail, __name__)

View File

@@ -1,10 +1,11 @@
from cpl.dependency import ServiceCollection as _ServiceCollection
from .translate_pipe import TranslatePipe
from .translation_service import TranslationService
from .translation_service_abc import TranslationServiceABC
from .translation_settings import TranslationSettings
def add_translation(self):
def add_translation(collection: _ServiceCollection):
from cpl.core.console import Console
from cpl.core.pipes import PipeABC
from cpl.translation.translate_pipe import TranslatePipe
@@ -12,16 +13,10 @@ def add_translation(self):
from cpl.translation.translation_service_abc import TranslationServiceABC
try:
self.add_singleton(TranslationServiceABC, TranslationService)
self.add_transient(PipeABC, TranslatePipe)
collection.add_singleton(TranslationServiceABC, TranslationService)
collection.add_transient(PipeABC, TranslatePipe)
except ImportError as e:
Console.error("cpl-translation is not installed", str(e))
def init():
from cpl.dependency import ServiceCollection
ServiceCollection.add_translation = add_translation
init()
_ServiceCollection.with_module(add_translation, __name__)

View File

@@ -1,6 +1,6 @@
from cpl.application.async_startup_abc import AsyncStartupABC
from cpl.core.configuration import ConfigurationABC
from cpl.dependency import ServiceProviderABC, ServiceCollectionABC
from cpl.dependency import ServiceProviderABC, ServiceCollection
from cpl.core.environment import Environment
@@ -13,5 +13,5 @@ class Startup(AsyncStartupABC):
) -> ConfigurationABC:
return configuration
async def configure_services(self, services: ServiceCollectionABC, environment: Environment) -> ServiceProviderABC:
async def configure_services(self, services: ServiceCollection, environment: Environment) -> ServiceProviderABC:
return services.build_service_provider()

View File

@@ -25,6 +25,7 @@ if __name__ == "__main__":
Console.spinner(
"Test:", test_spinner, spinner_foreground_color=ForegroundColorEnum.cyan, text_foreground_color="green"
)
Console.write_line("HOLD BACK")
# opts = [
# 'Option 1',
# 'Option 2',

View File

@@ -1,7 +0,0 @@
from cpl.database import DatabaseSettings
from cpl.database.context import DatabaseContext
class DBContext(DatabaseContext):
def __init__(self):
DatabaseContext.__init__(self)

View File

@@ -1,5 +1,5 @@
from cpl.core.console import Console
from cpl.database.context import DatabaseContextABC
from cpl.database.mysql.context import DatabaseContextABC
from .city_model import CityModel
from .user_model import UserModel

View File

@@ -1,11 +1,9 @@
from cpl.application import StartupABC
from cpl.core.configuration import Configuration
from cpl.database import DatabaseSettings
from cpl.dependency import ServiceCollectionABC, ServiceProviderABC
from cpl.core.environment import Environment
from cpl.core.log import Logger, LoggerABC
from model.db_context import DBContext
from cpl.database import mysql
from cpl.dependency import ServiceCollection
from model.user_repo import UserRepo
from model.user_repo_abc import UserRepoABC
@@ -23,11 +21,8 @@ class Startup(StartupABC):
self._configuration = configuration
def configure_services(self, services: ServiceCollectionABC, environment: Environment):
# Create and connect to database
db_settings: DatabaseSettings = self._configuration.get(DatabaseSettings)
services.add_db_context(DBContext, db_settings)
def configure_services(self, services: ServiceCollection, environment: Environment):
services.add_module(mysql)
services.add_singleton(UserRepoABC, UserRepo)
services.add_singleton(LoggerABC, Logger)

View File

@@ -1,6 +1,6 @@
from cpl.application import StartupABC
from cpl.core.configuration import ConfigurationABC
from cpl.dependency import ServiceProviderABC, ServiceCollectionABC
from cpl.dependency import ServiceProviderABC, ServiceCollection
from cpl.core.environment import Environment
from di.test1_service import Test1Service
from di.test2_service import Test2Service
@@ -17,7 +17,7 @@ class Startup(StartupABC):
def configure_configuration(self, configuration: ConfigurationABC, environment: Environment) -> ConfigurationABC:
return configuration
def configure_services(self, services: ServiceCollectionABC, environment: Environment) -> ServiceProviderABC:
def configure_services(self, services: ServiceCollection, environment: Environment) -> ServiceProviderABC:
services.add_scoped(TestService)
services.add_scoped(DITesterService)

View File

@@ -1,6 +1,7 @@
from cpl import mail
from cpl.application import StartupABC
from cpl.core.configuration import Configuration
from cpl.dependency import ServiceCollectionABC, ServiceProviderABC
from cpl.dependency import ServiceCollection, ServiceProviderABC
from cpl.core.environment import Environment
from cpl.core.pipes import IPAddressPipe
from test_service import TestService
@@ -15,8 +16,8 @@ class Startup(StartupABC):
config.add_json_file(f"appsettings.{env.get_environment()}.json")
config.add_json_file(f"appsettings.{env.get_host_name()}.json", optional=True)
def configure_services(self, services: ServiceCollectionABC, env: Environment):
def configure_services(self, services: ServiceCollection, env: Environment):
services.add_logging()
services.add_mail()
services.add_module(mail)
services.add_transient(IPAddressPipe)
services.add_singleton(TestService)

View File

@@ -1,7 +1,7 @@
from cpl.application import StartupExtensionABC
from cpl.core.configuration import Configuration
from cpl.core.console import Console
from cpl.dependency import ServiceCollectionABC
from cpl.dependency import ServiceCollection
from cpl.core.environment import Environment
@@ -12,5 +12,5 @@ class TestStartupExtension(StartupExtensionABC):
def configure_configuration(self, config: Configuration, env: Environment):
Console.write_line("config")
def configure_services(self, services: ServiceCollectionABC, env: Environment):
def configure_services(self, services: ServiceCollection, env: Environment):
Console.write_line("services")

View File

@@ -1,6 +1,6 @@
from cpl.application import StartupABC
from cpl.core.configuration import ConfigurationABC
from cpl.dependency import ServiceProviderABC, ServiceCollectionABC
from cpl.dependency import ServiceProviderABC, ServiceCollection
from cpl.core.environment import Environment
@@ -12,6 +12,6 @@ class Startup(StartupABC):
configuration.add_json_file("appsettings.json")
return configuration
def configure_services(self, services: ServiceCollectionABC, environment: Environment) -> ServiceProviderABC:
def configure_services(self, services: ServiceCollection, environment: Environment) -> ServiceProviderABC:
services.add_translation()
return services.build_service_provider()