Logging re-initialized in make_app()
Mads Kiilerich
mads at kiilerich.com
Mon Dec 30 00:14:20 UTC 2019
On 12/12/19 12:34 AM, Wolfgang Scherer wrote:
>
> I finished the analysis of logging initialization (http://sw-amt.ws/kallithea-deploy/html/overview.html#bug-logging-re-initialized-in-make-app). Since I don't think that all the packages will be updated any time soon, I will stay with the minimum required corrections in Kallithea (see attached patch).
>
> The initialization schema is generally
>
> 1. Initialize logging (each toolkit rolls their own, but defaults
> :attr:`__file__` and :attr:`here` are always set)
> 2. Load WSGI application (:func:`paste.deploy.loadapp`)
To make sure we all are aligned on the bigger picture, let me try to
phrase it. Please correct me if you think I got it wrong:
The basic architecture of the web part of Kallithea is that the web
server create the TurboGears based Kallithea app instance using
paste.deploy. The web server then use the app instance to serve WSGI
requests.
Paste.deploy reads the .ini file using loadwsgi.NicerConfigParser, which
is based on standard ConfigParser. Among other things, it also introduce
the convention of passing "here" and "__file__" as "defaults" to
ConfigParser, so these variables can be used for %()s string
interpolation when paste.deploy reads the .ini file. Paste.deploy will
pass the content of the app:main section as parameters to
kallithea.config.middleware:make_app (as specified in setup.py
paste.app_factory). We make sure Kallithea command line tools get the
same values by using `paste.deploy.appconfig`. Kallithea will use the
config values from paste.deploy, and will "not really" read the .ini
file directly. It works fine for example for the default config
`sqlalchemy.url = sqlite:///%(here)s/kallithea.db`.
Paste.deploy and TurboGears doesn't interfere with logging. They might
use it, but they do not configure it. That must be taken care of
elsewhere. Also when logging is configured in the same .ini file that
paste.deploy use, but in other sections.
It is common for "WSGI servers" (such as gearbox) to run some boiler
plate like `logging.config.fileConfig(config_file,
dict(__file__=config_file, here=os.path.dirname(config_file))` right
before `paste.deploy.loadapp('config:' + config_file)`. The
here/__file__ convention that was fully contained inside paste.deploy is
thus spreading, and it could seem like *all* "WSGI servers" now must
initialize logging this way to ensure consistency.
mod_wsgi gives/requires full control over these details and their
"configuration" by just launching a WSGI dispatch python script provided
by the user. Kallithea docs/setup.rst provide some sample scripts. They
initialize logging, but will apparently have to be extended with the
here/__file__ boilerplate.
Also, Kallithea must make sure to follow the same here/__file__
convention in *all* code paths, also command line tools that has to
invoke fileConfig directly. (That would all have been easy if it was
built into ConfigParser (and fileConfig) - now it is just annoying
boilerplate and tech debt.)
(We can get a ConfigParser instance like paste.deploy does by using
`paste.deploy.loadwsgi.ConfigLoader('my.ini').parser` ... but even
though it contains the logging config sections, there is no simple way
to use that to initialize the logging module in py2.)
It is pointless to configure logging multiple times with the same .ini
file. Especially if they use different conventions. That is the case
now, when Kallithea middleware.py runs
`fileConfig(global_conf['__file__'])` and will overwrite any `%(here)s`
expansion that the WSGI server might have done. It seems like the
Kallithea shouldn't mess with logging configuration, but assume it
already has been configured. The fileConfig in make_app solved a problem
when it was introduced in 0d4dd9380a45, but it is evidently no longer
relevant.
/Mads
More information about the kallithea-general
mailing list