ガジェット通信 GetNews

見たことのないものを見に行こう

IBM BluemixとNode.jsでお天気通知! – Facebook Messenger Bot(3) / Watson APIで天気情報を取得

DATE:
  • ガジェット通信 GetNewsを≫

今回作るもの

こんにちは、エンジニアのちゃんとくです。テクニカルライターとしてdotstudioに参加しています。

連載第3回の今回は、2016年に公開された話題のMessenger Platformを使って、Facebook Messenger Botを作りIBM Bluemixにホスティングしてみます。

BotプログラムはNode.jsで作成し、IBM Bluemixで提供されているWeather Company Dataから天気情報を取得して、IBM Bluemixにホスティングし、運用します。

下記の構成で手順を紹介します。
IBM Bluemixの設定
Botのベースを作成
天気情報を取得
Facebook Messenger Botをデプロイ

今回はIBM BluemixのWeather Company Dataから天気情報を取得する方法を説明していきます。

筆者の環境

OS X El Capitan(v10.11.6)
Node.js v8.2.1

Weather Company Dataとは

IBM Bluemixで提供されているサービスの一つで、APIで世界中の任意の場所の10日先までの気象データを取得することができます。

レスポンスの言語を指定でき、日本語にも対応しています。グローバルなデータでは言語変換がネックになることが多いので嬉しい仕様ですね。

また1分あたり10コール・1ヶ月に10,000コールまで無料で、手軽に試すことができます。(実稼働する際には料金体系をよく確認してください。)

今回は1本目で作成したアプリケーションにWeather Company Dataサービスを追加するところから天気情報を取得するところまでやってみます。

Bluemixのアプリケーションにサービスを追加する

Bluemixのコンソールを開き、メニューからサービス > データ&分析を選択します。

「データ&分析サービスの作成」を選択します。

「Weather Company Data」を検索し選択します。

「地域・組織・スペース・接続」はそれぞれ接続したいアプリケーションのものを選択しましょう。ここでは1本目に作成したアプリケーションを選びます。

その他のサービス名や資格情報名はデフォルトのままでも変更しても大丈夫です。

作成すると、アプリケーション側にサービスが追加されます。クリックしてサービスページに移動しましょう。

APIを作成する

サービスの「管理」に移動し、APIをクリックして移動します。

APIで取得できる情報の一覧が表示されます。今回は「Daily Forecast」を選択しましょう。

Daily ForecastのAPI一覧です。latitude(緯度)とlongitude(経度)を指定して3日後までの情報が取得できる一番上のAPIを利用してみます。

APIをクリックするとフォームが開きます。

取得したい地点の緯度経度をそれぞれ入力します。(サンプルは秋葉原の緯度経度です)都市の緯度経度を取得できるAPIも用意されていますが、今回はGoogleのGeocodingを使用しました。「language」はja-JPを指定します。

入力して「Try it out!」をクリックします。このとき認証を求められる場合がありますが、「キャンセル」を選択して先に進めます。(Bluemixアカウントだと弾かれます)

入力した情報でAPIが生成されるので、「Request URL」をコピーしておきます。

このURLをブラウザなどで試してみるとわかりますが、このままでは認証ができておらず利用することができません。先ほどのサービスのページの「サービス資格情報」の項目に移動し、「新規資格情報」を選択します。

任意の名前をつけ、「追加」します。

作成できたら「資格情報の表示」を開き、「username」と「password」の値をそれぞれ取得します。

APIを試してみる

前回オウム返しを試したディレクトリに移動し、app.jsを以下のように変更します。(新しくディレクトリを作成する場合はrequestモジュールをインストールしてください)と

は上記で取得したものに置き換えます。

‘use strict’;

const request = require(‘request’);

// bluemixの設定
const USERNAME = ”;
const PASSWORD = ‘

‘;
const LATITUDE = ‘35.698353’;
const LONGITUDE = ‘139.773114’;
const WEATHER_URL = `https://${USERNAME}:${PASSWORD}@twcservice.au-syd.mybluemix.net/api/weather/v1/geocode/${LATITUDE}/${LONGITUDE}/forecast/daily/3day.json?language=ja-JP`;

/**
* 気象データをまるごと取得
* @return {JSON}
*/
const getData = () => {
request({
method: ‘GET’,
url: WEATHER_URL
}, (e, res, body) => {
if (!e && res.statusCode == 200) {
console.log(JSON.parse(body));
} else {
console.log(‘Error: ‘, body);
}
});
}

getData();

ひとまず実行してみます。

このデータから、Botで返したい内容を切り出しましょう。

気象データから必要な部分を切り出す

今日から3日後までのデータがforcastsの中に配列で入っているので、「今日・明日・明後日・明々後日」という文字列に対して対応する天気を返すメッセージを作ります。それ以外の文字列が来た場合はとりあえず「いつの天気を知りたいですか?」というメッセージを返すようにします。

気象データの中にはたくさん情報がありますが、narrativeという天気と気温が一文になった値を使ってみます。

‘use strict’;

const request = require(‘request’);

// Bluemixの設定
const USERNAME = ”;
const PASSWORD = ‘

‘;
const LONGITUDE = ‘35.698353’;
const LATITUDE = ‘139.773114’;
const BASE_PATH = `https://${USERNAME}:${PASSWORD}@twcservice.au-syd.mybluemix.net/api/weather/v1/geocode/${LONGITUDE}/${LATITUDE}/forecast/daily/3day.json?language=ja-JP`;

/**
* APIから気象データを取得
*/
const getWeatherForecast = () => {
return new Promise((resolve, reject) => {
request({
url: BASE_PATH,
method: ‘GET’
}, (e, res, body) => {
if (!e && res.statusCode == 200) {
resolve(body);
} else {
reject(`Error: ${body}`);
}
});
});
}

/**
* いつの予報を返すか判定
* @param {string} text
* @return {number}
*/
const getForecastDay = (text) => {
const day = {‘今日’: 0, ‘明日’: 1, ‘明後日’: 2, ‘明々後日’: 3};
return day[text];
}

/**
* @param {res} data
* @param {number} day
* @return {string}
*/
const dataToMessage = (res, day) => {
return res.forecasts[day].narrative;
}

const main = async text => {
let forecastDay = await getForecastDay(text);
let message;
if (forecastDay === undefined) {
message = ‘いつの天気を知りたいですか?’;
} else {
let res = await getWeatherForecast();
message = await dataToMessage(JSON.parse(res), forecastDay);
}
console.log(message);
}

main(process.argv[2]).catch(e => {
console.log(e);
});

確認してみる

実行部分で引数に渡しているprocess.argv[2]の部分はコマンドライン引数を受け取ります。コマンドラインから実行してみましょう。

これでほしい天気情報が返ってくるようになりました!

まとめ

今回はIBM Bluemixのサービスを使って、天気情報を取得する部分をつくってみました。ホスティングするクラウド上に簡単に追加できるので連携がとても簡単です。

Bluemixの会話分析や機械学習APIなども同じように利用できるので、Bot作成と相性がよさそうです。とりあえず無料でサクッと試せるところが嬉しいですね。

次回は2本目に作ったFacebook Messanger Botと組み合わせ、いよいよBotをデプロイしてみたいと思います。

それではまた!

●著者プロフィール

dotstudio ちゃんとく
大学までは文系で法学を学んでいたが「モノを作れる人」に憧れて知識ゼロからエンジニアに転身。本業ではPHPでWebサーバサイド開発を担う傍ら、テクニカルライターとしてdotstudioに参加している。Node.jsユーザグループ内の女性コミュニティ「Node Girls」を主催。趣味の電子工作では日本最大のIoTコミュニティ「IoTLT」で体当たり電子工作を発表中。
Twitter: @tokutoku393 / dotstudio, inc.

カテゴリー : デジタル・IT タグ :
CodeIQ MAGAZINEの記事一覧をみる ▶
  • 誤字を発見した方はこちらからご連絡ください。
  • ガジェット通信編集部への情報提供はこちらから
  • 記事内の筆者見解は明示のない限りガジェット通信を代表するものではありません。