カタパルトのタイムスタンプ


はじめに

nem2のslackでこのようなコメントを見かけたので記事を書いてみようと思いました。

カタパルトと時刻

カタパルトのデータにおける時刻は、日常で使っているものとは少し異なります。

APIの内容を見てみると、111100670230という数字が入っています。

ところで、unixtimeといって、1970年1月1日0時0分0秒(世界標準時)からの経過秒数として時刻を表すものがあります。

これと考え方は同じです。

参考Unixtime相互変換ツール

fushicho 2まで

2016年4月1日 0時0分0秒(世界標準時)からの経過ミリ秒として時刻を表します。

この日付は、unixtimeで1459468800となります。これは秒であることに注意して、カタパルトのタイムスタンプからunixtimeに変換するには、

( 1459468800000 + <cataput timestamp> ) / 1000

となります。

以下のような場合、1459468800000 + 111100670230 = 1570569470230となり、これを1000で割ると2019年10月09日 06時17分50秒(日本標準時)という結果になります。

fushicho 3から

2019年11月11日 0時0分0秒(世界標準時)からの経過ミリ秒として時刻を表します。

この日付は、unixtimeで1573430400となります。これは秒であることに注意して、カタパルトのタイムスタンプからunixtimeに変換するには、

( 1573430400000 + <cataput timestamp> ) / 1000

となります。

以下のような場合、1573430400000 + 2594265200 = 1576024665200となり、これを1000で割ると2019年12月11日 09時37分45秒(日本標準時)という結果になります。

epochAdjustment

fushicho 3から、基準となるタイムスタンプが変更できるようになりました。設定はここにあります。

epochAdjustment = 1573430400sとあり、2019年11月11日のunixtimeが書かれています。

変更してみる

これを変更してみます。ちょうと一か月進めて、2019年12月11日 0時0分0秒(世界標準時)にしてみます。

epochAdjustment = 1576022400s

そして真っ新な状態でカタパルトを起動してみます。

ブロック番号2のAPIデータです。タイムスタンプには52812128という値が入っています。

これから時刻を求めると、以下のような式になります。2019年12月11日 14時40分12秒(世界標準時)という結果になりました。

1576022400000 + 52812128 = 1576075212128

そして、このブロックが発生した時刻をログから見てみます。2019-12-11 14:40:12.129085とあります。

peer-node-0_1             | 2019-12-11 14:40:12.129085 0x00007fdece594700: <info> (src::ScheduledHarvesterTask.cpp@35) successfully harvested block at 2 with signer 0F50BBC37BFF7523128C41F60EE93A9F094C933E95DDD518B7015466142EFBEA

一致しているのがわかります。

Deadline

Deadlineにも影響がある、という書き込みを見たのでこちらもやってみます。

fushicho 2まで

例として、Cowのトランザクションのペイロードです。

A5000000 // size
894A829717A6627C108BD69D56A188659C403A4E2C0CEDBB35F856AFD57713E9ACA553C68803E56E39683A9D18CBAF258BFCE043724C56175C53E425727C050F // signature
AC1A6E1D8DE5B17D2C6B1293F1CAD3829EEACF38D09311BB3C8E5A880092DE26 // signer public key
0390 // version
5441 // type
0000000000000000 // fee
F475D61517000000 // deadline
90FA39EC47E05600AFA74308A7EA607D145E371B5F4F1447BC // recipient address
0100 // msg size includes mgs type
01 // num mosaics
00 // msg
44B262C46CEABB85 // mosaic 1 id
0000000000000000 // mosaic 1 amount

deadlineはF475D61517000000となっています。これは10進数で99150624244を意味します。

この値はunixtimeとしては小さすぎるため、カタパルト用のタイムスタンプだと推測できます。

0x0000001715D675F4 = 99150624244

この値をunixtimeに直してみると、2019年05月23日 22時50分24秒(日本標準時)になります。

( 1459468800000 + 99150624244 ) / 1000 = 1558619424.244

このトランザクションを実際にいつ作ったかは覚えていませんが、妥当な日付だと思います。

fushicho 3から

試しにトランザクションを作ってみました。ペイロードを分解してみるとこんな感じです。

BF00000000000000 // size
60110DD8734B2154F45AA7021E2B144776C4A70E371536C622F4EC0B9830E01D6EBDCA92A6E096BE73E6C906E4C74E4597545BD5D54606DD255EB64679CCB50E // signature
12388D7D96E4BC5F264B5EF5F4D4BB1571BB863616E8BEDC1D90A3BD02461326 // signer public key
00000000 // reserved
0198 // version
5441 // type
204E000000000000 // fee
61B1959E00000000 // deadline
98DC6FD55C9A83416D9617CEDFDA88BACE0A84F2B95EC74CB7 // recipient address
01 // num mosaics
0F00 // msg size
00000000 // reserved
44B262C46CEABB85 // mosaic 1 id
8096980000000000 // mosaic 1 amount
0057656C636F6D6520546F204E454D // msg type + msg

deadlineは61B1959E00000000となっています。これは10進数で2660610401を意味します。

0x000000009E95B161 = 2660610401

この値はunixtimeとしては小さすぎるため、カタパルト用のタイムスタンプだと推測できます。

この値をunixtimeに直してみると、2019年12月12日 04時03分30秒(日本標準時)になります。

( 1573430400000 + 2660610401 ) / 1000 = 1576091010.401

トランザクションを作ったのが2019年12月12日 01時(日本標準時)ごろなので、妥当かなと思います。

あれ、Deadline.create()って+2時間じゃなかったっけ。

(追記)これはバグだったようです。nem2-sdkが内部でepochAdjustmentの値を保持しているのですが、それが間違いだったようです。

(追記)ペイロードを作成したのは、Node.jsの[email protected]を使用しました。

(追記)カタパルトのタイムスタンプをREST APIから取得する

/node/timeのエンドポイントから、カタパルトのタイムスタンプが取得できます。例えば、+2時間であればこの値に7200000を足すとよさそうです。

おわりに

カタパルトのタイムスタンプの表現方法と、計算方法を書きました。

fushicho 3から基準が変わったので、計算方法も少し変わったことがわかりました。

また、fushicho 3では、その基準も変えられることがわかりました。