RustでWindowsのファイル時刻を扱うためのライブラリのnt-time
を開発したので紹介します。
ファイル時刻とは
nt-time
クレートについて説明する前に、ファイル時刻について説明します。
ファイル時刻は、1601年1月1日0時0分0秒 (UTC) から経過した100ナノ秒間隔の数を表す64ビット整数値で、Unix系のシステムにおけるUNIX時間に相当するものです。
ファイル時刻は、NTFSや7zのタイムスタンプとして利用されています12。
ファイル時刻は、Win32 APIではGetSystemTime()
を使用することで取得することができ、.NETではDateTime.ToFileTime()
を使用することで取得することができます。
最大値は60056年5月28日5時36分10秒955161500 (UTC) ですが、WindowsのAPIでは最大値は64ビット符号付き整数の最大値に制限されます。
nt-timeとは
nt-time
クレートはこのファイル時刻を扱うためのライブラリです。
ファイル時刻を表す型としてnt_time::FileTime
を定義しています。
この型はNew Type Patternを利用しており、内部的にはu64
です。
FileTime
は以下のような機能を実装しています。
core::time::Duration
などとの加算や減算std
やtime
クレートやchrono
クレートの時間を表す型との相互変換- UNIX時間との相互変換
- Serdeを利用したシリアライズとデシリアライズ
コード例
|
|
定数
以下の3つの定数を定義しています。
FileTime::NT_TIME_EPOCH
- NT time epoch (1601-01-01 00:00:00 UTC) を表しますFileTime::UNIX_EPOCH
- Unix epoch (1970-01-01 00:00:00 UTC) を表しますFileTime::MAX
-FileTime
が表すことのできる最大値 (+60056-05-28 05:36:10.955161500 UTC) を表します
演算
FileTime
はAdd
を実装しているので、core::time::Duration
やtime::Duration
の値を加算することができます。
Sub
ではこれらに加えてstd::time::SystemTime
などの時間を表す型との演算を実装しているので、FileTime
からこれらの型の値を減算することができます。
core::time::Duration
との演算ではオーバーフローした場合に飽和するメソッド (FileTime::saturating_add()
、FileTime::saturating_sub()
) やNone
を返すメソッド (FileTime::checked_add()
、FileTime::checked_sub()
) を定義しています。
また、PartialEq
とPartialOrd
も実装しているので、これらの期間や時間を表す型との同値関係と順序関係を比較することができます。
相互変換
FileTime
はFrom
やTryFrom
によってstd::time::SystemTime
、time::OffsetDateTime
、chrono::DateTime<chrono::offset::Utc>
と相互変換することができます。
これらは変換元の値が変換先の型の範囲外の場合はTryFrom
を使うようになっています。
また、u64
の値からFileTime
を作成すること (FileTime::new()
) とその逆 (FileTime::to_raw()
) にも対応しています。
UNIX時間との相互変換については、秒単位とナノ秒単位に対応しています3456。
シリアライズとデシリアライズ
Serdeを利用してISO 8601形式、RFC 2822形式、RFC 3339形式、UNIX時間との間でシリアライズとデシリアライズを行うことができます。
|
|
終わりに
RustでWindowsのファイル時刻を扱うためのライブラリのnt-time
クレートを紹介しました。
詳細なドキュメントはDocs.rsで確認することができます。
気に入ってもらえたらsorairolake/nt-timeでStarを付けてもらえるとありがたいです。
nt-time
クレートの改善のためにIssueやPull Requestもお待ちしています。
https://learn.microsoft.com/ja-jp/windows/win32/sysinfo/file-times ↩︎
https://py7zr.readthedocs.io/en/v0.20.5/archive_format.html#filetime ↩︎
https://docs.rs/nt-time/0.5.1/nt_time/struct.FileTime.html#method.to_unix_time ↩︎
https://docs.rs/nt-time/0.5.1/nt_time/struct.FileTime.html#method.to_unix_time_nanos ↩︎
https://docs.rs/nt-time/0.5.1/nt_time/struct.FileTime.html#method.from_unix_time ↩︎
https://docs.rs/nt-time/0.5.1/nt_time/struct.FileTime.html#method.from_unix_time_nanos ↩︎