Bonjour à tous,
J'essaie d'écrire une classe pour effectuer mes logs.
J'aimerais avoir un découplage fort entre ma classe Logger et les classes émettant les messages devant être loggés. Pour cela, je passe en paramètre à ces classes une référence de std::ostream qui sera en réalité un Logger.
Voilà en gros l'idée :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2 CommandSender::CommandSender(std::ostream & logger, std::ostream & errorLogger);Pour rendre ceci possible, il faut que ma classe Logger dérive de std::ostream. Voilà ce que ça donne :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3 Logger logger, errorLogger; CommandSender sender(logger, errorLogger);
Je surcharge l'opérateur <<, qui appelle une méthode effectuant une écriture bufferisée et thread-safe dans un fichier (mais là n'est pas le propos).
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 class Logger: public std::ostream { template<class T> friend Logger& operator<<(Logger& out, T val); public: Logger(const std::string& filename); private: /*...*/ }; template<class T> Logger& operator<<(Logger& out, T value) { /*...*/ return out; }
Donc, tout ceci me semblant correct, je teste basiquement :
Pouf, aucun problème, ça roule.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3 Logger logger("default.log"); logger << "test";
Par contre, si j'essaie d'utiliser un objet logger dans un contexte polymorphe :
Patatra ! Erreur de segmentation, plantage, explosion, incendie, 12 morts dont 1 grièvement.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4 Logger logger0("default.log"); std::ostream& logger = logger0; logger << "test";
J'ai essayé quelques petits trucs pour m'en sortir, mais je ne vais pas en dire plus, tout cela fait déjà beaucoup à lire, et je me plante peut-être dés la base.
Quelqu'un pourrait-il m'aider ?
Partager