Skip to main content

A python context logger with thread-local storage and context propagation for Python applications.

Project description

Python Context Logger

A Python context logger using thread-local storage for log context propagation across threads, designed to simplify logging in multi-threaded applications. The logger dynamically updates log context based on function parameters and provides flexibility for customization at initialization.

Features

  • Thread-local storage for log context: Each thread maintains its own isolated log context, ensuring no cross-thread interference.
  • Dynamic log context updating: Automatically updates log context based on function parameters, enabling detailed logging.
  • Log context propagation across threads: Ensures log context consistency in multi-threaded environments.
  • Decorators for easy integration: Integrate logging into functions and classes using decorators for cleaner and more maintainable code.
  • Optional logRequestId generation: Automatically track request IDs if explicitly enabled.
  • Configurable logger: Customize the logger name, level, and format during initialization.
  • Constant key-value pairs: Set log constants to ensure that specific key-value pairs are present in every log entry.
  • Retrieve log property values: Get specific log property values (e.g., requestId) to propagate across services.

Installation

pip install py-context-logger

Usage

Basic Initialization

from context_logger import ContextLogger

# Initialize logger
context_logger = ContextLogger()

# Optional: Configure logger name, log format, and log level
context_logger.initialize_context_logger(name="MyLogger", log_format="%(asctime)s - %(message)s", level="INFO")

Flask Example

Integrating the logger into a Flask application to automatically log request context and function parameters.

from flask import Flask, request
from context_logger import UseContextLogger, ClearLogContext, ContextLogger

app = Flask(__name__)
context_logger = ContextLogger()

# Initialize context logger
context_logger.initialize_context_logger()

@app.route('/some-endpoint', methods=['POST'])
@UseContextLogger({
    'resource_name': 'name',
    'resource_id': 'id',
    'headers.requestId': 'requestId',
    'headers.mailId': 'requestedMail'
})
@ClearLogContext()
def some_endpoint(resource_name: str, resource_id: str, headers: dict, logger=None):
    logger.info("Processing request")
    data = request.get_json()

    # Class method logging example
    sample_class = SampleClass()
    user_name, company_name = "Sample user", "Sample company"
    sample_class.method_one(user_name=user_name, user_company=company_name)

    return {"status": "success"}

if __name__ == '__main__':
    app.run(debug=True)

Class-Level Logging

Decorate class methods to automatically add context information to logs.

from context_logger import UseContextLogger

@UseContextLogger()
class SampleClass:
    def __init__(self, logger=None):
        self.logger = logger

    @UseContextLogger({"user_name": "username", "log_constants": {"company_city": "New York"}})
    def method_one(self, user_name: str, user_company: str, logger=None):
        self.logger.info(f"Processing method_one with user")
        self.method_two(user_company=user_company)

    def method_two(self, user_company: str):
        self.logger.info(f"Processing method_two with company: {user_company}")
    
    # Fetch log property to pass across services
    def method_three(self, user_company: str):
        requestId = self.logger.get_property_value(log_property="requestId")
        self.logger.info(f"Processing method_three with company: {user_company} and requestId: {requestId}")

Customization of Logger

You can initialize the logger with a custom name, log level, and format.

context_logger.initialize_context_logger(
    name="CustomLogger",
    log_format="%(asctime)s - %(levelname)s - %(message)s",
    level="DEBUG"
)

Retrieve Log Properties

At any point in the application, you can retrieve a log property (e.g., requestId) to pass it to other services or systems.

requestId = context_logger.get_property_value("logRequestId")

Sample Log Format

2024-07-16 16:20:54,197 - main.py:79 - INFO - {'name': 'sample_resource', 'id': '123', 'logRequestId': '6239237f-1f96-48c6-93f3-89fd2c63ea6d', 'requestedMail': 'sample-user@gmail.com'} - Processing request
2024-07-16 16:20:54,198 - main.py:79 - INFO - {'name': 'sample_resource', 'id': '123', 'logRequestId': '6239237f-1f96-48c6-93f3-89fd2c63ea6d', 'requestedMail': 'sample-user@gmail.com', 'username': 'Sample user', 'company_city': 'New York'} - Processing method_one with user
2024-07-16 16:20:54,199 - main.py:79 - INFO - {'name': 'sample_resource', 'id': '123', 'logRequestId': '6239237f-1f96-48c6-93f3-89fd2c63ea6d', 'requestedMail': 'sample-user@gmail.com', 'username': 'Sample user', 'company_city': 'New York'} - Processing method_two with company: Sample company
2024-07-16 16:20:55,000 - main.py:79 - INFO - {'name': 'sample_resource', 'id': '123', 'logRequestId': '6239237f-1f96-48c6-93f3-89fd2c63ea6d', 'requestedMail': 'sample-user@gmail.com', 'username': 'Sample user', 'company_city': 'New York'} - Processing method_three with company: Sample company

Security Considerations

  1. Sensitive Data: Ensure sensitive information (e.g., user credentials, personal data) is not logged unless absolutely necessary.
  2. Log Access Control: Limit access to logs to authorized personnel only.
  3. Log Integrity: Implement security measures to detect and prevent log manipulation or tampering.

Performance

  • Thread-local storage: The use of thread-local storage ensures isolated log contexts for each thread, minimizing contention in multi-threaded applications.
  • Efficient context propagation: Log context is efficiently propagated across threads without introducing significant performance overhead.
  • Minimal overhead: The custom logger and decorators are designed to introduce minimal performance impact, allowing for high-throughput logging.

License

This project is licensed under the MIT License.


Conclusion

The py-context-logger package provides a flexible, powerful logging system designed for multi-threaded Python applications. With easy-to-use decorators, thread-local storage, and support for custom log contexts, this logger simplifies complex logging scenarios while maintaining performance and flexibility.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

py_context_logger-2.0.0.tar.gz (7.2 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

py_context_logger-2.0.0-py3-none-any.whl (8.1 kB view details)

Uploaded Python 3

File details

Details for the file py_context_logger-2.0.0.tar.gz.

File metadata

  • Download URL: py_context_logger-2.0.0.tar.gz
  • Upload date:
  • Size: 7.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/5.1.1 CPython/3.9.6

File hashes

Hashes for py_context_logger-2.0.0.tar.gz
Algorithm Hash digest
SHA256 e63882732ccf64e57b9763e57907ea83aaeada88b8ac0eafb5f9600d0ec86799
MD5 55807e4cc7923d10da8cfdfe77cb7b2f
BLAKE2b-256 599892acd51f523c1fe21e5e19acdad2e496b1d9286adfa35a824787f3af212b

See more details on using hashes here.

File details

Details for the file py_context_logger-2.0.0-py3-none-any.whl.

File metadata

File hashes

Hashes for py_context_logger-2.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 40816368d9e9909cdab5ea9435e3ae6f6935f25b31511ab83955f9f9f5cb21e8
MD5 3bd780e621d45955fcc53d238a9ad813
BLAKE2b-256 0c630eb050622ca5b699b7c30bf402ab530a4c0fdbab606fd0da6aa805bf1e80

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page