C Oracle Blockchain PlatformでのEVMを使用したSolidityスマート・契約の実行

Oracle Blockchain PlatformにチェーンコードとしてデプロイされたEthereum Virtual Machine (EVM)を使用してSolidityスマート・契約を実行できます。

EVMは、EthereumネットワークでSolidityスマートコントラクトを実行します。EVMは、Hyperledger Burrowプロジェクトを介して作成され、Hyperledger Fabricに統合されました。このプロジェクトでは、Hyperledger Fabric許可型ブロックチェーン・プラットフォームを使用して、SolidityなどのEVM互換言語で記述されたEthereumスマート・コントラクトと連携できます。

次のステップでは、プロビジョニングされたOracle Blockchain PlatformでSolidityスマート・コントラクトを実行するプロセスの概要を示します:
  1. Oracle Blockchain PlatformコンソールからEVMチェーンコード・パッケージをダウンロードします。
  2. EVMチェーンコードをチャネルにデプロイします。
  3. Remix IDEを使用して、Solidityスマートコントラクトのバイトコードを生成します。
  4. スマート・コントラクト・バイトコードをデプロイ済EVMチェーンコードにデプロイします。トランザクションを送信するには、デプロイメントから返されたアドレスを使用します。
このトピックのステップは、Oracle Blockchain Platformコンソールから使用可能なEVMチェーンコード・パッケージでテストされており、他のリリースでは動作しない可能性があります。

ノート:

チェーンコードが以前にHyperledger Fabric v1.4.7インスタンスにインストールされている場合、インスタンスがHyperledger Fabric v2.xにアップグレードされると、そのチェーンコードは期待どおりに機能し続けるはずです。

EVMチェーンコードおよびFab3パッケージのダウンロード

Oracle Blockchain Platformコンソールの「開発者ツール」タブで、「アプリケーション開発」ペインを開き、EVMチェーンコード・パッケージのダウンロードをクリックします。ファイルをダウンロードするには、管理者ユーザーである必要があります。

Oracle Blockchain PlatformでのEVMチェーンコードのデプロイ

EVMチェーンコード・パッケージをダウンロードしたら、Oracle Blockchain Platformにデプロイします。

  1. Oracle Blockchain Platformコンソールにログインします。
  2. チェーン・コード・タブで、新規チェーン・コードのデプロイをクリックします。
  3. 「クイック・デプロイメント」を選択し、次の情報を入力します:
    • パッケージ・ラベル:チェーンコード・パッケージの説明を入力します。
    • チェーンコード言語: GoLang。
    • チェーンコード名:チェーンコードの名前を入力します。たとえば、solidityccと入力します。
    • バージョン: v1
    • Init-required:これを選択しないままにします。
    • チャネル:チェーンコードをインストールするチャネルを選択します。
    • 「パッケージ・チェーンコード」:選択を解除したままにします。
    • チェーンコード・ソース:前にダウンロードしたevmcc.zipパッケージをアップロードします。
    クイック配置ウィザードの詳細と、「パッケージ・ラベル」「チェーンコード名」などのフィールドに関する制限事項は、「クイック配置の使用」を参照してください。

情報を送信すると、EVMチェーンコードが「チェーンコード」タブに表示され、インストール対象として選択した各チャネルにデプロイ済のチェーンコードとしてリストされます。

Solidityスマート・契約の作成およびコンパイル

  1. ブラウザベースのRemix IDE (https://remix.ethereum.org/)を開きます。
  2. Solidityスマート・契約がすでに記述されている場合は、Remixにインポートします。
  3. Solidityスマート・契約が記述されていない場合は、RemixでSolidityファイル(.sol)を作成し、次のいずれかを実行します:
    • Solidityに精通している場合は、独自のスマート・契約ファイルを作成できます。
    • Solidityドキュメント(Solidity: Smart Contracts)に記載されているSimple Storageサンプル・コードを使用できます
    • この例で使用されているサンプル・コードを使用すると、入力としてstring nameを使用し、set(name)およびget()を使用して出力文字列と同じ内容を印刷できます:
      pragma solidity ^0.4.0;
      contract Myname {
          string public yourName;
      
          function set(string name) public {
              yourName = name;
          }
          function get() public view returns (string) {
              return yourName;
          }
      }
      
    デフォルトのコンパイラ・バージョンが、スマート・契約で指定したバージョンと一致しないというエラー・メッセージが表示される場合があります。
  4. スマート・契約をコンパイルします。Remixで「Solidity Compiler」パネルを開き、スマート・コントラクト・タブが開いていることを確認してコンパイル対象のファイルとして選択し、コンパイラ・バージョンを最新の4に設定します。Xバージョンで、「コンパイル」をクリックします。
    「Remix Compiler」ビューのテストSolidityスマート・契約のスクリーン・キャプチャ。

  5. ファイルのコンパイル後、「Bytecode」アイコンをクリックして、バイトコードをJSONドキュメントとしてクリップボードにコピーします。
  6. コピーしたバイトコードをテキスト・エディタに保存します。

スマート・契約の配置

コピーされたバイトコードでは、必要なセクションは"object"フィールドです。これは、サンプルのスマート・契約のEVMバイトコードです。
"object": "608060405234801561001057600080fd5b50610410806100206000396000f30060
8060405260043610610057576000357c0100000000000000000000000000000000000000000000000000000000900463
ffffffff1680634ed3885e1461005c5780636d4ce63c146100c5578063d97d663014610155575b600080fd5b34801561
006857600080fd5b506100c3600480360381019080803590602001908201803590602001908080601f01602080910402
602001604051908101604052809392919081815260200183838082843782019150505050505091929192905050506101
e5565b005b3480156100d157600080fd5b506100da6101ff565b60405180806020018281038252838181518152602001
91508051906020019080838360005b8381101561011a5780820151818401526020810190506100ff565b505050509050
90810190601f1680156101475780820380516001836020036101000a031916815260200191505b509250505060405180
910390f35b34801561016157600080fd5b5061016a6102a1565b60405180806020018281038252838181518152602001
91508051906020019080838360005b838110156101aa57808201518184015260208101905061018f565b505050509050
90810190601f1680156101d75780820380516001836020036101000a031916815260200191505b509250505060405180
910390f35b80600090805190602001906101fb92919061033f565b5050565b6060600080546001816001161561010002
03166002900480601f016020809104026020016040519081016040528092919081815260200182805460018160011615
6101000203166002900480156102975780601f1061026c57610100808354040283529160200191610297565b82019190
6000526020600020905b81548152906001019060200180831161027a57829003601f168201915b505050505090509056
5b60008054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190
818152602001828054600181600116156101000203166002900480156103375780601f1061030c576101008083540402
83529160200191610337565b820191906000526020600020905b81548152906001019060200180831161031a57829003
601f168201915b505050505081565b828054600181600116156101000203166002900490600052602060002090601f01
6020900481019282601f1061038057805160ff19168380011785556103ae565b828001600101855582156103ae579182
015b828111156103ad578251825591602001919060010190610392565b5b5090506103bb91906103bf565b5090565b61
03e191905b808211156103dd5760008160009055506001016103c5565b5090565b905600a165627a7a72305820a990d4
0b57c66329a32a18e847b3c18d6c911487ffadfed2098e71e8cafa0c980029",
一般に、EVMには次の2つの引数が必要です:
  • toアドレス。
  • イーサリアム・トランザクションで必要なinput

toフィールドはゼロ・アドレスで、inputは契約のコンパイル済EVMバイトコードです。したがって、invokeコマンドには2つの引数があります。最初の引数は、従来はチェーンコード内のファンクション名になっていましたが、0000000000000000000000000000000000000000になり、2番目の引数はSolidityスマート・コントラクトのバイトコードです。

  1. Solidityスマート・コントラクトをOracle Blockchain Platformにデプロイするには、次のRESTプロキシ・コールを実行して、2つの引数をEVMに送信します。
    {
        "chaincode": "<evmcc-ccid>",
        "args": [
            "0000000000000000000000000000000000000000",
            "<bytecode-of-the-smart-contract>"
        ],
        "timeout": 0,
        "sync": true
    }
    次の例では、cURLを使用して、Solidityスマート・契約をOracle Blockchain Platformsolidityccという名前でデプロイします:
    curl -L -X POST 'https://<hostname>:7443/restproxy/api/v2/channels/<channelname>/transactions' \
    -H 'Authorization: Basic dXNlcm5hbWU6cGFzc3dvcmQ=' \
    -H 'Content-Type: application/json' \
    --data-raw '{"chaincode":"<evmcc-ccid>","args":["0000000000000000000000000000000000000000","<bytecode-of-the-smart-contract>"],"timeout":0,"sync":true}'
  2. トランザクションのレスポンスpayloadは、デプロイされたコントラのアドレスです。この住所をコピーして保存します。契約住所は、スマート・契約機能の実行時に使用されます。
    「ペイロード応答」フィールドにスマート・契約住所が表示されたAPIコールおよびレスポンスの画面キャプチャ。
    この例では、スマート・契約住所は66b92979bb66d645371b3247177e4b2513cb9834です。
デプロイされたスマート・コントラクトと対話するには、次の2つの方法があります。
  1. メソッドおよび入力パラメータのハッシュ値を使用します。
  2. メソッド名と入力パラメータを直接使用します。

ハッシュ値を使用したスマート・コントラクトの操作

スマート・コントラクト・アドレスを取得した後、次のコールを使用して、RESTプロキシを介してデプロイ済スマート・コントラクトと対話できます。

関数を実行するには、呼出しトランザクションと問合せトランザクションをそれぞれのパラメータとともに使用します。サンプル契約には、getsetの2つの関数が含まれています。

これらのトランザクションでは、toフィールドは契約の住所で、inputフィールドは必要な引数のいずれかと連結された関数実行ハッシュです。

トランザクションを実行するには、関数実行のハッシュを取得する必要があります。これを行う簡単な方法は、Remix IDEで関数を実行し、トランザクション・ログからハッシュをコピーすることです:

  1. Remix IDEで、「Deploy and Run Transactions」パネルを開きます。「Contract」フィールドで契約が選択されていることを確認し、「Deploy」をクリックします。
    デプロイしようとしているSolidityコントローラのスクリーン・キャプチャ。

    デプロイメントが完了すると、コントラクトが「Deployed Contracts」リストに表示されます。
  2. 「Deployed Contracts」リスト内の契約を展開します。スマート・契約機能がリストされます。
  3. トランザクションを実行します。表示された例では、oracleと入力し、「set」をクリックします。
  4. ターミナル・ウィンドウにトランザクション・ログが表示されます。トランザクション・ログが最小化されている場合は、ログをクリックして展開します。横にあるアイコンをクリックして、inputフィールドの値(ファンクション実行ハッシュ)をコピーします。この値を契約先アドレスと同じ場所に保存し、先頭の0xを削除します。
    完了したトランザクションおよびフィールド値が表示され、関数実行ハッシュ値を含む入力フィールドを指しているデプロイメント・ページの画面キャプチャ。

  5. 関数実行ハッシュおよびコントラスト・アドレスを取得したら、RAWデータ引数としてハッシュおよびアドレスを使用して、Oracle Blockchain Platformでsetトランザクションを実行できます。
    
    --data-raw '{"chaincode":"<chaincodename>","args":["<contractaddress>","<setfunctionexecutionhash>"]}'
    
    たとえば、cURLを使用します。
    curl -L -X POST 'https://<hostname>:7443/restproxy/api/v2/channels/<channelname>/transactions' \
    -H 'Authorization: Basic dXNlcm5hbWU6cGFzc3dvcmQ=' \
    -H 'Content-Type: application/json' \
    --data-raw '{"chaincode":"soliditycc","args":["66b92979bb66d645371b3247177e4b2513cb9834","4ed3885e000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000066f7261636c650000000000000000000000000000000000000000000000000000"]}'
    
  6. Oracle Blockchain Platformコンソールを開き、トランザクションが元帳にリストされていることを確認します。

スマート・コントラクトのget関数を使用して問合せなどの別のトランザクションを実行するには、Remixで関数実行ハッシュを生成し、それをコントラクトの住所と結合します:

  1. Remixの「Deploy and Run Transactions」パネルで、契約が「Deployed Contracts」にまだリストされていることを確認します。そうでない場合は、再デプロイします。
  2. get」をクリックします。setトランザクションの場合と同様に、トランザクションから入力を取得して保存し、先頭の 0xを削除します。
    入力フィールドに必要な関数実行ハッシュが含まれていることを明らかにした、Remixの取得トランザクションのスクリーンショット。

  3. このトランザクション・ハッシュおよびコントラクトのアドレスを使用して、Oracle Blockchain Platformにデプロイされたチェーンコードに対して問合せトランザクションを実行できます。
    
    --data-raw '{"chaincode":"<chaincodename>","args":["<contractaddress>","<getfunctionexecutionhash>"]}'
    
    たとえば、cURLでは:
    curl -L -X POST 'https://<hostname>:7443/restproxy/api/v2/channels/<channelname>/chaincode-queries' \
    -H 'Authorization: Basic dXNlcm5hbWU6cGFzc3dvcmQ=' \
    -H 'Content-Type: application/json' \
    --data-raw '{"chaincode":"soliditycc","args":["66b92979bb66d645371b3247177e4b2513cb9834","6d4ce63c"]}'
    
    返されるペイロードには、問い合せるアセット(この例では文字列oracle)が含まれます。

次のサンプル・ペイロードは、16進形式でエンコードされた入力を使用してトランザクションを送信する別の方法を示しています。

{
    "chaincode": "<evmcc-ccid>",
    "args": [
        "<smart-contract-address>",
        "<hexadecimal-encoded-method-and-input-parameters>"
    ],
    "sync": true
}

メソッド名を使用したスマート・コントラクトの操作

オプションのsetAbiメソッドを使用して、アプリケーション・バイナリ・インタフェース(ABI)仕様を設定します。これにより、入力を送信し、バイトコードではなく読取り可能な(16進エンコードではなく)形式で出力を取得できます。Remix IDEの「Solidity Compiler」パネルにある「ABI」アイコン(「Bytecode」アイコンの横)をクリックして、ABI仕様を取得します。読取り可能な入力形式では、uintstringaddress booluint[]string[]およびaddress[]の入力タイプがサポートされています。メソッドのオーバーライドおよびメソッドのオーバーロードを実装するスマート・コントラクトでのトランザクションの実行は、RESTプロキシからのみ、fab3プロキシからはサポートされません。次のサンプル・ペイロードでは、setAbiメソッドを使用してABI仕様を設定します。

{
    "chaincode": "<evmcc-ccid>",
    "args": [
        "setABI",
        "<smart-contract-address>",
        "<abi-spec-of-smart-contract>" --> use the string format of the abi specification
    ],
    "sync": true
}

次のサンプル・ペイロードに示すように、メソッド名と入力パラメータを使用して直接コールすることもできます。

{
    "chaincode": "<evmcc-ccid>",
    "args": [
        "<smart-contract-address>",
        "<smart-contract-method-name>",
		"[<array-of-input-parameters>]", --> empty array if there are no input parameters.
		"[<string-array-of-input-types>]" --> this is optional and is needed when there is method overriding in the smart contract.
    ],
    "sync": true
}

ガス量の設定

次のサンプル・ペイロードに示すように、setGasAmountおよびgetGasAmountメソッドを使用してガス量を構成できます。

{
    "chaincode": "<evmcc-ccid>",
    "args": [
        "setGasAmount",
        "<gas-amount>"
    ],
    "sync": true
}
{
    "chaincode": "<evmcc-ccid>",
    "args": [
        "getGasAmount"
    ],
    "sync": true
}