• Stars
    star
    134
  • Rank 269,444 (Top 6 %)
  • Language
    Python
  • License
    Apache License 2.0
  • Created over 7 years ago
  • Updated about 2 months ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Flake8 extension to validate (lack of) logging format strings

flake8-logging-format

Flake8 extension to validate (lack of) logging format strings

What's This?

Python logging supports a special extra keyword for passing a dictionary of user-defined attributes to include in a logging event. One way to ensure consistency and rigor in logging is to always use extra to pass non-constant data and, therefore, to never use format strings, concatenation, or other similar techniques to construct a log string.

In other words, do this:

logger.info(
    "Hello {world}",
    extra=dict(
        world="Earth"
    )
)

Instead of:

logger.info(
    "Hello {world}".format(world=Earth)
)

Extra Whitelist

As a further level of rigor, we can enforce that extra dictionaries only use keys from a well-known whitelist.

Usage:

flake8 --enable-extra-whitelist

The built-in Whitelist supports plugins using entry_points with a key of "logging.extra.whitelist". Each registered entry point must be a callable that returns an iterable of string.

In some cases you may want to log sensitive data only in debugging scenarios. This is supported in 2 ways:

  1. We do not check the logging.extra.whitelist for lines logged at the debug level
  2. You may also prefix a keyword with 'debug_' and log it at another level. You can safely assume these will be filtered out of shipped logs.

Violations Detected

  • G001 Logging statements should not use string.format() for their first argument
  • G002 Logging statements should not use % formatting for their first argument
  • G003 Logging statements should not use + concatenation for their first argument
  • G004 Logging statements should not use f"..." for their first argument (only in Python 3.6+)
  • G010 Logging statements should not use warn (use warning instead)
  • G100 Logging statements should not use extra arguments unless whitelisted
  • G101 Logging statement should not use extra arguments that clash with LogRecord fields
  • G200 Logging statements should not include the exception in logged string (use exception or exc_info=True)
  • G201 Logging statements should not use error(..., exc_info=True) (use exception(...) instead)
  • G202 Logging statements should not use redundant exc_info=True in exception

These violations are disabled by default. To enable them for your project, specify the code(s) in your setup.cfg:

[flake8]
enable-extensions=G

Motivation

Our motivation has to do with balancing the needs of our team and those of our customers. On the one hand, developers and front-line support should be able to look at application logs. On the other hand, our customers don't want their data shared with anyone, including internal employees.

The implementation approaches this in two ways:

  1. By trying to prevent the use of string concatenation in logs (vs explicit variable passing in the standard logging extra dictionary)

  2. By providing an (optional) mechanism for whitelisting which field names may appear in the extra dictionary

Naturally, this does not prevent developers from doing something like:

extra=dict(
    user_id=user.name,
)

but then avoiding a case like this falls back to other processes around pull-requests, code review and internal policy.

More Repositories

1

sklearn-hierarchical-classification

Python
67
star
2

microcosm

Component wiring for Python microservices
Python
35
star
3

openapi

Python Open API 2.0 (Swagger) object model
Python
30
star
4

opencypher

OpenCypher AST and Builder API
Python
9
star
5

microcosm-flask

Opinionated Flask services.
Python
9
star
6

botoenv

Manage AWS environment variables using botocore
Dockerfile
8
star
7

deboiler

Deboiler - Boilerplate Identification and Removal
Python
7
star
8

microcosm-pubsub

PubSub with SNS/SQS
Python
6
star
9

microcosm-fastapi

Opinionated fastapi services.
Python
6
star
10

cookiecutter-microcosm-service

Python
4
star
11

cookiecutter-graphql-gateway

JavaScript
4
star
12

nodule-graphql

Node GraphQL Conventions
JavaScript
4
star
13

microcosm-postgres

Opinionated persistence with PostgreSQL
Python
4
star
14

microcosm-eventsource

Event-sourced state machines using microcosm.
Python
4
star
15

nodule-config

Opinionated configuration for Node applications
TypeScript
3
star
16

pystreet

Street address validation, formatting, and geocoding
Python
3
star
17

microcosm-logging

Opinionated logging configuration using microcosm wiring.
Python
3
star
18

microcosm-sample-service

Python
2
star
19

microcosm-elasticsearch

Elasticsearch configuration using microcosm wiring.
Python
2
star
20

microcosm-caching

Caching for microcosm microservices.
Python
1
star
21

nodule-openapi

Opinionated OpenAPI (Swagger) Client
JavaScript
1
star
22

globality-corp.github.io

Globality Open Source
HTML
1
star
23

cookiecutter-microcosm-sagemaker

Python
1
star
24

vaultenv

Ansible vault environment variable exporting
Python
1
star
25

microcosm-metrics

Opinionated metrics configuration.
Python
1
star