Skip to content
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 7 additions & 2 deletions application/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,22 +21,27 @@
import os
import sys

import application.paths
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Fix the import statement to match usage.

The code imports application.paths but later uses paths directly, which will cause an undefined name error.

-import application.paths
+import application.paths as paths
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
import application.paths
import application.paths as paths
🧰 Tools
🪛 Ruff (0.8.2)

24-24: application.paths imported but unused; consider removing, adding to __all__, or using a redundant alias

(F401)

import yaml
from flask import Flask, Blueprint, jsonify
from werkzeug.exceptions import HTTPException
from werkzeug.serving import WSGIRequestHandler

logger = logging.getLogger(__name__)

try:
with open('log_config.yaml') as config_file:
config = yaml.safe_load(config_file.read())

config['handlers']['timedRotatingFile']['filename'] = paths.LOG_FILE_PATH
paths.makedir_if_not_exists(paths.LOGS_DIR_PATH)
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can you explain how this works?

  1. shouldn't we create the file before configuring logging?
  2. does makedir_if_not_exists work for files?

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor Author

@li-ruihao li-ruihao Mar 30, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Answer to question 1:

Per Python documentation for TimedRotatingHandler under logging handlers, it says this upon returning a new instance of the TimedRotatingFileHandler class

The specified file is opened and used as the stream for logging.

Although not explicitly mentioning that the specified file is created, it does perform file creation if the file does not exist already, and I've tested it on my Windows machine. Unless you think it is safe to create the file first before configuring logging, I do not think this is a concern.

Answer to question 2:

Please note that paths.LOGS_DIR_PATH is not the same as paths.LOG_FILE_PATH, the first specifies the directory that stores the logs, which I wrote the code to create the directory if it does not exist already to prevent any issues or errors for loggin

Explanation for how this works:

paths.LOGS_DIR_PATH and paths.LOG_FILE_PATH are two FINAL variables(not explicitly annotated or commented, but they shouldn't be changed during runtime in any case) declared and assigned in paths.py.

config['handlers']['timedRotatingFile']['filename'] = paths.LOG_FILE_PATH: this is to set the current log's file name as well as the file prefix for older log files. Upon file rotation, the naming of the log files will show the behaviour per Python's documentation on TimedRotatingFileHandler as follows:

The system will save old log files by appending extensions to the filename. The extensions are date-and-time based, using the strftime format %Y-%m-%d_%H-%M-%S or a leading portion thereof, depending on the rollover interval.

Here is a screenshot of some sample logs that were produced during the testing of the TimedRotatingFileHandler, where ictrl_log is the current log:
image

paths.makedir_if_not_exists(paths.LOGS_DIR_PATH): Already explained

logging.config.dictConfig(config)
except Exception:
# Fallback to a basic configuration
logging.basicConfig(format='%(asctime)s %(levelname)s [%(name)s:%(lineno)d] %(message)s', level=logging.INFO, force=True)

logger = logging.getLogger(__name__)
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we keep Line 29 and remove this?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reasoning for this was explained in PR#48, but I forgot I also made the changes here since these changes were not merged. I can collapse the other PR onto this.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick (assertive)

Consider initializing the logger only once.

The logger is initialized in both the exception and else blocks. Consider initializing it once before the try block and reusing it to reduce duplication.

+logger = logging.getLogger(__name__)
 try:
     with open('log_config.yaml') as config_file:
         config = yaml.safe_load(config_file.read())

     config['handlers']['timedRotatingFile']['filename'] = paths.LOG_FILE_PATH
     logging.config.dictConfig(config)
 except Exception:
     # Fallback to a basic configuration
     logging.basicConfig(format='%(asctime)s %(levelname)s [%(name)s:%(lineno)d] %(message)s', level=logging.INFO, force=True)

-    logger = logging.getLogger(__name__)
     logger.exception("Logging setup failed")
 else:
-    logger = logging.getLogger(__name__)
     logger.warning("Logging setup is completed with config=%s", config)

Also applies to: 43-43

logger.exception("Logging setup failed")
else:
logger = logging.getLogger(__name__)
logger.warning("Logging setup is completed with config=%s", config)

from .Profile.Profile import Profile
Expand Down
2 changes: 2 additions & 0 deletions application/paths.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,3 +39,5 @@ def makedir_if_not_exists(path):
USER_PROFILE_PATH = os.path.join(PROFILE_PATH, "user_profile.json")
PRIVATE_KEY_PATH = os.path.join(PROFILE_PATH, "private_keys")
makedir_if_not_exists(PRIVATE_KEY_PATH)
LOGS_DIR_PATH = os.path.join(PROFILE_PATH, 'logs')
LOG_FILE_PATH = os.path.join(LOGS_DIR_PATH, 'ictrl_log.log')
10 changes: 9 additions & 1 deletion log_config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,15 @@ handlers:
level: DEBUG
formatter: default
stream: ext://sys.stderr
timedRotatingFile:
class: logging.handlers.TimedRotatingFileHandler
level: DEBUG
formatter: default
when: H
interval: 3
backupCount: 112
# filename: dynamically assigned upon the initialization of the program

root:
level: DEBUG
handlers: [console]
handlers: [console, timedRotatingFile]
Loading