AWSの話題を中心に、日々の業務やプログラミングの徒然を綴るエンジニアブログです。

HANDS LAB

HANDS LAB ENGINEERS BLOG

ハンズラボエンジニアブログ

DynamoDB PHP SDKのMarshalerクラスを使った時にはでかい数値に気をつける

Pocket

下記のblogで紹介されているように、AWS PHP SDKの 2.7.7 から PHPの型とjsonとDynamoDBの型の相互変換を行うクラス、Marshaler が追加されています。

DynamoDB JSON and Array Marshaling for PHP

この Marshaler クラスを使うと、型変換が行われるため、数値型に大きな値を入れている場合に注意が必要です。

以下に例を示します。

id = 1 のレコードに number = 9223372036854775808 という値が入っているレコードを取り出してみます。

結果

9223372036854775808 という値が取り出せました。

これを Marshaler でPHPの型に戻してみます。
使用するメソッドは、unmarshalItem です。

結果

9.2233720368548E+18 になってしまいました。/(^o^)\ ナンテコッタイ

原因

PHPでの整数の最大値はPHP_INT_MAXで定められており、9223372036854775807 になっています。(64bitの場合)
それを超えた数字を整数に変換しようとすると、指数表記になってしまいます。

参考:PHP>マニュアル>言語リファレンス>型>整数

一方、DynamoDBの方は、下記ドキュメントにて、最大 38 桁の精度とあるように、 99999999999999999999999999999999999999 まで投入できます。

参考:DynamoDB データモデル

この辺りの相互変換は、言語側の精度に依存する形になると思うので、使っている言語側の仕様を確認しておいた方がよさそうです。
たしか、rubyの場合には BigDecimal に変換されたと思います。

参考

Pocket