first implementations of database and logging utilities.
This commit is contained in:
		
							parent
							
								
									4e6dff930d
								
							
						
					
					
						commit
						172de21f55
					
				
							
								
								
									
										2
									
								
								.gitignore
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										2
									
								
								.gitignore
									
									
									
									
										vendored
									
									
								
							@ -167,3 +167,5 @@ cython_debug/
 | 
			
		||||
#  and can be added to the global gitignore or merged into this file.  For a more nuclear
 | 
			
		||||
#  option (not recommended) you can uncomment the following to ignore the entire idea folder.
 | 
			
		||||
#.idea/
 | 
			
		||||
 | 
			
		||||
forensic_trails.db
 | 
			
		||||
							
								
								
									
										7
									
								
								config.json
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										7
									
								
								config.json
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,7 @@
 | 
			
		||||
{
 | 
			
		||||
    "database_path": "forensic_trails.db",
 | 
			
		||||
    "database_schema_version": 1,
 | 
			
		||||
    "database_template": "schema.sql",
 | 
			
		||||
    "log_path": "forensic_trails.log",
 | 
			
		||||
    "log_level": "DEBUG"
 | 
			
		||||
}
 | 
			
		||||
@ -8,9 +8,9 @@ version = "0.1.0"
 | 
			
		||||
description = "Forensic Investigation Documentation System"
 | 
			
		||||
readme = "README.md"
 | 
			
		||||
requires-python = ">=3.12"
 | 
			
		||||
license = {text = "MIT"}  # Change as needed
 | 
			
		||||
license = {text = "BSD 3-Clause"}
 | 
			
		||||
authors = [
 | 
			
		||||
    {name = "Your Name", email = "your.email@example.com"}
 | 
			
		||||
    {name = "Overcuriousity", email = "overcuriousity@posteo.org"}
 | 
			
		||||
]
 | 
			
		||||
classifiers = [
 | 
			
		||||
    "Development Status :: 3 - Alpha",
 | 
			
		||||
@ -26,6 +26,7 @@ dependencies = [
 | 
			
		||||
    "Pillow>=10.0.0",
 | 
			
		||||
    "cryptography>=41.0.0",
 | 
			
		||||
    "pyinstaller>=6.0.0",
 | 
			
		||||
    "logging>=0.4.9.6",
 | 
			
		||||
]
 | 
			
		||||
 | 
			
		||||
[project.optional-dependencies]
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										6
									
								
								run.py
									
									
									
									
									
								
							
							
						
						
									
										6
									
								
								run.py
									
									
									
									
									
								
							@ -1,4 +1,4 @@
 | 
			
		||||
import forensic_trails
 | 
			
		||||
from src.forensictrails.__main__ import main
 | 
			
		||||
 | 
			
		||||
def run():
 | 
			
		||||
    forensic_trails.main()
 | 
			
		||||
if __name__ == "__main__":
 | 
			
		||||
    main()
 | 
			
		||||
@ -1,24 +1,33 @@
 | 
			
		||||
"""Entry point for ForensicTrails application."""
 | 
			
		||||
import sys
 | 
			
		||||
import logging
 | 
			
		||||
from PyQt6.QtWidgets import QApplication
 | 
			
		||||
 | 
			
		||||
from .db.database import initialize_database
 | 
			
		||||
from .utils.logging import setup_logging
 | 
			
		||||
 | 
			
		||||
def main():
 | 
			
		||||
    """Main entry point for the application."""
 | 
			
		||||
    setup_logging()
 | 
			
		||||
    logging.info("Starting ForensicTrails application")
 | 
			
		||||
    
 | 
			
		||||
    initialize_database()
 | 
			
		||||
    
 | 
			
		||||
    # Create Qt application
 | 
			
		||||
    app = QApplication(sys.argv)
 | 
			
		||||
    app.setApplicationName("ForensicTrails")
 | 
			
		||||
    app.setOrganizationName("Your Organization")
 | 
			
		||||
    app.setOrganizationName("ForensicTrails")
 | 
			
		||||
    app.setApplicationVersion("0.1.0")
 | 
			
		||||
    
 | 
			
		||||
    # TODO: Create and show main window
 | 
			
		||||
    # from forensictrails.gui.main_window import MainWindow
 | 
			
		||||
    # from .gui.main_window import MainWindow
 | 
			
		||||
    # window = MainWindow()
 | 
			
		||||
    # window.show()
 | 
			
		||||
    
 | 
			
		||||
    print("ForensicTrails - Forensic Investigation Documentation System")
 | 
			
		||||
    print("Application starting...")
 | 
			
		||||
    
 | 
			
		||||
    sys.exit(app.exec())
 | 
			
		||||
 | 
			
		||||
    # For now, just exit immediately since we have no GUI yet
 | 
			
		||||
    logging.debug("No GUI yet - exiting...")
 | 
			
		||||
    return 0
 | 
			
		||||
    # sys.exit(app.exec())
 | 
			
		||||
 | 
			
		||||
if __name__ == "__main__":
 | 
			
		||||
    main()
 | 
			
		||||
    sys.exit(main())
 | 
			
		||||
							
								
								
									
										45
									
								
								src/forensictrails/db/database.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										45
									
								
								src/forensictrails/db/database.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,45 @@
 | 
			
		||||
import sqlite3
 | 
			
		||||
import logging
 | 
			
		||||
from pathlib import Path
 | 
			
		||||
 | 
			
		||||
from ..utils.config import config
 | 
			
		||||
 | 
			
		||||
def get_db_connection(db_path=None):
 | 
			
		||||
    if db_path is None:
 | 
			
		||||
        db_path = create_db_if_not_exists()
 | 
			
		||||
    conn = sqlite3.connect(db_path)
 | 
			
		||||
    conn.row_factory = sqlite3.Row
 | 
			
		||||
    return conn
 | 
			
		||||
 | 
			
		||||
def create_db_if_not_exists(db_path=None, schema_path=None):
 | 
			
		||||
    if db_path is None:
 | 
			
		||||
        db_path = config.database_path
 | 
			
		||||
    
 | 
			
		||||
    if schema_path is None:
 | 
			
		||||
        schema_path = Path(__file__).parent / config.database_template
 | 
			
		||||
    
 | 
			
		||||
    conn = get_db_connection(db_path)
 | 
			
		||||
    cursor = conn.cursor()
 | 
			
		||||
    
 | 
			
		||||
    with open(schema_path, 'r') as f:
 | 
			
		||||
        schema = f.read()
 | 
			
		||||
    
 | 
			
		||||
    cursor.executescript(schema)
 | 
			
		||||
    conn.commit()
 | 
			
		||||
    conn.close()
 | 
			
		||||
    
 | 
			
		||||
def initialize_database(db_path=None):
 | 
			
		||||
    if db_path is None:
 | 
			
		||||
        db_path = config.database_path
 | 
			
		||||
    get_db_connection(db_path)
 | 
			
		||||
    if config.log_level == 'DEBUG':
 | 
			
		||||
        show_db_schema(db_path)
 | 
			
		||||
    logging.info(f"Database initialized at {db_path}")
 | 
			
		||||
    
 | 
			
		||||
def show_db_schema(db_path):
 | 
			
		||||
    conn = get_db_connection(db_path)
 | 
			
		||||
    cursor = conn.cursor()
 | 
			
		||||
    logging.debug("Displaying database schema:")
 | 
			
		||||
    for row in cursor.execute("SELECT name, sql FROM sqlite_master WHERE type='table';"):
 | 
			
		||||
        logging.debug(f"Table: {row['name']}\nSQL: {row['sql']}\n")
 | 
			
		||||
    conn.close()
 | 
			
		||||
							
								
								
									
										20
									
								
								src/forensictrails/utils/config.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										20
									
								
								src/forensictrails/utils/config.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,20 @@
 | 
			
		||||
import json
 | 
			
		||||
import os
 | 
			
		||||
 | 
			
		||||
class Config:
 | 
			
		||||
    def __init__(self, config_filepath='config.json'):
 | 
			
		||||
        config_data = self._load_config(config_filepath)
 | 
			
		||||
        self.database_template = config_data.get('database_template', 'schema.sql')
 | 
			
		||||
        self.database_path = config_data.get('database_path', 'forensic_trails.db')
 | 
			
		||||
        self.database_schema_version = config_data.get('database_schema_version', 1)
 | 
			
		||||
        self.log_path = config_data.get('log_path', 'forensic_trails.log')
 | 
			
		||||
        self.log_level = config_data.get('log_level', 'DEBUG')
 | 
			
		||||
    
 | 
			
		||||
    def _load_config(self, config_filepath):
 | 
			
		||||
        if os.path.exists(config_filepath):
 | 
			
		||||
            with open(config_filepath, 'r') as f:
 | 
			
		||||
                return json.load(f)
 | 
			
		||||
        else:
 | 
			
		||||
            return {}
 | 
			
		||||
 | 
			
		||||
config = Config()
 | 
			
		||||
							
								
								
									
										31
									
								
								src/forensictrails/utils/logging.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										31
									
								
								src/forensictrails/utils/logging.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,31 @@
 | 
			
		||||
import logging
 | 
			
		||||
from pathlib import Path
 | 
			
		||||
from ..utils.config import config
 | 
			
		||||
import sys
 | 
			
		||||
 | 
			
		||||
def setup_logging(log_path=None):
 | 
			
		||||
    if log_path is None:
 | 
			
		||||
        log_path = config.log_path
 | 
			
		||||
    
 | 
			
		||||
    log_file = Path(log_path)
 | 
			
		||||
    log_file.parent.mkdir(parents=True, exist_ok=True)
 | 
			
		||||
    
 | 
			
		||||
    logger = logging.getLogger()
 | 
			
		||||
    logger.setLevel(config.log_level)
 | 
			
		||||
 | 
			
		||||
    formatter = logging.Formatter(
 | 
			
		||||
        '%(asctime)s - %(name)s - %(levelname)s - %(message)s',
 | 
			
		||||
        datefmt='%Y-%m-%d %H:%M:%S'
 | 
			
		||||
    )
 | 
			
		||||
 | 
			
		||||
    file_handler = logging.FileHandler(log_file)
 | 
			
		||||
    file_handler.setLevel(config.log_level)
 | 
			
		||||
    file_handler.setFormatter(formatter)
 | 
			
		||||
    logger.addHandler(file_handler)
 | 
			
		||||
 | 
			
		||||
    stream_handler = logging.StreamHandler(sys.stdout)
 | 
			
		||||
    stream_handler.setLevel(config.log_level)
 | 
			
		||||
    stream_handler.setFormatter(formatter)
 | 
			
		||||
    logger.addHandler(stream_handler)
 | 
			
		||||
    
 | 
			
		||||
    
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user