Qiita Teams that are logged in
You are not logged in to any team

Log in to Qiita Team
Community
OrganizationAdvent CalendarQiitadon (β)
Service
Qiita JobsQiita ZineQiita Blog
10
Help us understand the problem. What is going on with this article?
@Dsuke-K

Rustでのロギング

More than 1 year has passed since last update.

Rustで使えるロガーを調べてみます。この記事ではいくつかある実装のうち、

  • env_logger
  • simple_logger
  • stderrlog

を動かしてみました。

log crate

Rustのlog crateinfo!等のマクロが定義されてますが、用途に応じてその実装を選べる作りになっているようです。

log実装の一覧

Available loggin implementationsの転載です。

  • Simple minimal loggers:
    • env_logger
    • simple_logger
    • simplelog
    • pretty_env_logger
    • stderrlog
    • flexi_logger
  • Complex configurable frameworks:
    • log4rs
    • fern
  • Adaptors for other facilities:
    • syslog
    • slog-stdlog_

env_logger

logの実装でどれを使えばいいのか分かりませんが、crates.ioによるとenv_loggerのダウンロード数が圧倒的に多いようです。

#[macro_use]
extern crate log;
extern crate env_logger as logger;

use log::Level;
use std::env;

fn main() {
    env::set_var("RUST_LOG", "info");
    // env::set_var("RUST_LOG", "trace");
    logger::init();

    debug!("this is a debug {}", "message");
    error!("this is printed by default");

    if log_enabled!(Level::Info) {
        let x = 3 * 4; // expensive computation
        info!("the answer was: {}", x);
    }
}

実行ファイルの名前がmainとすると、次のような実行結果が得られます。env_loggerのデフォルトログレベルはErrorで、標準エラー出力に書き出されます。ソースコードの中で環境変数のRUST_LOGInfoに設定しているため、ここではerrorinfoは出力されていますが、debugは何も出ませんね。

$ ./main
[2019-03-24T14:16:11Z ERROR log_sample] this is printed by default
[2019-03-24T14:16:11Z INFO  log_sample] the answer was: 12

simple_logger

crateの名前の通り、シンプルに標準出力に書き出します

#[macro_use]
extern crate log;
extern crate simple_logger as logger;

use log::Level;

fn main() {
    // logger::init().unwrap();
    logger::init_with_level(Level::Info).unwrap();

    debug!("this is a debug {}", "message");
    error!("this is printed by default");

    if log_enabled!(Level::Info) {
        let x = 3 * 4; // expensive computation
        info!("the answer was: {}", x);
    }
}

実行ファイルの名前がmainとすると、次のような実行結果が得られます。simple_loggerのデフォルトログレベルはtraceですが、そのレベルは簡単に変更できるみたいです。多くのloggerの実装ではこのようなinit関数が用意されているとのことです。

$ ./main
2019-03-24 23:32:48 ERROR [log_sample] this is printed by default
2019-03-24 23:32:48 INFO  [log_sample] the answer was: 12

stderrlog

もう一つくらい、stderrlog試してみます。

#[macro_use]
extern crate log;
extern crate stderrlog as logger;

use log::Level;

fn main() {
    logger::new()
        .module(module_path!())
        .verbosity(2)
        .init()
        .unwrap();

    debug!("this is a debug {}", "message");
    error!("this is printed by default");

    if log_enabled!(Level::Info) {
        let x = 3 * 4; // expensive computation
        info!("the answer was: {}", x);
    }
}

実行結果は次のようになります。タイムスタンプを入れたりもっと細かい設定もできますが、ここではサボっています。実行結果は次のようになります。

$ ./main
ERROR - this is printed by default
INFO - the answer was: 12

注意点としては、stderrlogのverbosityがログレベルに相当するのですが、logcrateのLovelとは微妙にずれているのでverbosity(Level::Info as usize)等とすると期待する結果とずれてしまいました。ソースコードで確認しといたほうが良さそうですね。

補足(?)

use ... as loggerとすればダックタイピングになるかなと期待したのですが、実装ごとに初期化に必要な手順が異なってるのでほとんど意味がありませんでしたorz

参考にした記事など

コード

log_sample

10
Help us understand the problem. What is going on with this article?
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away

Comments

No comments
Sign up for free and join this conversation.
Sign Up
If you already have a Qiita account Login
10
Help us understand the problem. What is going on with this article?