
【Candid】インターネットコンピューターのインターフェース
- Candidとはなんなんでしょう。
試しにインターネットコンピューターでプログラミングをしてみようと思っている方向けの記事です。
Candidはインターネットコンピューターの言語の一つとして紹介されていますがRustやMotokoとの役割の違いについて触れ、実際の使われ方を紹介していきます。
目次
Candidはインターフェース記述言語
最初に結論から。
Candidはインターフェース記述言語(IDL)としてインターネットコンピューターに用意されました。
MotokoとRustはプログラミング言語として使われているのとは異なりますね。
Candidの使われ方としてはMotokoとCandid、RustとCandid組み合わせで使っていきます。
ちなみに拡張子は.didです。
姿かたちはこのようなもの。
※インターネットアイデンティティのdidファイル抜粋
個人的にはかなり直観的なインターフェースかなと思ってます。見た目からもプログラムのように読めるので初見でもある程度理解できる方も多いのではないでしょうか。
処理の記述がないのでシンプル。まさに「インターフェース」ですね。
インターフェース記述言語(IDL)とは?
そういえばIDLってなんだっけ?
現状のWebプログラミングで使用されているIDLで有名なのはRESTやWSDLですね。JSONやXML形式で記述されて使われています。ことなるアプリ間でも連携するために使用されています。
RESTではなくCandid
すでに実績十分なIDLがあるのでRESTやWSDLでもよいような気がしますが、新しくCandidを開発した理由は公式ドキュメントにも書かれています。
抜粋すると
- データだけでなくサービス内容も記述できる
- サーバー側の型とマッピングしやすい
- インターフェースをアップデートするルールが定義できる
- 関数を参照にとれる
(一部REST・WSDLでもあるような気もしますが・・・)
読み取りに使用されるquery、そしてデータを更新すうるupdateに対応することができるので、インターネットコンピューターの機能をサポートするのに最適なIDLをつくった、ということでしょう。データだけではなくサービスや関数を引数にとれたりするのは面白いですね。
Candidの役割
Candid役割の一つはクライアント生成ですね。これはRESTやWSDLにも存在する機能。公開されているインターフェース仕様を読み込むことでサポートされているプログラムにクライアントを自動生成してくれます。

helloサンプル・プログラミングを実行してみると以下のように

declarationsディレクトリの下に.didファイル元に.d.tsと.jsファイルも生成されるので、あとはそれを利用するだけでスマートコントラクトが可能です。
Candidの使用方法
Candidは使用するプログラミング言語によって扱いが変わります。それぞれ見てみましょう。
motokoは自動生成
はい。MotokoではCandidは自動生成です。つまりやることはありません。dfx deployでキャニスターを展開するときなどに、Motokoのコードから.didファイルを生成してくれます。
RustのCandidの記述
Rustの場合はMotokoとは違い自分で記述していく必要があります。
Rustでプロジェクトを作成するとlib.rsのある階層にdidファイルも生成されます。
Rustのコードのquery,updateに合わせてdidファイルに書き込みます。
なお、declarationsディレクトリにあるdidには書かないようにしましょう。
※declarationsは別のプロジェクトが参照する先として使われるアウトプット用です。
実際の記述
具体的な書き方は公式ドキュメントに記載があるのでご確認ください。基本はここにあります。
https://smartcontracts.org/docs/current/references/candid-ref
本記事では、Rustのコードと対応する書き方について少しふれておきます。
RustとCandidの対応
インターネットコンピューターのスマートコントラクトの特徴である
- update
- query
を取り扱ったのち
使用頻度が高いキーワードを紹介したいと思います。
- record
- vec
- variant
- opt
前提
cargoの依存関係には次のパッケージが含まれている前提で話していきます。
- candid
- ic-cdk
- ic-cdk-macros
- serde
query
helloサンプルにもあるので引用しましょう。didファイルにはgreetが用意されています。特徴は「query」が最後にあること。
対応するrustのコードはこちら。
ic_cdk_macrosにあるqueryマクロを使えばOK。
update
つづいてupdateです。
updateはcandidではqueryを外せばOKです。
対応するrustのコードはこちら。queryからupdateに変えておきます。
メソッド名のリネーム
「name」でメソッドをリネームすることができます。query、update共通です。
rustの命名規則からCandidで公開したい外部向けの命名規則に変換できますね。
recordと構造体
構造体に対応するrecordです。まずはCandid側をみてみましょう。
recodeに対応する構造体はこちら。
derive属性にCandidTypeを入れておきます。
フィールドのリネーム
メソッド名と同じく、フィールド名もリネーム可能です。ただic_cdk_macrosではなく、使用するのは「serde」です。
vecと配列
配列に対応するのはvecです。例えばBookの配列を返すCandidがこちら。
対応するrustのコードはこちら。
rustの可変配列もVecなので、割とまんまですね。
variantと列挙型
メソッドの実行結果によってことなる型が返したい場合に使用されるのがvariantです。リクエストが不適切なときにエラーオブジェクトを返却したいときなどに使用できます。
対応するrustのコードはこちら。上記はtrueを渡せばBookが返され、falseを渡すとエラーメッセージを返すメソッドです。
variantには列挙型で対応です。
optとOption
optはNullになる可能性がある型を扱います。
対応するrustのコードはこちら。variantの例と似た形で、単にNoneを返すかBookを返すか単純なものです。
rustのOptionは列挙型なので本質的にはvariantと同じでしょうが、Nullを扱えるインターフェースは高頻出なので専用でoptが用意されています。
まとめ
Motokoが自動でRustが手動なのは気になりますが、いずれアップデートでRustも自動生成にならないかなと期待しています。
- Candidはインターネットコンピューターで使用されるインターフェース記述言語(IDL)
- Motoko使用時は自動生成、Rustは手動生成
つまみ食い的な記事なので、まだ取り扱っていないcandidの項目がちらほらあります。funcやらprincipal等が用意されているので折をみて、この記事で更新しようかと思います。
ちなみに、funcはdfx canister callでは動くんですけど、candid_uiで微妙な動きをしたりするので、動作確認にはまだ注意が必要です。