Electron+Vueで仮想通貨の板情報を表示する


Eletronを触ってみたいと思い、今回は、実装ネタとして仮想通貨の板情報を表示してみたいと思います。
Eletronとは、改めて言いますと、Windows/macOS/Linuxで実行できるデスクトップアプリを、HTML+CSS+JavaScriptといったWeb技術で開発できるフレームワークです。VSCodeやAtomで使われているフレームワークですね。

前提

Node.jsがインストールされている必要があります。

プロジェクトの作成

フロントエンドはVue.jsを使って作りたいので、ElectronにVue.jsが入ったボイラープレートであるelectron-vueを使ってプロジェクトを作成しようと思います。

electron-vueは日本語ドキュメントが、充実しておりますのでそちらの方を見てもらった方が早いとかあるのですが、以下のようにvue-cliをインストールして、vue initで環境がすぐ作成できます。

# vue-cliをインストール
npm install -g vue-cli
# プロジェクト作成
vue init simulatedgreg/electron-vue my-project

# 依存関係をインストールして実行
cd my-project
yarn # or npm install
yarn run dev # or npm run dev

表示された!

Bitflyer Lightning APIキー取得

Bitflyer Lightningの開発者ページにてAPIキーとAPIシークレットを発行します。

BitflyerのAPIドキュメントは下記にあります。
https://lightning.bitflyer.jp/docs

例えば、今回取得したい板情報の場合だと、以下のように簡単に取得できます。

var request = require('request');
var url = 'https://api.bitflyer.jp/v1/board';
request(url, function (err, response, payload) {
  console.log(payload);
});

と、書いて気づいたが、BitflyerのAPIには、API キーによる認証が不要な HTTP Public API と、 認証が必要な HTTP Private API があり、今回の板情報のようなPublicなAPIを使うだけなら、APIキーはいりません。。。

実装

まずプロジェクトを開いて、routerを修正し、板情報表示用のページへのルーティングを書きます。

router/index.js
import Vue from 'vue'
import Router from 'vue-router'

Vue.use(Router)

export default new Router({
  routes: [
    {
      path: '/',
      name: 'btc',
      component: require('@/components/Btc').default
    },
    {
      path: '*',
      redirect: '/'
    }
  ]
})

次に、板情報表示用のページを作ります。

Btc.vue
<template>
  <main>
    <section class="section">
      <div class="container">
        <h1 class="title">Bitcoin ask/bid volume</h1>
        <board></board>
      </div>
    </section>
  </main>
</template>


<script>
  import Board from './Btc/Board'

  export default {
    name: 'btc',
    components: { Board }
  }
</script>

次に、板情報表示用のコンポーネントを作成します。
※BitflyerのAPIは、上の方で例示したように簡単に使えますが、コードではAPIをラップしてモジュール化して使う様にしています。
※ちなみに省略しましたが、CSSはvuejs+bulmaなbuefyもインストールしてます。

Btc/Board.vue
<template>
  <div class="is-size-7">
      <b-table
        :data="asks"
        :narrowed="true"
        :bordered="true">
        <template slot-scope="props">
          <b-table-column label="size (Ask)" width="120" numeric class="has-text-success">
            {{ props.row.size.toFixed(8) }}
          </b-table-column>
          <b-table-column label="price" width="100" numeric centered>
            {{ props.row.price.toLocaleString() }}
          </b-table-column>
          <b-table-column label="" width="120">
          </b-table-column>
        </template>
      </b-table>
      <b-table
        :data="bids"
        :narrowed="true"
        :bordered="true">
        <template slot-scope="props">
          <b-table-column label="" width="120" numeric>
          </b-table-column>
          <b-table-column label="price" width="100" numeric centered>
            {{ props.row.price.toLocaleString() }}
          </b-table-column>
          <b-table-column label="size (Bid)" width="120" class="has-text-danger">
            {{ props.row.size.toFixed(8) }}
          </b-table-column>
        </template>
      </b-table>
  </div>
</template>

<script>
  import { BitFlyerClient } from '@tadko/bitflyer-client'

  export default {
    name: 'board',
    mounted () {
      this.$nextTick(function () {
        const bitflyerClient = new BitFlyerClient(process.env.BITFLYER_KEY, process.env.BITFLYER_SECRET)
        window.setInterval(() => {
          bitflyerClient.getBoard()
            .then((board) => {
              this.asks = board.asks.slice(0, 10).reverse()
              this.bids = board.bids.slice(0, 10)
            })
            .catch(console.error)
        },
        3000)
      })
    },
    data () {
      return {
        bids: [],
        asks: []
      }
    }
  }
</script>

実行すると、リアルタイムにBitflyerのBTC板情報が表示されるようになります。

最後に

Electronは、ウェブの技術だけでデスクトップアプリが作れて、色んなブラウザ依存を気にせずに最新の技術を使え、結構楽しいので今後ちょくちょく使っていこうと思います。