Adding some comments, editing methods names

This commit is contained in:
adator85
2025-08-15 15:47:01 +02:00
parent 21a2619f49
commit 6b22d786e3
25 changed files with 344 additions and 233 deletions

View File

@@ -11,40 +11,42 @@ import logging
import threading
import ipaddress
import ast
import requests
from pathlib import Path
from types import ModuleType
import requests
from dataclasses import fields
from typing import Union, TYPE_CHECKING
from typing import Any, Optional, TYPE_CHECKING
from base64 import b64decode, b64encode
from datetime import datetime, timedelta, timezone
from sqlalchemy import create_engine, Engine, Connection, CursorResult
from sqlalchemy.sql import text
from core.definition import MConfig
if TYPE_CHECKING:
from core.classes.settings import Settings
from core.loader import Loader
class Base:
def __init__(self, Config: MConfig, settings: 'Settings') -> None:
def __init__(self, loader: 'Loader') -> None:
self.Loader = loader
self.Config = loader.Config
self.Settings = loader.Settings
self.Utils = loader.Utils
self.Config = Config # Assigner l'objet de configuration
self.Settings: Settings = settings
self.init_log_system() # Demarrer le systeme de log
self.check_for_new_version(True) # Verifier si une nouvelle version est disponible
# Liste des timers en cours
self.running_timers:list[threading.Timer] = self.Settings.RUNNING_TIMERS
self.running_timers: list[threading.Timer] = self.Settings.RUNNING_TIMERS
# Liste des threads en cours
self.running_threads:list[threading.Thread] = self.Settings.RUNNING_THREADS
self.running_threads: list[threading.Thread] = self.Settings.RUNNING_THREADS
# Les sockets ouvert
self.running_sockets: list[socket.socket] = self.Settings.RUNNING_SOCKETS
# Liste des fonctions en attentes
self.periodic_func:dict[object] = self.Settings.PERIODIC_FUNC
self.periodic_func: dict[object] = self.Settings.PERIODIC_FUNC
# Création du lock
self.lock = self.Settings.LOCK
@@ -150,13 +152,6 @@ class Base:
return unixtime
def get_datetime(self) -> str:
"""
Retourne une date au format string (24-12-2023 20:50:59)
"""
currentdate = datetime.now().strftime('%d-%m-%Y %H:%M:%S')
return currentdate
def get_all_modules(self) -> list[str]:
"""Get list of all main modules
using this pattern mod_*.py
@@ -190,20 +185,20 @@ class Base:
importlib.reload(module)
self.logs.debug(f'[LOAD_MODULE] Module {module} success')
except Exception:
self.logs.error(f'[LOAD_MODULE] Module {module} failed [!]')
except Exception as err:
self.logs.error(f'[LOAD_MODULE] Module {module} failed [!] - {err}')
def create_log(self, log_message: str) -> None:
"""Enregiste les logs
Args:
string (str): Le message a enregistrer
log_message (str): Le message a enregistrer
Returns:
None: Aucun retour
"""
sql_insert = f"INSERT INTO {self.Config.TABLE_LOG} (datetime, server_msg) VALUES (:datetime, :server_msg)"
mes_donnees = {'datetime': str(self.get_datetime()),'server_msg': f'{log_message}'}
mes_donnees = {'datetime': str(self.Utils.get_sdatetime()),'server_msg': f'{log_message}'}
self.db_execute_query(sql_insert, mes_donnees)
return None
@@ -247,13 +242,14 @@ class Base:
def replace_filter(self, record: logging.LogRecord) -> bool:
response = True
filter: list[str] = ['PING', f":{self.Config.SERVICE_PREFIX}auth"]
filters: list[str] = ['PING',
f':{self.Config.SERVICE_PREFIX}auth']
# record.msg = record.getMessage().replace("PING", "[REDACTED]")
if self.Settings.CONSOLE:
print(record.getMessage())
for f in filter:
for f in filters:
if f in record.getMessage():
response = False
@@ -274,10 +270,11 @@ class Base:
return None
def log_cmd(self, user_cmd:str, cmd:str) -> None:
def log_cmd(self, user_cmd: str, cmd: str) -> None:
"""Enregistre les commandes envoyées par les utilisateurs
Args:
user_cmd (str): The user who performed the command
cmd (str): la commande a enregistrer
"""
cmd_list = cmd.split()
@@ -288,10 +285,10 @@ class Base:
cmd = ' '.join(cmd_list)
insert_cmd_query = f"INSERT INTO {self.Config.TABLE_COMMAND} (datetime, user, commande) VALUES (:datetime, :user, :commande)"
mes_donnees = {'datetime': self.get_datetime(), 'user': user_cmd, 'commande': cmd}
mes_donnees = {'datetime': self.Utils.get_sdatetime(), 'user': user_cmd, 'commande': cmd}
self.db_execute_query(insert_cmd_query, mes_donnees)
return False
return None
def db_isModuleExist(self, module_name:str) -> bool:
"""Teste si un module existe déja dans la base de données
@@ -311,22 +308,24 @@ class Base:
else:
return False
def db_record_module(self, user_cmd:str, module_name:str, isdefault:int = 0) -> None:
def db_record_module(self, user_cmd: str, module_name: str, isdefault: int = 0) -> None:
"""Enregistre les modules dans la base de données
Args:
cmd (str): le module a enregistrer
user_cmd (str): The user who performed the command
module_name (str): The module name
isdefault (int): Is this a default module. Default 0
"""
if not self.db_isModuleExist(module_name):
self.logs.debug(f"Le module {module_name} n'existe pas alors ont le créer")
insert_cmd_query = f"INSERT INTO {self.Config.TABLE_MODULE} (datetime, user, module_name, isdefault) VALUES (:datetime, :user, :module_name, :isdefault)"
mes_donnees = {'datetime': self.get_datetime(), 'user': user_cmd, 'module_name': module_name, 'isdefault': isdefault}
mes_donnees = {'datetime': self.Utils.get_sdatetime(), 'user': user_cmd, 'module_name': module_name, 'isdefault': isdefault}
self.db_execute_query(insert_cmd_query, mes_donnees)
else:
self.logs.debug(f"Le module {module_name} existe déja dans la base de données")
return False
return None
def db_update_module(self, user_cmd: str, module_name: str) -> None:
"""Modifie la date et le user qui a rechargé le module
@@ -336,22 +335,22 @@ class Base:
module_name (str): le module a rechargé
"""
update_cmd_query = f"UPDATE {self.Config.TABLE_MODULE} SET datetime = :datetime, user = :user WHERE module_name = :module_name"
mes_donnees = {'datetime': self.get_datetime(), 'user': user_cmd, 'module_name': module_name}
mes_donnees = {'datetime': self.Utils.get_sdatetime(), 'user': user_cmd, 'module_name': module_name}
self.db_execute_query(update_cmd_query, mes_donnees)
return False
return None
def db_delete_module(self, module_name:str) -> None:
"""Supprime les modules de la base de données
Args:
cmd (str): le module a supprimer
module_name (str): The module name you want to delete
"""
insert_cmd_query = f"DELETE FROM {self.Config.TABLE_MODULE} WHERE module_name = :module_name"
mes_donnees = {'module_name': module_name}
self.db_execute_query(insert_cmd_query, mes_donnees)
return False
return None
def db_sync_core_config(self, module_name: str, dataclassObj: object) -> bool:
"""Sync module local parameters with the database
@@ -369,7 +368,7 @@ class Base:
"""
try:
response = True
current_date = self.get_datetime()
current_date = self.Utils.get_sdatetime()
core_table = self.Config.TABLE_CONFIG
# Add local parameters to DB
@@ -446,7 +445,7 @@ class Base:
isParamExist = result.fetchone()
if not isParamExist is None:
mes_donnees = {'datetime': self.get_datetime(),
mes_donnees = {'datetime': self.Utils.get_sdatetime(),
'module_name': module_name,
'param_key': param_key,
'param_value': param_value
@@ -471,9 +470,9 @@ class Base:
user = self.db_execute_query(f"SELECT id FROM {self.Config.TABLE_ADMIN}")
if not user.fetchall():
admin = self.Config.OWNER
password = self.crypt_password(self.Config.PASSWORD)
password = self.Utils.hash_password(self.Config.PASSWORD)
mes_donnees = {'createdOn': self.get_datetime(),
mes_donnees = {'createdOn': self.Utils.get_sdatetime(),
'user': admin,
'password': password,
'hostname': '*',
@@ -500,8 +499,11 @@ class Base:
self.logs.debug(f"-- Timer ID : {str(t.ident)} | Running Threads : {len(threading.enumerate())}")
return None
except AssertionError as ae:
self.logs.error(f'Assertion Error -> {ae}')
return None
def create_thread(self, func:object, func_args: tuple = (), run_once:bool = False, daemon: bool = True) -> None:
"""Create a new thread and store it into running_threads variable
@@ -737,19 +739,6 @@ class Base:
except AttributeError as ae:
self.logs.error(f"Attribute Error : {ae}")
def crypt_password(self, password:str) -> str:
"""Retourne un mot de passe chiffré en MD5
Args:
password (str): Le password en clair
Returns:
str: Le password en MD5
"""
md5_password = hashlib.md5(password.encode()).hexdigest()
return md5_password
def int_if_possible(self, value):
"""Convertit la valeur reçue en entier, si possible.
Sinon elle retourne la valeur initiale.
@@ -768,14 +757,14 @@ class Base:
except TypeError:
return value
def convert_to_int(self, value: any) -> Union[int, None]:
def convert_to_int(self, value: Any) -> Optional[int]:
"""Convert a value to int
Args:
value (any): Value to convert to int if possible
Returns:
Union[int, None]: Return the int value or None if not possible
int: Return the int value or None if not possible
"""
try:
response = int(value)
@@ -816,7 +805,7 @@ class Base:
self.logs.error(f'General Error: {err}')
return False
def decode_ip(self, ip_b64encoded: str) -> Union[str, None]:
def decode_ip(self, ip_b64encoded: str) -> Optional[str]:
binary_ip = b64decode(ip_b64encoded)
try:
@@ -827,7 +816,7 @@ class Base:
self.logs.critical(f'This remote ip is not valid : {ve}')
return None
def encode_ip(self, remote_ip_address: str) -> Union[str, None]:
def encode_ip(self, remote_ip_address: str) -> Optional[str]:
binary_ip = socket.inet_aton(remote_ip_address)
try:
@@ -890,7 +879,7 @@ class Base:
self.logs.debug(f'Method to execute : {str(self.periodic_func)}')
return None
def clean_uid(self, uid:str) -> Union[str, None]:
def clean_uid(self, uid:str) -> Optional[str]:
"""Clean UID by removing @ / % / + / ~ / * / :
Args:

View File

@@ -3,7 +3,7 @@ from typing import Any, Optional, Literal, TYPE_CHECKING
if TYPE_CHECKING:
from core.definition import MChannel
from core.base import Base
from core.loader import Loader
class Channel:
@@ -11,10 +11,11 @@ class Channel:
"""List that contains all the Channels objects (ChannelModel)
"""
def __init__(self, base: 'Base') -> None:
def __init__(self, loader: 'Loader') -> None:
self.Logs = base.logs
self.Base = base
self.Logs = loader.Base.logs
self.Base = loader.Base
self.Utils = loader.Utils
return None
@@ -22,7 +23,7 @@ class Channel:
"""This method will insert a new channel and if the channel exist it will update the user list (uids)
Args:
newChan (ChannelModel): The channel model object
new_channel (MChannel): The channel model object
Returns:
bool: True if new channel, False if channel exist (However UID could be updated)
@@ -30,7 +31,7 @@ class Channel:
result = False
exist = False
if not self.Is_Channel(new_channel.name):
if not self.is_valid_channel(new_channel.name):
self.Logs.error(f"The channel {new_channel.name} is not valid, channel must start with #")
return False
@@ -64,8 +65,16 @@ class Channel:
return result
def delete(self, channel_name: str) -> bool:
"""Delete channel from the UID_CHANNEL_DB
chan_obj = self.get_Channel(channel_name)
Args:
channel_name (str): The Channel name
Returns:
bool: True if it was deleted
"""
chan_obj = self.get_channel(channel_name)
if chan_obj is None:
return False
@@ -75,10 +84,19 @@ class Channel:
return True
def delete_user_from_channel(self, channel_name: str, uid:str) -> bool:
"""Delete a user from a channel
Args:
channel_name (str): The channel name
uid (str): The Client UID
Returns:
bool: True if the client has been deleted from the channel
"""
try:
result = False
chan_obj = self.get_Channel(channel_name.lower())
chan_obj = self.get_channel(channel_name.lower())
if chan_obj is None:
return result
@@ -95,6 +113,14 @@ class Channel:
self.Logs.error(f'{ve}')
def delete_user_from_all_channel(self, uid:str) -> bool:
"""Delete a client from all channels
Args:
uid (str): The client UID
Returns:
bool: True if the client has been deleted from all channels
"""
try:
result = False
@@ -111,14 +137,22 @@ class Channel:
self.Logs.error(f'{ve}')
def add_user_to_a_channel(self, channel_name: str, uid: str) -> bool:
"""Add a client to a channel
Args:
channel_name (str): The channel name
uid (str): The client UID
Returns:
bool: True is the clien has been added
"""
try:
result = False
chan_obj = self.get_Channel(channel_name)
self.Logs.debug(f"** {__name__}")
chan_obj = self.get_channel(channel_name)
if chan_obj is None:
result = self.insert(MChannel(channel_name, uids=[uid]))
return result
# Create a new channel if the channel don't exist
self.Logs.debug(f"New channel will be created ({channel_name} - {uid})")
return self.insert(MChannel(channel_name, uids=[uid]))
chan_obj.uids.append(uid)
del_duplicates = list(set(chan_obj.uids))
@@ -127,18 +161,19 @@ class Channel:
return True
except Exception as err:
self.Logs.error(f'{err}')
return False
def is_user_present_in_channel(self, channel_name: str, uid: str) -> bool:
"""Check if a user is present in the channel
Args:
channel_name (str): The channel to check
uid (str): The UID
channel_name (str): The channel name to check
uid (str): The client UID
Returns:
bool: True if the user is present in the channel
"""
chan = self.get_Channel(channel_name=channel_name)
chan = self.get_channel(channel_name=channel_name)
if chan is None:
return False
@@ -150,7 +185,7 @@ class Channel:
return False
def clean_channel(self) -> None:
"""Remove Channels if empty
"""If channel doesn't contain any client this method will remove the channel
"""
try:
for record in self.UID_CHANNEL_DB:
@@ -161,25 +196,33 @@ class Channel:
except Exception as err:
self.Logs.error(f'{err}')
def get_Channel(self, channel_name: str) -> Optional['MChannel']:
def get_channel(self, channel_name: str) -> Optional['MChannel']:
"""Get the channel object
Args:
channel_name (str): The Channel name
Returns:
MChannel: The channel object model if exist else None
"""
for record in self.UID_CHANNEL_DB:
if record.name == channel_name:
if record.name.lower() == channel_name.lower():
return record
return None
def get_channel_asdict(self, chan_name: str) -> Optional[dict[str, Any]]:
def get_channel_asdict(self, channel_name: str) -> Optional[dict[str, Any]]:
channel_obj: Optional['MChannel'] = self.get_Channel(chan_name)
channel_obj: Optional['MChannel'] = self.get_channel(channel_name)
if channel_obj is None:
return None
return channel_obj.to_dict()
def Is_Channel(self, channel_to_check: str) -> bool:
"""Check if the string has the # caractere and return True if this is a channel
def is_valid_channel(self, channel_to_check: str) -> bool:
"""Check if the string has the # caractere and return True if this is a valid channel
Args:
channel_to_check (str): The string to test if it is a channel or not
@@ -216,7 +259,7 @@ class Channel:
bool: True if action done
"""
try:
channel_name = channel_name.lower() if self.Is_Channel(channel_name) else None
channel_name = channel_name.lower() if self.is_valid_channel(channel_name) else None
core_table = self.Base.Config.TABLE_CHANNEL
if not channel_name:
@@ -231,7 +274,7 @@ class Channel:
is_channel_exist = response.fetchone()
if is_channel_exist is None:
mes_donnees = {'datetime': self.Base.get_datetime(), 'channel_name': channel_name, 'module_name': module_name}
mes_donnees = {'datetime': self.Utils.get_sdatetime(), 'channel_name': channel_name, 'module_name': module_name}
insert = self.Base.db_execute_query(f"INSERT INTO {core_table} (datetime, channel_name, module_name) VALUES (:datetime, :channel_name, :module_name)", mes_donnees)
if insert.rowcount:
self.Logs.debug(f'New channel added: channel={channel_name} / module_name={module_name}')

View File

@@ -14,6 +14,7 @@ class Inspircd:
self.__Irc = ircInstance
self.__Config = ircInstance.Config
self.__Base = ircInstance.Base
self.__Utils = ircInstance.Loader.Utils
self.__Base.logs.info(f"** Loading protocol [{__name__}]")
@@ -169,7 +170,7 @@ class Inspircd:
def sjoin(self, channel: str) -> None:
if not self.__Irc.Channel.Is_Channel(channel):
if not self.__Irc.Channel.is_valid_channel(channel):
self.__Base.logs.error(f"The channel [{channel}] is not valid")
return None
@@ -259,7 +260,7 @@ class Inspircd:
if userObj is None:
return None
if not self.__Irc.Channel.Is_Channel(channel):
if not self.__Irc.Channel.is_valid_channel(channel):
self.__Base.logs.error(f"The channel [{channel}] is not valid")
return None
@@ -284,7 +285,7 @@ class Inspircd:
self.__Base.logs.error(f"The user [{uidornickname}] is not valid")
return None
if not self.__Irc.Channel.Is_Channel(channel):
if not self.__Irc.Channel.is_valid_channel(channel):
self.__Base.logs.error(f"The channel [{channel}] is not valid")
return None
@@ -600,7 +601,7 @@ class Inspircd:
nickname = self.__Irc.User.get_nickname(self.__Base.clean_uid(serverMsg[1]))
dnickname = self.__Config.SERVICE_NICKNAME
arg = serverMsg[4].replace(':', '')
current_datetime = self.__Base.get_datetime()
current_datetime = self.__Utils.get_sdatetime()
if nickname is None:
return None

View File

@@ -16,6 +16,7 @@ class Unrealircd6:
self.__Config = ircInstance.Config
self.__Base = ircInstance.Base
self.__Settings = ircInstance.Base.Settings
self.__Utils = ircInstance.Loader.Utils
self.known_protocol: set[str] = {'SJOIN', 'UID', 'MD', 'QUIT', 'SQUIT',
'EOS', 'PRIVMSG', 'MODE', 'UMODE2',
@@ -242,7 +243,7 @@ class Unrealircd6:
Args:
channel (str): Channel to join
"""
if not self.__Irc.Channel.Is_Channel(channel):
if not self.__Irc.Channel.is_valid_channel(channel):
self.__Base.logs.error(f"The channel [{channel}] is not valid")
return None
@@ -264,7 +265,7 @@ class Unrealircd6:
try:
userObj = self.__Irc.User.get_User(uidornickname=nick_to_sapart)
chanObj = self.__Irc.Channel.get_Channel(channel_name)
chanObj = self.__Irc.Channel.get_channel(channel_name)
service_uid = self.__Config.SERVICE_ID
if userObj is None or chanObj is None:
@@ -288,7 +289,7 @@ class Unrealircd6:
try:
userObj = self.__Irc.User.get_User(uidornickname=nick_to_sajoin)
chanObj = self.__Irc.Channel.get_Channel(channel_name)
chanObj = self.__Irc.Channel.get_channel(channel_name)
service_uid = self.__Config.SERVICE_ID
if userObj is None:
@@ -297,7 +298,7 @@ class Unrealircd6:
if chanObj is None:
# Channel not exist
if not self.__Irc.Channel.Is_Channel(channel_name):
if not self.__Irc.Channel.is_valid_channel(channel_name):
# Incorrect channel: leave
return None
@@ -412,7 +413,7 @@ class Unrealircd6:
if userObj is None:
return None
if not self.__Irc.Channel.Is_Channel(channel):
if not self.__Irc.Channel.is_valid_channel(channel):
self.__Base.logs.error(f"The channel [{channel}] is not valid")
return None
@@ -452,7 +453,7 @@ class Unrealircd6:
self.__Base.logs.error(f"The user [{uidornickname}] is not valid")
return None
if not self.__Irc.Channel.Is_Channel(channel):
if not self.__Irc.Channel.is_valid_channel(channel):
self.__Base.logs.error(f"The channel [{channel}] is not valid")
return None
@@ -464,7 +465,7 @@ class Unrealircd6:
def send_mode_chan(self, channel_name: str, channel_mode: str) -> None:
channel = self.__Irc.Channel.Is_Channel(channel_name)
channel = self.__Irc.Channel.is_valid_channel(channel_name)
if not channel:
self.__Base.logs.error(f'The channel [{channel_name}] is not correct')
return None
@@ -939,7 +940,7 @@ class Unrealircd6:
cmd_to_send = convert_to_string.replace(':','')
self.__Base.log_cmd(user_trigger, cmd_to_send)
fromchannel = str(cmd[2]).lower() if self.__Irc.Channel.Is_Channel(cmd[2]) else None
fromchannel = str(cmd[2]).lower() if self.__Irc.Channel.is_valid_channel(cmd[2]) else None
self.__Irc.hcmds(user_trigger, fromchannel, arg, cmd)
if cmd[2] == self.__Config.SERVICE_ID:
@@ -975,7 +976,7 @@ class Unrealircd6:
fromchannel = None
if len(arg) >= 2:
fromchannel = str(arg[1]).lower() if self.__Irc.Channel.Is_Channel(arg[1]) else None
fromchannel = str(arg[1]).lower() if self.__Irc.Channel.is_valid_channel(arg[1]) else None
self.__Irc.hcmds(user_trigger, fromchannel, arg, cmd)
return None
@@ -1039,7 +1040,7 @@ class Unrealircd6:
nickname = self.__Irc.User.get_nickname(self.__Base.clean_uid(serverMsg[1]))
dnickname = self.__Config.SERVICE_NICKNAME
arg = serverMsg[4].replace(':', '')
current_datetime = self.__Base.get_datetime()
current_datetime = self.__Utils.get_sdatetime()
if nickname is None:
return None

View File

@@ -26,7 +26,8 @@ class Settings:
def set_cache(self, key: str, value_to_cache: Any):
"""When you want to store a variable
Ex.
Ex.
```python
set_cache('MY_KEY', {'key1': 'value1', 'key2', 'value2'})
```

View File

@@ -320,21 +320,6 @@ class MConfig(MainModel):
self.SERVEUR_CHARSET: list = ["utf-8", "iso-8859-1"]
"""0: utf-8 | 1: iso-8859-1"""
@dataclass
class MClone(MainModel):
"""Model Clone"""
connected: bool = False
uid: str = None
nickname: str = None
username: str = None
realname: str = None
channels: list = field(default_factory=list)
vhost: str = None
hostname: str = 'localhost'
umodes: str = None
remote_ip: str = '127.0.0.1'
group: str = 'Default'
@dataclass
class MCommand(MainModel):
module_name: str = None

View File

@@ -261,21 +261,21 @@ class Install:
if not do_install:
return None
print("===> Vider le cache de pip")
print("===> Clean pip cache")
self.run_subprocess([self.config.venv_pip_executable, 'cache', 'purge'])
print("===> Verifier si pip est a jour")
print("===> Check if pip is up to date")
self.run_subprocess([self.config.venv_python_executable, '-m', 'pip', 'install', '--upgrade', 'pip'])
if not self.check_package('greenlet'):
self.run_subprocess([self.config.venv_pip_executable, 'install', '--only-binary', ':all:', 'greenlet'])
print('====> Module Greenlet installé')
print('====> Greenlet installed')
for module in self.config.venv_cmd_requirements:
if not self.check_package(module):
print("### Trying to install missing python packages ###")
self.run_subprocess([self.config.venv_pip_executable, 'install', module])
print(f"====> Module {module} installé")
print(f"====> Module {module} installed!")
else:
print(f"==> {module} already installed")
@@ -307,8 +307,8 @@ WantedBy=default.target
with open(full_service_file_path, 'w+') as servicefile:
servicefile.write(contain)
servicefile.close()
print(f'Service file generated with current configuration')
print(f'Running Defender IRC Service ...')
print('Service file generated with current configuration')
print('Running IRC Service ...')
self.run_subprocess(self.config.service_cmd_daemon_reload)
self.run_subprocess(self.config.service_cmd_executable)
@@ -316,8 +316,8 @@ WantedBy=default.target
with open(full_service_file_path, 'w+') as servicefile:
servicefile.write(contain)
servicefile.close()
print(f'Service file generated with current configuration')
print(f'Running Defender IRC Service ...')
print('Service file generated with current configuration')
print('Running IRC Service ...')
self.run_subprocess(self.config.service_cmd_daemon_reload)
self.run_subprocess(self.config.service_cmd_executable)

View File

@@ -31,6 +31,9 @@ class Irc:
# Load the configuration
self.Config = self.Loader.Config
# Load Main utils functions
self.Utils = self.Loader.Utils
# Date et heure de la premiere connexion de Defender
self.defender_connexion_datetime = self.Config.DEFENDER_CONNEXION_DATETIME
@@ -802,7 +805,7 @@ class Irc:
hostname = get_user.hostname
vhost = get_user.vhost
spassword = self.Base.crypt_password(password)
spassword = self.Loader.Utils.hash_password(password)
mes_donnees = {'admin': nickname}
query_search_user = f"SELECT id FROM {self.Config.TABLE_ADMIN} WHERE user=:admin"
@@ -811,7 +814,7 @@ class Irc:
# On verifie si le user exist dans la base
if not exist_user:
mes_donnees = {'datetime': self.Base.get_datetime(), 'user': nickname, 'password': spassword, 'hostname': hostname, 'vhost': vhost, 'level': level}
mes_donnees = {'datetime': self.Utils.get_sdatetime(), 'user': nickname, 'password': spassword, 'hostname': hostname, 'vhost': vhost, 'level': level}
self.Base.db_execute_query(f'''INSERT INTO {self.Config.TABLE_ADMIN}
(createdOn, user, password, hostname, vhost, level) VALUES
(:datetime, :user, :password, :hostname, :vhost, :level)
@@ -833,7 +836,7 @@ class Irc:
log_msg (str): the message to log
"""
try:
mes_donnees = {'datetime': self.Base.get_datetime(), 'server_msg': log_msg}
mes_donnees = {'datetime': self.Utils.get_sdatetime(), 'server_msg': log_msg}
self.Base.db_execute_query(f'INSERT INTO {self.Config.TABLE_LOG} (datetime, server_msg) VALUES (:datetime, :server_msg)', mes_donnees)
return None
@@ -1151,7 +1154,7 @@ class Irc:
return False
if not user_to_log is None:
mes_donnees = {'user': user_to_log, 'password': self.Base.crypt_password(password)}
mes_donnees = {'user': user_to_log, 'password': self.Loader.Utils.hash_password(password)}
query = f"SELECT id, level FROM {self.Config.TABLE_ADMIN} WHERE user = :user AND password = :password"
result = self.Base.db_execute_query(query, mes_donnees)
user_from_db = result.fetchone()
@@ -1204,7 +1207,7 @@ class Irc:
return None
user_to_edit = cmd[1]
user_password = self.Base.crypt_password(cmd[2])
user_password = self.Loader.Utils.hash_password(cmd[2])
get_admin = self.Admin.get_Admin(fromuser)
if get_admin is None:
@@ -1343,9 +1346,9 @@ class Irc:
# If the account doesn't exist then insert into database
data_to_record = {
'createdOn': self.Base.get_datetime(), 'account': fromuser,
'createdOn': self.Utils.get_sdatetime(), 'account': fromuser,
'nickname': user_obj.nickname, 'hostname': user_obj.hostname, 'vhost': user_obj.vhost, 'realname': user_obj.realname, 'email': email,
'password': self.Base.crypt_password(password=password), 'level': 0
'password': self.Loader.Utils.hash_password(password=password), 'level': 0
}
insert_to_db = self.Base.db_execute_query(f"""
@@ -1380,7 +1383,7 @@ class Irc:
return None
account = str(cmd[1]) # account
encrypted_password = self.Base.crypt_password(cmd[2])
encrypted_password = self.Loader.Utils.hash_password(cmd[2])
user_obj = self.User.get_User(fromuser)
client_obj = self.Client.get_Client(user_obj.uid)

View File

@@ -1,25 +1,28 @@
from core.classes import user, admin, client, channel, reputation, settings, commands
import core.definition as df
import core.base as baseModule
import core.classes.config as confModule
import core.utils as utils
import core.base as base_module
import core.classes.config as conf_module
class Loader:
def __init__(self):
# Load Modules
self.Definition: df = df
# Load Main Modules
self.Definition: df = df
self.ConfModule: confModule = confModule
self.ConfModule: conf_module = conf_module
self.BaseModule: baseModule = baseModule
self.BaseModule: base_module = base_module
self.Utils: utils = utils
# Load Classes
self.Settings: settings.Settings = settings.Settings()
self.Config: df.MConfig = self.ConfModule.Configuration().ConfigObject
self.Base: baseModule.Base = self.BaseModule.Base(self.Config, self.Settings)
self.Base: base_module.Base = self.BaseModule.Base(self)
self.User: user.User = user.User(self.Base)

View File

@@ -1,28 +1,24 @@
import sys
import importlib
from types import ModuleType
from typing import Literal, Union
from pathlib import Path
from typing import Literal, Optional, Any
from datetime import datetime
from time import time
from random import choice
from hashlib import md5, sha3_512
def convert_to_int(value: any) -> Union[int, None]:
def convert_to_int(value: Any) -> Optional[int]:
"""Convert a value to int
Args:
value (any): Value to convert to int if possible
value (Any): Value to convert to int if possible
Returns:
Union[int, None]: Return the int value or None if not possible
int: Return the int value or None if not possible
"""
try:
value_to_int = int(value)
return value_to_int
except ValueError:
return None
except Exception:
return None
def get_unixtime() -> int:
"""Cette fonction retourne un UNIXTIME de type 12365456
@@ -32,7 +28,7 @@ def get_unixtime() -> int:
"""
return int(time())
def get_datetime() -> str:
def get_sdatetime() -> str:
"""Retourne une date au format string (24-12-2023 20:50:59)
Returns:
@@ -41,6 +37,12 @@ def get_datetime() -> str:
currentdate = datetime.now().strftime('%d-%m-%Y %H:%M:%S')
return currentdate
def get_datetime() -> datetime:
"""
Return the current datetime in a datetime object
"""
return datetime.now()
def generate_random_string(lenght: int) -> str:
"""Retourn une chaîne aléatoire en fonction de la longueur spécifiée.
@@ -52,15 +54,15 @@ def generate_random_string(lenght: int) -> str:
return randomize
def hash(password: str, algorithm: Literal["md5, sha3_512"] = 'md5') -> str:
"""Retourne un mot de passe chiffré en fonction de l'algorithme utilisé
def hash_password(password: str, algorithm: Literal["md5, sha3_512"] = 'md5') -> str:
"""Return the crypted password following the selected algorithm
Args:
password (str): Le password en clair
algorithm (str): L'algorithm a utilisé
password (str): The plain text password
algorithm (str): The algorithm to use
Returns:
str: Le password haché
str: The crypted password, default md5
"""
match algorithm:
@@ -75,3 +77,13 @@ def hash(password: str, algorithm: Literal["md5, sha3_512"] = 'md5') -> str:
case _:
password = md5(password.encode()).hexdigest()
return password
def get_all_modules() -> list[str]:
"""Get list of all main modules
using this pattern mod_*.py
Returns:
list[str]: List of module names.
"""
base_path = Path('mods')
return [file.name.replace('.py', '') for file in base_path.rglob('mod_*.py')]