Truffleを使ってEthereumでペットショップアプリを作る〜後半：アプリケーション〜

#これまで
[前半](https://qiita.com/gaisho81/items/06c58d5eb24ae302f690)ではコントラクト部分を作ってきましたが
後半はWebUIの部分を作っていきます。
JavaScriptを久々に見たので心が穏やかになりました。

#アプリケーション
`src`の中にあれこれ格納されており、`index.html`が骨格部分、`js`の中にある`app.js`が動かす部分です。
bootstrapとweb3が最初から入っています。

*`web3.js`とは*
Ethereumノードとやり取りできるJavaScriptライブラリだそうです

`app.js`が親切にも穴埋め式にしてくれていますので、以下は`Replace me...`となっている箇所に入れていきます。

#web3とコントラクトのインスタンス化

```javascript:app.js
    initWeb3: function() {
    // すでに有効可されていたらそれをそのまま使う
    if (typeof web3 !== 'undefined'){
      App.web3Provider = web3.currentProvider;
    }else{
      App.web3Provider = new Web3.providers.HttpProvider('http://localhost:7545');
    }
    web3 = new Web3(App.web3Provider);

    return App.initContract();
  },

  initContract: function() {
    $.getJSON('Adoption.json',function(data){
      var AdoptionArtifact = data;
      App.contracts.Adoption = TruffContract(AdoptionArtifact);

      App.contracts.Adoption.setProvider(App.web3Provider);
      // 状態を呼び起こす
      return App.markAdopted();
    });

    return App.bindEvents();
  },

```

#状況の取得と表示
チェーンの中にデプロイされているコントラクトの状態を取得し、
販売中だったらそのまま`Adopt`ボタンを表示し、
すでに引き取られていたらボタンを押せないようにする必要があります。

'app.js`の真ん中少し後ろにある`markAdopted:`の箇所に記述します。

```javascript:app.js
markAdopted: function(adopters, account) {
    /*
    デプロイしたAdoptionより、getAdoptersをcallする。
    */
    var adoptionInstance;
    App.contracts.Adoption.deployed().then(function(instance){
      adoptionInstance = instance;
      return adoptionInstance.getAdopters.call();
    }).then(function(adopters){
      /*
      adoptersを順番に取り出し、「0じゃない」＝すでに引き取られているものがあれば、
      パネルのボタンの文字をSuccessにし、非表示とする
      */
      for(i=0; i<adopters.length; i++){
        if(adopters[i] !== "0x0000000000000000000000000000000000000000"){
          $(".panel-pet").eq(i).find("button").text("Success").attr('disabled', true);
        }
      }
    }).catch(function(err){
      console.log(err.message);
    });
  },
```

#引き取った際の処理
`Adopt`すると、
該当の`petId`に自分の`account`を紐付けて`adopter`になり、状況を更新して再表示する必要があります。
今度は`handleAdopt`のところに記述していきます。

```javascript:app.js
  handleAdopt: function(event) {
    event.preventDefault();

    // 選択したidをpetIdにする
    var petId = parseInt($(event.target).data('id'));
    var adoptionInstance;

    // アカウントを取得
    web3.eth.getAccounts(function(error, accounts){
      if(error){
        console.log(error);
      }
      var account = accounts[0];
      
      App.contracts.Adoption.deployed().then(function(instance){
        adoptionInstance = instance;

        // 現在のアカウントでコンストラクトを実行
        return adoptionInstance.adopt(prtId,{from:account});
    }).then(function(result){

      // markAdoptedを行って表示を更新する
      return App.markAdopted();
    }).catch(function(err){
      console.log(err.message);
    });
  });
};
```

#確認用のウォレットを導入
Etherの動きを確認するためにプライベートネットに接続できるウォレットを設定します。
チュートリアルでは[MetaMask](https://chrome.google.com/webstore/detail/metamask/nkbihfbeogaeaoehlefnkodbefgpgknn/related?hl=ja)を使用していたので今回もそれでいきます。

`Import Existing DEN`より、Ganacheに表示されているMNEMONICを入力します。
`Custom RPC`を選択し、Ganacheで立ち上げているRPCサーバーのアドレスである`http://127.0.0.1:7545`を入力

うまくいくと。index0である一番上のアカウントの残高が載るかとおもいます


#ローカルサーバーの立ち上げ
できたアプリケーションを確認するためにサーバーを立ち上げてブラウザから確認します。
チュートリアルのやつはご丁寧にも直下にある`bs-config.json`と`package.json`というやつを準備してくれて、lite-serverを立ち上げるだけになっています。

```bash
$ npm run dev
```
上手く行けばペットショップが立ち上がるかと思います。
Adoptのボタンを押すとgasとgas limitを設定するところがでてきますので数字を入れ、好きな子を選んで引き取ってあげてください


#あとがき
おもったよりスイスイできました。
手数料しかかからなかったのでペットショップというより里親募集サイトみたいなものでしょうか。

ソース全体はこちら
[https://github.com/gagaga81/pet-shop](https://github.com/gagaga81/pet-shop)