いるねすのブログ

働きたくない系SEが無駄に遊んだ記録

Hyperledger Fabric と戯れる part.4

Writing Your First Application (つづき)

前回に続き、Writing Your First Application チュートリアルをすすめてく。

hyperledger-fabric.readthedocs.io

node query.js

前々回あたりからチラホラ query とか invoke とか普通に言ってたが、基本的に query は参照などの read only なアクセス、invoke は追加・更新などの write を伴うアクセスに使う。

(実際のところ invoke で read only な事とかも出来たりするので不正確だったりするけど、まあさておき。)

  1. ../../basic-network/connection.jsonccp として読み込み
    • 前回と同じ
    • 以下、mychannel へのアクセスをするために使用している
  2. new FileSystemWallet() として ./wallet を使用
    • 前回と同じ
    • これまでの操作により、 ./wallet には adminuser1 の Identity が存在している
  3. gateway.connect(ccp, {wallet, identity: 'user1' ...})user1 としてゲートウェイに接続
    • admin でなく user1 として接続する点以外は前回と同じ
    • これで、各ノードに対し wallet を使用して接続し、 clientuser1@org1.department1 として振舞える
  4. network = await gateway.getNetwork('mychannel')mychannel へのアクセスを獲得
  5. contract = network.getContract('fabcar') で ChainCode fabcar へのアクセスを獲得
  6. result = await contract.evaluateTransaction('queryAllCars') で ChainCode の queryAllCars() をコール

で、肝心の ChainCode 側を見ていく。ChainCode 側のドキュメントはこちら。

fabric-shim.github.io

lib/fabcar.js が本体。 (index.js もあるけど、module の export しかしてない)

class FabCar extends Contract のように fabric-contract-api.Contract を継承しているクラスのメソッドがそのまま SDK 側から呼べるようになっている。

メソッドは Context クラスを第一引数に必ず取り、以降の引数(省略可能) を取れば、クライアントSDK側からデータを受けとることができる。

詳しくはこちらを参照。

fabric-shim.github.io

なお、Context の class API にはクラス変数の説明がないが上記ドキュメントの「Structure of the Transaction Context」を読めばわかる通り、ctx.stubChainCodeStub オブジェクト、 ctx.identityClientIdentity オブジェクトをそれぞれ取得できる。

やってることは単純にこれだけ。

  1. FabCar.queryAllCars(ctx)

なお、取得したデータは startFabric.shinvoke していた、initLedger() で格納している。 せっかくなので内容を見てみるけど、queryAllCars 以上にやってる事は単純。

  1. FabCar.initLedger(ctx)

node invoke.js

query.js と diff を取るとわかるが、違いは最後の contract.evaluateTransaction('queryAllCars')contract.submitTransaction('createCar', ...) になっている事と、明示的に gateway.disconnect() しているところのみ。

  • evaluateTransaction -> submitTransaction
  • FabCar.createCar()
    • 引数で指定された内容で Car オブジェクトを作って、それを ctx.stub.putState() で保存してるだけ
  • gateway.disconnect() の実行
    • コメントアウトして実行してみるとわかるけど、これをやらないと invoke.js は永久に終わらない。
    • 不可解だが、 query にこの行を足しても問題は起きないし、極めて一般的な感覚として connect したら必ず disconnect するべきと思うので、そういうもんだと思っておく

おしまい

話長くなるかと思ったけど、すげえ短かった。

次回は Commercial paper tutorial をやる予定。

hyperledger-fabric.readthedocs.io