Webエンジニアがサクッと社内通貨を作ってみた

_※2ヶ月前に作ったものをようやく記事にしたものになります。仮想通貨界隈は流れが早いのですでに作り方など情報が古い可能性がありますのでご了承ください。_

一時期の仮想通貨ブームが少し落ち着き最近では相場はすっかり冷え込んできてしまいましたね。。

**しかし、ブロックチェーン技術はまだまだこれからなのです！**

というわけで、[Ethereum](https://ethereum.org/) 上で発行したトークンを使って Slack 上で簡単に送り合える社内通貨 & Slack アプリ（DApps）を作ってみました。

## 完成品
![readme-01.png](https://qiita-image-store.s3.amazonaws.com/0/3989/bad371e5-a0d7-bc66-92c8-a19b60683b95.png)
<img width="689" alt="readme-02.png" src="https://qiita-image-store.s3.amazonaws.com/0/3989/47022c92-939b-4ab2-2e3f-4be12648ca8f.png">
`internal-coin` という bot に対して対話して、トークンをメッセージ付きで指定したアドレスに送ることができます。

## 仕様（コマンドの詳細説明）
`welcome` : welcome メッセージを表示します。
`help` : bot の使い方を説明します。
`add {address}` : 自分のウォレットのアドレスを登録します。このコマンドで登録すると Slack のメンションと登録したアドレスが紐づきます。
`send` \`{message}\` `to @{mention}` : @{mention} 宛にメッセージとともに `100ITN` トークン送ります。
（今はデバッグ用に自分宛てにも送れるようになっています。）
`show message` : 自分宛てに届いた最新のメッセージが見れます。
`balance` : 自分の ITN トークンの残高を確認できます。

自分のアカウントから相手のアカウントに直接 ITN トークンを送れるようにすると秘密鍵も Slack bot 上で管理しないといけないので Owner アカウントを作って Owner アカウントからユーザーにトークンを配布するようにしました。
<img width="822" alt="スクリーンショット 2018-06-25 18.39.11.png" src="https://qiita-image-store.s3.amazonaws.com/0/3989/01acdec1-40ad-087b-aae4-c82d7597d208.png">


## トークン実装
ほとんど
- [Truffle で始める Ethereum 入門 - ERC20 トークンを作ってみよう](https://qiita.com/amachino/items/8cf609f6345959ffc450)
- [EthereumのERC20 トークンとして社内通貨(風)のものを作ってみます](https://qiita.com/Yaggytter/items/9df7e35e8725c3baad82)
- [Ropstenのテストネット上でERC20トークンを作成・送付してみる](https://tech.pepabo.com/2017/12/06/erc20-token-on-ropsten/)
こちらを参考にさせてもらっていますm

同じように ERC20 ベースでスマートコントラクトを書いています。
↑を見ればトークン発行までできると思うのでコードだけ貼っておきます。
[トークンのコード: GitHub internal-coin(ITN)](https://github.com/keyiiiii/internal-coin)
[トークンの詳細: Etherscan](https://ropsten.etherscan.io/token/0x8cf870f3045ab35fc2c142674325ad80e9b15c4d)

また、メインネットではなく Ropsten（テストネット）にデプロイしています。

最近は [MetaMask](https://metamask.io/) （ベータ版） や [Ethereum/Mist](https://github.com/ethereum/mist/releases) でもトークンの発行だけなら簡単にできるようになってるので業界本当に活発ですね。

## Slack bot を作る
Slack bot には [botkit](https://www.npmjs.com/package/botkit) を使っています。
[完成品コード](https://github.com/keyiiiii/internal-coin-slack-bot)

起動コマンド

```
CONTRACT_ADDRESS={コントラクトのアドレス} ACCESS_TOKEN={infura のアクセストークン} MNEMONIC='{ウォレットの MNEMONIC}' BOT_TOKEN='{Slack の bot トークン}' PARENT_ADDRESS='{Owner アカウント の アドレス}' node index.js
```

bot のインターフェースコードは [/index.js](https://github.com/keyiiiii/internal-coin-slack-bot/blob/master/index.js) にあります。
スマートコントラクトとのつなぎ込みコードは [/contract.js](https://github.com/keyiiiii/internal-coin-slack-bot/blob/master/contract.js) に書いてあります。

contract.js

```js
const PROVIDER = new HDWalletProvider(
  config.MNEMONIC,
  "https://ropsten.infura.io/" + config.ACCESS_TOKEN
);

const web3 = new Web3(PROVIDER);

const contract = new web3.eth.Contract(ABI, config.CONTRACT_ADDRESS);
```
`PROVIDER` で infura に接続してブロックチェーン上にあるスマートコントラクトにアクセスしています。

```js
function thanksMessage(address) {
  return contract.methods.thanksMessage(address).call();
}

function thanks(address, message) {
  return contract.methods.thanks(address, message);
}

function balanceOf(address) {
  return contract.methods.balanceOf(address).call();
}
```
`thanksMessage` , `thanks` , `balanceOf` をそれぞれスマートコントラクトから呼び出しています。

## まとめ

こんな感じで必要なメソッドをスマートコントラクト上で定義し、それを読み出すDApps（今回は Slack bot）を実装すれば割とサクッとそれらしいものが実装できました。
ブロックチェーン界隈は日進月歩で開発が進んでいます。
相場だけでなくちゃんと技術を追っていきたいですね！