Skip to content

Systemd log format activable via env var #349

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
RCasatta opened this issue Jan 10, 2025 · 14 comments · May be fixed by #358
Open

Systemd log format activable via env var #349

RCasatta opened this issue Jan 10, 2025 · 14 comments · May be fixed by #358

Comments

@RCasatta
Copy link

I updated my program with something along the lines of https://github.com/rust-cli/env_logger/blob/main/examples/syslog_friendly_format.rs to have a systemd friendly logging, however when I use other binaries using env_logger usually the same logic is not available, can we have it enable-able by default in env_logger?

ie if RUST_LOG_STYLE=SYSTEMD the default formatting is changed with the systemd friendly one without having to change the downstream lib

@djugei
Copy link

djugei commented Mar 31, 2025

specifically for systemd its quite easy to automatically detect being run as a daemon.
i am sure that its possible for other service managers/init systems too, but to the best of my knowledge systemd simply is the main one by far.

@epage
Copy link
Contributor

epage commented Mar 31, 2025

@djugei in #357, you also mentioned the idea of having a separate format string.

What value would users get by having all of this baked into env_logger::Logger vs having a way to compose multiple loggers, including a syslog logger?

@djugei
Copy link

djugei commented Mar 31, 2025

defaults matter a lot. developers want to run their binaries in terminal and see timestamps, users want to run applications as daemons and see timestamps only once. people simply will not have a more complex setup.

and this is a real issue, i am sure @RCasatta has observed this in a rust application they were running, and so have i.
ofc if the app is open source we can go around and make prs for every single project.
or just one here.
the later seems like the smarter option.

@epage
Copy link
Contributor

epage commented Mar 31, 2025

Sorry, I missed read this (being used to multi-platform system logs being rendered out of band from stdout). Looking back over #358, this is just about changing the output format.

env_logger then auto-detects if its running as a daemon

I am open to auto-detection.

env_logger then auto-detects if its running as a daemon, with an override available.

I don't think we need a specific variable to control the auto-detection: we can expose a function that matches the custom format signature and people can customize things as they want.

ie if RUST_LOG_STYLE=SYSTEMD the default formatting is changed with the systemd friendly one without having to change the downstream lib

That is specific to binaries, not libraries, and I assume binaries will generally know they will be run in a daemon mode to support something like this.

#358

The format used in this was

                Box::new(|buf, record| {
                    writeln!(
                        buf,
                        "<{}>{}: {}",
                        match record.level() {
                            Level::Error => 3,
                            Level::Warn => 4,
                            Level::Info => 6,
                            Level::Debug => 7,
                            Level::Trace => 7,
                        },
                        record.target(),
                        record.args()
                    )
                })

Where is the relevant documentation for this? My initial searches come up short.

@djugei
Copy link

djugei commented Apr 1, 2025

the format was literally copied from the example in this repository, after cross-checking with the relevant manpages to verify that this is actually a valid way to log to syslog. there is more valid ways, for example by providing a timestamp, but that gets auto-filled in by the syslog.
syslog format is.. semi-standardtized but that setup seems to work for journald.

@RCasatta
Copy link
Author

RCasatta commented Apr 1, 2025

I confirm I use it with systemd and it works. For example you can filter error logs via:

journalctl -u unit -p 3

@epage
Copy link
Contributor

epage commented Apr 1, 2025

the format was literally copied from the example in this repository, after cross-checking with the relevant manpages to verify that this is actually a valid way to log to syslog. there is more valid ways, for example by providing a timestamp, but that gets auto-filled in by the syslog.
syslog format is.. semi-standardtized but that setup seems to work for journald.

Was not aware of that example, thanks!

In that case, for anything we do, we should update or remove that example. We'll also need to ensure people have a good way of discovering this functionality.

@djugei
Copy link

djugei commented Apr 2, 2025

I confirm I use it with systemd and it works. For example you can filter error logs via:

journalctl -u unit -p 3

just to be explicit here: you have tested #358 and it solves your usecase?

@djugei
Copy link

djugei commented Apr 2, 2025

In that case, for anything we do, we should update or remove that example. We'll also need to ensure people have a good way of discovering this functionality.

i have updated the example. discoverability is not worse now, and also somewhat optional as it should just work, thats the magic of good defaults.
as mentioned in #358 (comment) please do advise where adding documentation would be useful.

@RCasatta
Copy link
Author

RCasatta commented Apr 4, 2025

I confirm I use it with systemd and it works. For example you can filter error logs via:

journalctl -u unit -p 3

just to be explicit here: you have tested #358 and it solves your usecase?

I was referring to the log format, I didn't test with #358

@epage
Copy link
Contributor

epage commented Apr 9, 2025

@djugei what are your thoughts on the plain I laid out in #349 (comment)?

To re-summarize

  • Auto-detect we are running as a service and switch the format
  • Provide a syslog_format and ConfigurableFormat, allowing people to remove the auto-detection by passing ConfigurableFormat as a custom format, or providing their own auto-detection by wrapping syslog_format and ConfigurableFormat

The main question I have is whether we provide a syslog_format function or a SysLogFormat struct that then allows customization in the future.

@epage
Copy link
Contributor

epage commented Apr 9, 2025

From #358 (comment)

@djugei

i kinda want to slightly alter the log format, right now syslog contains

date host processname[process_id] processname::module:: message

i would like date host processname[process_id] ::module:: message better to reduce redundancy.

i am unsure what the easiest way to get the top level binary name is though. then it would be a simple .strip_prefix(name).

@epage
Copy link
Contributor

epage commented Apr 9, 2025

i am unsure what the easiest way to get the top level binary name is though. then it would be a simple .strip_prefix(name).

If I understand correctly, you are wanting to strip processname from the target?

Looks like log gets that from std::module_path!(). So I'm guessing that the standard library is just using the crate's name in which the log operation was invoked. So it mostly looks like the process name when inside of the binary and something else when outside which means we can't simply strip the first component before ::. It won't always match argv[0] / current_exe() either because a module name can be different than a binary name (e.g. foo_bar vs foo-bar.exe). Cargo sets CARGO_CRATE_NAME but we have to be built inside the users crate to access that.

Some solutions I see include

  • Add a strip_crate_name builder method to SysLogFormat
    • This requires manually constructing one. Maybe we could generalize this and also put it on ConfigurableFormat / Builder which will then strip it regardless of the format
  • Have a syslog_format!() which won't work with auto-detection
  • Leave this extra customization to users, like it is today

What I'm unsure of is how universal people would want this. While it is redundant, I could also see it being helpful when you have log messages coming from a variety of crates. This could also make writing of RUST_LOG filters difficult if you don't see the full target.

@djugei
Copy link

djugei commented Apr 17, 2025

#349 (comment)

That seems like a sensible approach though currently i am unsure to what extent customizing the syslog format is useful.
i will rebase and rework my pr in the comming days

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants