Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add ProcessorFormatter for setting different renderers for different loggers #79

Closed
wants to merge 2 commits into from

Conversation

@insolite
Copy link

@insolite insolite commented Aug 29, 2016

…using native logging formatters.
Implementation taken from #73 (comment)
Could be useful along with #78

@codecov-io
Copy link

@codecov-io codecov-io commented Aug 29, 2016

Current coverage is 100% (diff: 100%)

Merging #79 into master will not change coverage

@@           master   #79   diff @@
===================================
  Files          13    14     +1   
  Lines         739   708    -31   
  Methods         0     0          
  Messages        0     0          
  Branches       91    89     -2   
===================================
- Hits          739   708    -31   
  Misses          0     0          
  Partials        0     0          

Powered by Codecov. Last update c256057...94ddb8d

@insolite insolite force-pushed the insolite:processor-formatter branch from daa00db to 94ddb8d Aug 29, 2016
@hynek
Copy link
Owner

@hynek hynek commented Sep 10, 2016

(Just wanted to let you know that I’m currently too busy to review either of your PRs but am grateful for your submissions. I’ll get to it eventually. Sorry.)

@hynek
Copy link
Owner

@hynek hynek commented Oct 17, 2016

Could you please give me an example on how this is supposed to be used? I can write the docs myself if it needs to be but I’m a bit lost about its practical application?

@insolite
Copy link
Author

@insolite insolite commented Dec 7, 2016

For example, when we need to use colored output for console and plain text for file, we can configure logger like this:

    logging.config.dictConfig({
        'version': 1,
        'disable_existing_loggers': False,
        'formatters': {
            'plain': {
                '()': ProcessorFormatter,
                'processor': structlog.dev.ConsoleRenderer(colors=False),
            },
            'colored': {
                '()': ProcessorFormatter,
                'processor': structlog.dev.ConsoleRenderer(colors=True),
            },
        },
        'handlers': {
            'default': {
                'level': 'DEBUG',
                'class': 'logging.StreamHandler',
                'formatter': 'colored',
            },
            'file': {
                'level': 'DEBUG',
                'class': 'logging.handlers.WatchedFileHandler',
                'filename': 'test.log',
                'formatter': 'plain',
            },
        },
        'loggers': {
            '': {
                'handlers': ['default', 'file'],
                'level': 'DEBUG',
                'propagate': True,
            },
        }
    })
    structlog.configure(
        processors=[
            structlog.stdlib.add_log_level,
            structlog.stdlib.PositionalArgumentsFormatter(),
            structlog.processors.TimeStamper(fmt='%Y-%m-%d %H:%M:%S'),
            structlog.processors.StackInfoRenderer(),
            structlog.processors.format_exc_info,
            event_dict_to_message,
        ],
        context_class=dict,
        logger_factory=structlog.stdlib.LoggerFactory(),
        wrapper_class=structlog.stdlib.BoundLogger,
        cache_logger_on_first_use=True,
    )
msg_repr = self.processor(
record._logger, record._name, record.msg.copy())
return msg_repr
return record.getMessage()

This comment has been minimized.

@if-fi

if-fi Feb 14, 2017

I would suggest that you change the implementation to call the super formatter as well

        if isinstance(record.msg, dict):
            msg_repr = self.processor(
                record._logger, record._name, record.msg.copy())
            record.msg = msg_repr
        formatted_msg = super(ProcessorFormatter, self).format(record)
        return formatted_msg

that way we can configure additional formatting in the logging config e.g.

            'plain': {
                '()': ProcessorFormatter,
                'processor': structlog.dev.ConsoleRenderer(colors=False),
               'format': '\n%(message)s [in %(pathname)s:%(lineno)d]'
            },
@if-fi
Copy link

@if-fi if-fi commented Feb 14, 2017

@insolite Thank you, for thins pull request!
This is a usecase that I have, and I have been trying to figure out how to make it work elegantly with structlog.
I have tried your code locally and it works perfectly.
I hope it will become part of the next version of structlog.

I have also added a small comment on the implementation.


def __init__(self, processor, *args, **kwargs):
"""Keep reference to the ``processor``."""
super(ProcessorFormatter, self).__init__(*args, **kwargs)

This comment has been minimized.

@if-fi

if-fi Feb 14, 2017

And we should have a default 'fromat' if no 'format' is set in the logging config.

        fmt = kwargs.pop('fmt', '%(message)s')
        super(ProcessorFormatter, self).__init__(fmt=fmt, *args, **kwargs)
@hynek hynek mentioned this pull request Mar 5, 2017
hynek added a commit that referenced this pull request Mar 6, 2017
Based on the work of @fabianbuechler, @insolite, and @if-fi.

Fixes #79
@hynek
Copy link
Owner

@hynek hynek commented Mar 6, 2017

c.f. #105 – sorry for the delays

@hynek hynek closed this in 065b69a Apr 24, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Linked issues

Successfully merging this pull request may close these issues.

None yet

4 participants