Rather than rely on environment variables at runtime, I'd like to compile a debug or release version with non-error log messages stripped out completely.
Is it possible to change the log level for an application in the Cargo.toml
or via cargo
/rustc
command line arguments?
For each service that you have running in BMC Atrium Discovery, you can dynamically change the log level without having to restart the appliance.
To change log levels as a root user, perform the following: To enable debug logging, run the following command: /subsystem=logging/root-logger=ROOT:change-root-log-level(level=DEBUG) To disable debug logging, run the following command: /subsystem=logging/root-logger=ROOT:change-root-log-level(level=INFO)
I don't believe that the log crate has exactly the requested functionality built in.
There is a way to statically set the logging level. If you compile the log
crate with any of these Cargo features, the log level will be capped at that point:
release_max_level_off
release_max_level_error
release_max_level_warn
release_max_level_info
release_max_level_debug
release_max_level_trace
You can drop the release_
off for the same functionality in non-release builds.
It's possible that the optimizer will see this static value and remove code that is impossible. If that happens, then you should be good to go!
If you want to be absolutely certain, you could approximate it by creating your own conditional compilation with Cargo features. Here's a simple example that will print a value or not, depending on whether the feature is enabled:
#[cfg(not(feature = "slim"))]
macro_rules! my_info {
($x: expr) => { println!("{:?}", $x) }
}
#[cfg(feature = "slim")]
macro_rules! my_info {
($x: expr) => { }
}
fn main() {
my_info!("Hello, world!");
}
This has a corresponding stanza in Cargo.toml
:
[features]
slim = []
And when you compile / run your program, you can pick which features there are:
$ cargo run
Running `target/debug/log`
"Hello, world!"
$ cargo run --features=slim
Running `target/debug/log`
$
Then it's just a matter of wrapping the logger macros in your own conditionally-compiled macros:
#[cfg(not(feature = "slim"))]
macro_rules! my_info {
($($arg: tt)*) => { info!($($arg)*) }
}
#[cfg(feature = "slim")]
macro_rules! my_info {
($($arg: tt)*) => { }
}
Running yields:
$ RUST_LOG=info cargo run
Running `target/debug/log`
INFO:log: Hello, world!
$ RUST_LOG=info cargo run --features=slim
Running `target/debug/log`
$
For a bit of editorial, I disagree with doing this. When something breaks, that's when you most want the ability to log something. In the majority of cases, I don't believe that the cost of the check of the boolean would be expensive enough to warrant this. I also doubt that you will have megabytes of text in most cases.
There are always exceptions - maybe you need to log something in a tight loop, or you have to compile to fit on a microcontroller with limited space.
Note that I didn't try to couple stripping out the log messages with the concept of a "release" build. I guarantee that there are times you will want a release build with these messages, so it's better to make those two ideas orthogonal.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With