夢の国のアトラクション待ち時間をスマホで確認する

# 概要

みなさん、[夢の国](https://www.tokyodisneyresort.jp/)は好きですか？
僕は大好きです。毎日行きたいです。

以前は、Webサイトからアトラクションの待ち時間が取得できたのですが、
現在はアプリのみでしか確認することができなくなりました。

アプリは便利なのですが、マップベースで確認することしかできないため、
一覧で表示したいなぁと思ってスマホ向けのWebアプリを作ってみました。

# 作ったもの

## [TDR Wait Times](https://tdr-wait-time.now.sh/)

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/365084/51a9d073-b129-dcd8-fdad-d9c7e9fac735.png" width=50%>

平日めっちゃ空いてるな！

## 機能
* ランドとシーの切替えてアトラクションの待ち時間が確認ができる。
* 待ち時間順にソートできる。
* ファストパスがあるアトラクションを確認できる（時間や、残は確認できない）

# 待ち時間データの取得

## [Themeparks](https://github.com/cubehouse/themeparks)

* 使い方は[この記事](https://qiita.com/sosukesuzuki/items/b0efb84e8f534db4aa00)が参考になります。
* こんな感じで、取得した待ち時間データをJSONファイルに吐き出しておきます。

```javascript:index.js
const Themeparks = require('themeparks');
const fs = require('fs');

const getPark = url =>
  url === 'tds'
    ? new Themeparks.Parks.TokyoDisneyResortDisneySea()
    : new Themeparks.Parks.TokyoDisneyResortMagicKingdom();

(async () => {
  const tdr = getPark('tdl');
  await fs.writeFile(
    '/var/www/html/tdl.json',
    JSON.stringify(await tdr.GetWaitTimes()),
    () => {}
  );

  const tds = getPark('tds');
  await fs.writeFile(
    '/var/www/html/tds.json',
    JSON.stringify(await tds.GetWaitTimes()),
    () => {}
  );
})();
```

## アトラクション名の日本語化

* そのまま実行するとアトラクション名が英語になるので、以下を修正します。

```javascript:node_modules/themeparks/dist/disneytokyo/index.js
// 247行目付近
rideData[attr.id] = {
-    name: englishData && englishData.name !== undefined ? englishData.name : attr.nameKana,
+    name: attr.name,
    fastpass: !!attr.fastpass,
    type: attr.attractionType.id,
    facilityCode: Number(attr.facilityCode)
};
```

## GCEにVMインスタンス立て

* [この記事](https://qiita.com/yfujii01/items/41c15d885830deea8ed1)を参考にして無料枠を使ってVMを立てます。
* cronで定期的にJSONを出力するようにしておきます。
* JSONは外部参照できるようにしておきます。

# Webアプリ作成

## 実装

* とりあえず、`create-react-app`を叩きます。
* GCEのVM上にあるJSONをGETします。
* ソースコードは長くなるので[こちら](https://github.com/obuchi3/tdr-wait-time)

## デプロイ

* `now`コマンドでデプロイします。
* React用の`now.json`の作り方は[ここ](https://zeit.co/examples/create-react-app)にあるので、まるっとコピればOK。

```json:now.json
{
    "version": 2,
    "name": "my-react-app",
    "builds": [
        { "src": "package.json", "use": "@now/static-build", "config": { "distDir": "build" } }
    ],
    "routes": [
      { "src": "/static/(.*)", "headers": { "cache-control": "s-maxage=31536000,immutable" }, "dest": "/static/$1" },
      { "src": "/favicon.ico", "dest": "/favicon.ico" },
      { "src": "/asset-manifest.json", "dest": "/asset-manifest.json" },
      { "src": "/manifest.json", "dest": "/manifest.json" },
      { "src": "/precache-manifest.(.*)", "dest": "/precache-manifest.$1" },
      { "src": "/service-worker.js", "headers": { "cache-control": "s-maxage=0" }, "dest": "/service-worker.js" },
      { "src": "/(.*)", "headers": {"cache-control": "s-maxage=0"}, "dest": "/index.html" }
    ]
}
```

# その他

* GCEの無料枠 + NOWなので無料で作れました。
* とりあえずiPhoneのSafariでしか動作確認してません。
* パーク閉園中とか考慮してません。
* エリアごとにアトラクションまとめたいなぁ。
* 申し訳程度の休止アトラクション情報。
* Bootstrapくさい。
* FastPassの時間も欲しかったけど、Themeparksで対応してないんで無理かな。
* グリーティングの待ち時間も欲しかったけど（以下略
* リファクタリングしたい…。

## ソースコード
https://github.com/obuchi3/tdr-wait-time-api
https://github.com/obuchi3/tdr-wait-time