text: import logging.config
  import os
  import sys
  
  from pythonjsonlogger.jsonlogger import JsonFormatter
  
  
  class JSFormatter(JsonFormatter):
      msg_keys = [
          'asctime',
          'created',
          'filename',
          'funcName',
          'levelname',
          'levelno',
          'lineno',
          'module',
          'msecs',
          'message',
          'name',
          'pathname',
          'process',
          'processName',
          'relativeCreated',
          'thread',
          'threadName',
      ]
  
      def __init__(self, *args, env_vars=[], **kwargs):
          super(JSFormatter, self).__init__(*args, **kwargs)
          self.default_keys = {k: v for k, v in list(os.environ.items()) if k in env_vars}
          self._required_fields.extend(self.msg_keys)
  
      def process_log_record(self, rec):
          rec.update(self.default_keys)
          return rec
  
  
  def base_handler(filename, **params):
      return {
          'level': 'DEBUG',
          'class': 'safe_logger.TimedRotatingFileHandlerSafe',
          'when': 'midnight',
          'backupCount': 7,
          'formatter': 'standard',
          'filename': filename,
          **params,
      }
  
  
  def get_plain_logname(base_name, root_dir, enable_json):
      """
      we nest all plain logs to prevent double log shipping
      """
      if enable_json:
          nested_dir = os.path.join(root_dir, 'plain')
          if os.path.exists(root_dir) and not os.path.exists(nested_dir):
              os.mkdir(nested_dir)
          root_dir = nested_dir
      return os.path.join(root_dir, '{}.log'.format(base_name))
  
  
  def setup_logger(
      base_name,
      root_dir=None,
      enable_json=True,
      json_formatter='fan_tools.fan_logging.JSFormatter',
      loggers={},
      enable_stdout=True,
      stdout_level='DEBUG',
      handlers={},
      json_params={}
  ):
      """
      json_formatter:
      'fan.contrib.django.span_formatter.SpanFormatter' - add INSTALLATION_ID, SPAN and etc
      """
      if not root_dir:
          root_dir = os.environ.get('LOG_DIR')
      assert root_dir, 'You should pass root_dir parameter or set env LOG_DIR'
  
      JSON_FORMATTER = {
          '()': json_formatter,
          'env_vars': ['HOST_TYPE', 'DEPLOYMENT_CONFIG', 'DEPLOYMENT_BRANCH', 'CONTAINER_TYPE'],
          **json_params,
      }
  
      default_loggers = {
          '': {'handlers': ['default'], 'level': 'DEBUG', 'propagate': True},
          'googleapicliet.discovery_cache': {'level': 'ERROR'},
          'boto3': {'level': 'INFO'},
          'botocore': {'level': 'INFO'},
          'kazoo': {'level': 'INFO'},
          'urllib3': {'level': 'INFO'},
      }
  
      LOGGING = {
          'version': 1,
          'disable_existing_loggers': False,
          'formatters': {
              'json': JSON_FORMATTER,
              'standard': {'format': '%(asctime)s [%(levelname)s] %(name)s: %(message)s'},
          },
          'handlers': {'default': base_handler(get_plain_logname(base_name, root_dir, enable_json))},
          'loggers': {**default_loggers, **loggers},
      }
      if enable_json:
          LOGGING['handlers']['json'] = base_handler(
              os.path.join(root_dir, '{}.json_log'.format(base_name)), formatter='json'
          )
          LOGGING['loggers']['']['handlers'].append('json')
  
      if handlers:
          LOGGING['handlers'].update(handlers)
          for handler_name in handlers:
              LOGGING['loggers']['']['handlers'].append(handler_name)
  
      if enable_stdout:
          LOGGING['handlers']['stdout'] = {
              'level': stdout_level,
              'class': 'logging.StreamHandler',
              'stream': sys.stdout,
              'formatter': 'standard',
          }
          LOGGING['loggers']['']['handlers'].append('stdout')
      logging.config.dictConfig(LOGGING)
  
  
  def setup_fan_logger(base_name, root_dir=None):
      return setup_logger(
          base_name,
          root_dir,
          enable_json=True,
          json_formatter='fan.contrib.django.span_formatter.SpanFormatter',
      )
  