Remixを使ってJPYCスマートコントラクト貯金箱をPolygonにデプロイする
jpyc日本円ハッカソンに参加した時にRemix(https://remix.ethereum.org/)の使い方を教えて貰いました。RemixはEthereum IDEで、面倒な環境構築やエラーに悩まされることなく、Polygon NetworkにDappsをデプロイすることができます。
今回はなんでもトークンさん(@NandemoToken)に教えてもらったこともあり、なんでもさんのJPYCスマートコントラクト貯金箱をベースに説明します。
追記
半年前くらいに書いたこのZennですが、Remixがバージョンアップしたからか、PolygonやERC20トークンの何かが変わったからか、色々とエラーがでてうまく動かなくなりました…。なので初めて「スマコンをデプロイしてみたい」という方にはハマってしまうと思いますので、JPYC開発者コミュニティなどで最新のやり方などを学ぶ方がいいかもしれません。。
完成物
実際のdAppはPolygon上にデプロイされますが、そのdApp(Contract)と通信してJPYCを送受信する操作をRemixで行うことができます。
一応、重要な関数(オレンジのボタン)だけ混乱しないように説明を明記しておきますね。
//貯金箱からの送金を許可する関数です
function approveJpycFromContract() public {
jpyc.approve( address(this) , jpyc.balanceOf(address(this)) );
}
//貯金箱からの出金をする関数です
function withdraw_jpyc() public {
//貯金箱の持ち主だけが呼び出せるように『require』で指定しています
require(msg.sender == owner);
jpyc.transferFrom(address(this) , owner , jpyc.balanceOf(address(this)) );
}
前提
- Metamaskが入っている
- Polygon Network やERC20などブロックチェーンの基礎的なことが分かっている
- Maticを持っている(デプロイ時のガス代)
PolygonというのはEthereumのLayer2 Solutionですね。Ethereumを拡張するブロックチェーン。そのPolygonのトークンがMATICです。もしHiDEなどで投げ銭でJPYCをゲットしてて、「Polygon Network のJPYCは持ってるけどMATICは持ってないよー」という方はこちらの方法でJPYC→MATICにするとお得に交換できるようです(誤解されやすいですが、同じJPYCでもEthereum、Polygon、BSCとチェーンが違えば別物です)。
画面説明
デフォルトでは file explorers タブにいて、default_workspaceが選択されています。左側のRemixのロゴの下に並ぶタブは全部で4つ。
- File explorers
- Solidity Compiler
- Deploy & run transactions
- Plugin Manager
コードを書いて、コンパイルして、デプロイ&実際にアプリの処理を試す(貯金箱からお金を引き出す等)場所ということですね。Plugin Manager は必要がない限り使いません。
貯金箱のコードをコピペ
基本的にSolidityのコードはcontracts配下に置くようです。contracts配下にmoneybox.solファイルを作成し、上記GitHubリポジトリのなんでもさんのmoneyboxのコードをコピペします。
コンパイル
Solidty Compiler タブに移り、Compile moneybox.sol
を押します。設定はデフォルトのままでOK.成功すると Solidty Compiler タブにチェックマークが付き、Contract(Dappsのこと)が生成されます。このとき、IERC20とJPYC_Exampleの2つのContractが生成されていることがわかります。
これは Solidty Compiler が、Solidityのコードをもとに自動的に生成しているようで、IERC20というのはERC20規格を読み込むため何からしく、よくわからないので(おい)一旦無視しましょう。
File exploeres タブに戻ってみると、contracts配下にartifactsフォルダが出来ており、2つのContractに紐づくjsonファイルが生成されています。
これ以降はJPYC_Example Contractのみを使います。
デプロイ
Deploy & run transactions タブに移動します。
①ENVIROMENT を injected Web3 に変更
初期では Javascript VM というローカル環境に構築したブロックチェーンにデプロイする設定になっているので、Polygon Networkにデプロイ時のするため injected Web3 に変えます。
②CONTRACTをJPYC_Exampleに変更
上記①②ができたら、Deployボタンを押すとMetamaskが起動します。
Deployに必要なMATICが表示されるので確認ボタンを押します。
しばらくすると下のコンソールに緑のチェックマークがついたログが流れたらDeploy成功です。
また左下のDeployed ContractsにDeploy済みのContract(Dapps)が追加されるはずです。分かりにくいですが矢印(>)を押すと展開され、貯金箱Contractに実装されたメソッド(スマートコントラクト)を呼ぶボタンが表示されているはずです。
Contract名(JPYC_Example)の横に表示されているのは、Polygon上のContractのアドレスです。
※たまにDeployed Contractsに何も表示されない場合もあるので、その際はMetamaskのアクティビティを見て、成功しているのならそのpolygonscan上にToとして表示されているContractのアドレスを、「At address」のフィールドに入れてやることで直接ContractをDeployed Contractsに追加することも可能です。
Run Transaction
貯金する
このContractでは貯金箱の総額の表示や引き出しなどのスマートコントラクトが実行(Run Transaction)できますが、Deploy直後は当然1JPYCも入っていません。
そこでMetamaskでこのContract宛にJPYCを送ってあげます(gweiは10くらいが承認が早いです)。
Transactionの承認が終わって(Metamaskで確認できるし下のコンソールにも出る)、もう一度jpyAmmount
ボタンを押すとたしかに1JPYCを送金できていることがわかります。
引き出す
このContractでは貯金箱からの送金を許可してからしか引き出せない仕様になってます。
まずapproveJpycFromContract
ボタンを押してMetamaskが起動し、Transactionを実行します。これは送金を許可するということをブロックチェーン上に記録するためのTransactionです。
これがpolygon上で承認されたら、次にwithdraw_jpyc
ボタンを押し、再度Metamaskを起動して今度は引き出しのTransactionを実行します。
これで貯金箱の引き出しができました。
ローカルファイルとremixを同期
remixdというのを使います。手順はドキュメントの通りです。
が僕みたいにせっかちな方のために答えだけ。
npm install -g @remix-project/remixd
remixd -s /moneybox-apps --remix-ide https://remix.ethereum.org
pathは絶対パス。
この状態でremix.ethereumのFile exploeresを開きWorkspacesで「Connect to localhost」を選択するとローカルファイルと同期されます。
npm run dev
とかでローカルサーバーを立ち上げてたりすると接続が上手く行かないことが多い。
その後
僕はPolygonというブロックチェーン上に初めて自分のContract(Dapps)をデプロイできただけでちょっと感動したのですが、実際このままでは誰にも見つけて貰えないどころか、RemixにわざわざdAppのコントラクトアドレスを貼り付けてDeployed Contractsに追加しないと引き出しもできません。
だからこそReactやVueでフロントエンドを作り、web3.jsかethers.jsを使ってpolygon上のContractと通信できるようにしないといけないのですが、中々これが難しい。GanacheやTruffleというかなり前からあるEthereum開発のツール郡はあるのですが、ローカル開発するためのものだったり、Getting Started通りやってもエラーが出たりと初心者には難しい。
こっちのRopstenテストネットワークに Hello world 的なContractをデプロイし、Next.jsから操作するスターターは動いたけど、PolygonのContractと通信したり、infraというまた新しいツールが出てきたりとカスタマイズは難しい。
シンプルに今回つくった貯金箱のデータを表示して、ボタンぽちぽちでMetamask起動して操作できる最小限のNext.jsアプリをVercelにデプロイしたいのだが。誰かいい方法知ってませんか?
ハマりどころ
デプロイエラー
2022年3月時点でやってみたら、Remixのバージョンが新しくなったからか下記エラーがでてデプロイができませんでした。
params specify an EIP-1559 transaction but the current network does not support EIP-1559
もしかしたら前回と違うチェーンの状態で色々イジったからおかしくなったのかもしれません。しかしもう一度、一から workspace を作り直してPolygon環境でやると無事デプロイできたようです。
デプロイ済み Contract の読み込み
Remixは毎回使う度に新規コントラクトとしてデプロイしなくても、過去にデプロイしたコントラクトのアドレスを読み込むことで「Deployed Contracts」に表示されます。上記のデプロイエラー中はこの黄色い「Deploy」ボタンすら表示されないのですが、MetaMaskで過去にデプロイしたチェーンに切り替えていることを確認してContractアドレスを入れると「At Address」の部分が光って押せるようになり、押すと下にContract(dApp)が追加されます。
ただpolygonscanなどから過去にデプロイしたContract(dApp)を探すと思うんですが、注意したいのは from, to, transaction address, jpyc contract address など同じようなHash値がならんでいるので、どれが dApp か分からないことです。
// これは JPYC の Polygon でのコントラクトアドレスなので混同しないように
0x6AE7Dfc73E0dDE2aa99ac063DcF7e8A63265108c
そこでpolygonscanなどのexplorerに Sign up しておき、WatchListに加えたり、tagnameをつけておくとMyPageから確認できるので便利です。
承認や反映までの時間
どんなトランザクションも直ぐには承認されない(マイニングされない?)ので、MetaMaskのガス代を「積極的🦍」などにして、トランザクションが承認されるのを確認してから色んなボタンを試してください。
例えば「jpycAmount」を押しても以下のエラーがコンソールに出て結果が返ってこないことがあります。
call to JPYC_Example.jpycAmount errored: Internal JSON-RPC error.
{
"details": "Internal RPC Error. Try again after some time..",
"code": -32005
}
call to JPYC_Example.jpycAmount errored: Internal JSON-RPC error.
{
"code": -32000,
"message": "header not found"
}
MetaMaskでJPYCをdAppのコントラクトアドレス宛に送金し、トランザクションが承認されたとしても、Polygonscanを見てわかるようにブロックチェーン上に反映されるまではしばらく時間がかかるようです。また今回作ったJPYC貯金箱にJPYCがいくらか入っていたとしても、しばらく時間がたってから「jpycAmount」ボタンを推してもエラーがでるなど、ちょっとまだ初心者には分からない挙動があったりします。
関数実行エラー
もう、分からない…。approveJpycFromContractが承認されないと withdraw_jpyc は実行できないはずなので2番目のエラーがでると思いますが、何回か approveJpycFromContract をやってたらなんかできた…。
approveJpycFromContract
errored: [ethjs-query] while formatting outputs from RPC '{"value":{"code":-32603,"data":{"code":-32000,"message":"header not found"}}}'
withdraw_jpyc
コンソールではないがポップアップで以下の警告がでる。
Gas estimation errored with the following message (see below). The transaction execution will likely fail. Do you want to force sending?
Internal JSON-RPC error. { "code": 3, "message": "execution reverted: ERC20: transfer amount exceeds allowance", "data": "xxxxxxxx" }
なんか昔作ったコントラクトの方で失敗しやすい気がします。また実行時にガス代を最初から「Aggressive🦍」にせず「Site suggested」で一度実行して、後からMetaMask上で「Speedup」をするとうまく行きます。Gasestimatedというのがうまくいってないのかな…わからん。
Discussion
フレームワークは違いますがMetaMaskでシンプルなコントラクトを扱う以下記事がもし参考になれば幸いです。
返信漏れてました!ありがとうございます!最近またブロックチェーンの実装しそうなのでその際試してみたいと思います!
これってテストネットで動作確認とかできますか?
だいぶ前なので、記憶が怪しいですが、デプロイ時にメタマスクでpolygon mumbaiチェーンを選択した状態でネプロイすればテストネットにデプロイできると思います(なんか返信形式になってなかったので再通知すみませんがこっちに書かせてくださいm(_ _)m)