Handler duplication on DictConfig
Closed this issue · 5 comments
I configure logging manually:
import (
"github.com/hhkbp2/go-logging"
)
func LoggingDefault() {
rootLogger := logging.GetLogger("")
rootLogger.SetLevel(logging.LevelInfo)
formatter := logging.NewStandardFormatter("%(asctime)s %(levelname)s (%(filename)s:%(lineno)d) %(name)s %(message)s",
"%Y-%m-%d %H:%M:%S.%3n")
stdoutHandler := logging.NewStdoutHandler()
stdoutHandler.SetLevel(logging.LevelInfo)
stdoutHandler.SetFormatter(formatter)
rootLogger.AddHandler(stdoutHandler)
}
Than I load config file:
{
"version": 1,
"root": {
"level": "DEBUG",
"propagate": true,
"handlers": ["stdout", "file"]
},
"handlers": {
"stdout": {
"class": "StdoutHandler",
"level": "DEBUG",
"formatter" : "ft"
},
"file": {
"class": "FileHandler",
"level": "DEBUG",
"filename": "xignite_fetcher_stocks.log",
"mode": "O_CREATE",
"bufferSize": 0,
"formatter": "ft"
}
},
"formatters": {
"ft": {
"format": "%(asctime)s %(levelname)s (%(filename)s:%(lineno)d) %(name)s %(message)s",
"datefmt": "%Y-%m-%d %H:%M:%S.%3n"
}
}
}
by ApplyJsonConfigFile.
Actual behavior: every line is duplicated in stdout
Expected behavior: no duplication
Every time when I call DictConfig, I receive handler duplication.
So, after 5 times I have 6 duplicates for every line.
Can we change DictConfig to "replace" behavior - when it totally replace actual configuration to provided by argument?
Note please, just "reset and apply" the bad way, because during replace we will omit some lines.
Hi @zamotivator ,
Using go-logging, you could write code like LoggingDefault()
to initialize the log facility. Loading configuration from config file is an alternative way. If you want to log to the stdout, either calling LoggingDefault()
or loading configuration with handler stdout
will be sufficient. It is not necessary to do them both.
It's not suggested the user exposes the rootLogger
and uses it directly, such as stdoutHandler
is directly added to rootLogger
In LoggingDefault()
. The rootLogger
should be consider as a internal placeholder for the whole logging hierarchy, if you need a logger to do some logging, please call GetLogger()
with non-empty name and call SetPropagate(false)
to disable the propagation. Then you could use the returned logger as the 'root' logger and add handlers to it.
The Apply(Json|Xml)*ConfigFile()
interfaces are just wrapper functions to DictConfig()
, so there is no need to call them both, or call DictConfig()
many times on initialization. And all the handlers and formatters have no id or unique name for management or replacement. So the behavior of DictConfig
is to "add" config but not to "replace", as the user should do the initialization in only one call to DictConfig
. This is consistent with the Python logging
package.
I got your point of view. So, unfortunatelly is really useless to my task :(
I need some way to dynamically reconfigure logging configuration.
My daemon is handling SIGHUP signal, and on SIGHUP reconfigure daemon (without stopping).
It is very important on production environment.
I think, we need some solution for dynamic REconfiguration, which REPLACE actual.
Hi @zamotivator ,
I don't get the clear picture of "dynamic reconfiguration". Could you clarify a little bit.
There are 3 classes in go-logging
, logger, handler and formatter. We could replace the formatter for handler in the fly by calling SetFormatter()
, and get/add/remove handler for logger in the fly by calling GetHandlers()/AddHandler()/RemoveHandler()
. And there are interfaces that we could reset and re-initialize everything(construct a new log hierarchy) in log facility. I'm not sure what is missing for reconfiguration in your task.
There is no update on this issue over 2 months. I assume the problem was solved and close this issue now.