BluemixにデプロイしたNode.jsアプリが起動しない！そんなときは、ローカル環境で確認しましょう

Bluemixにアプリケーションをデプロイするときに、アプリケーションが起動と停止を繰り返して、最終的には起動失敗となることがあります。
こんな感じの出力ですね。

```
-----> Uploading droplet (8.7M)

0 of 1 instances running, 1 starting
0 of 1 instances running, 1 starting
0 of 1 instances running, 1 down
0 of 1 instances running, 1 down
0 of 1 instances running, 1 starting
0 of 1 instances running, 1 starting
0 of 1 instances running, 1 down
0 of 1 instances running, 1 down
0 of 1 instances running, 1 starting
0 of 1 instances running, 1 starting
0 of 1 instances running, 1 down
0 of 1 instances running, 1 down
0 of 1 instances running, 1 failing
FAILED
Start unsuccessful

TIP: use 'cf logs HelloWorld --recent' for more information
```

こんなときは、エラー出力の最後のTIPにも表示されているように、`cf logs application_name --recent`コマンドを利用して、ログを確認し、どこがまずいのかをチェックします。

今回のケースは単純な入力ミスで、変数名の指定間違いでした。

```
2015-04-22T20:46:11.49+0900 [App/0]      ERR
2015-04-22T20:46:11.49+0900 [App/0]      ERR /home/vcap/app/app.js:11
2015-04-22T20:46:11.49+0900 [App/0]      ERR var app = express();
2015-04-22T20:46:11.49+0900 [App/0]      ERR           ^
2015-04-22T20:46:11.50+0900 [App/0]      ERR ReferenceError: express is not defined
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at Object.<anonymous> (/home/vcap/app/app.js:11:11)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at Module._compile (module.js:456:26)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at Object.Module._extensions..js (module.js:474:10)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at Module.load (module.js:356:32)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at Function.Module._load (module.js:312:12)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at Function.Module.runMain (module.js:497:10)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at startup (node.js:119:16)
2015-04-22T20:46:11.50+0900 [App/0]      ERR     at node.js:906:3
```

こんな感じで、`cf logs`を使ってログを確認すればよいのですが、Syntax Errorや今回の変数間違いのような単純エラーを、毎回Bluemixにアプリケーションをデプロイしてから確認するのは少し面倒です。

そんなときは、ローカル環境でテストしてからBluemixにデプロイしましょう。
「Bluemixで使用しているNode.jsと同じ実装でテストしてみたい」というのであれば、IBM developerWorksのサイトから["IBM SDK for Node.js"](http://www.ibm.com/developerworks/web/nodesdk/)をダウンロードし、ローカル環境に導入するとよいでしょう。

ローカル環境でテストする際の大きな注意点は、以下の2つです。

* リクエストをListenするポート番号
* Bluemixの各サービスを使用するための接続情報（VCAP_SERVICES）の取得方法

リクエストをListenするポート番号の決定方法は、とてもシンプルです。Node.jsでサーバーを作成する際に、以下のようなコーディングにすればOKです。

```
var server = app.listen(process.env.PORT || 3000, function() {
	console.log('Listening on port %d', server.address().port);
});
```

Bluemixでは、Listenに使用するために割り当てられるポート番号が、環境変数*PORT*にセットされます。したがって、`process.env.PORT`が定義されていなければ、ローカル環境と判断し、任意のポート番号（ここでは3000番）を使うようにコーディングすれば問題ありません。

少々面倒なのが、接続情報（VCAP_SERVICES）の取得方法です。以下の方法のどちらかで対応するケースが多いかと思います。

1. OSの環境変数にVCAP_SERVICESを定義する
2. 設定ファイルにVCAP_SERVICESの内容を記述し、利用する

「1. OSの環境変数にVCAP_SERVICESを定義する」の方法については、developwerWorksに掲載されている["Bluemix 上で稼動する Web アプリケーション開発方法 - Node.js 編"](http://www.ibm.com/developerworks/jp/cloud/library/j_cl-bluemix-nodejs-app/)の"3-5. ローカル PC 環境での動作確認"を参照してください。

「2. 設定ファイルにVCAP_SERVICESの内容を記述し、利用する」のコーディング例は、以下のとおりです。*config/VCAP_SERVICES.json*にVCAP_SERVICESの内容がコピーされており、その内容を参照しています。

```
var cradle = require('cradle');

if (typeof process.env.VCAP_SERVICES === 'undefined') {
	var services = require('../config/VCAP_SERVICES.json');
} else {
	services = JSON.parse(process.env.VCAP_SERVICES)
};
var credentials = services['cloudantNoSQLDB'][0].credentials;
var host = credentials.host;
var port = credentials.port;
var dbName = process.env.DB_NAME || require('../config/DB_NAME.json').DB_NAME;
var db = new (cradle.Connection)(host, port, options).database(dbName);
```

ちなみにですが、VCAP_SERVICESの値は、Bluemixの管理コンソールより確認でき、一括コピーのボタンも用意されています。

ダッシュボードより、VCAP_SERVICESを参照したいアプリケーションをクリックし、左側の**環境変数**を選択します。
![nodered-vcap.jpg](https://qiita-image-store.s3.amazonaws.com/0/73397/e1ac0282-f912-86c5-00a8-81b53ea5b697.jpeg)

右上のオレンジ枠で囲ったボタンをクリックするとクリップボードに内容がコピーされます。**エクスポート**ボタンをクリックすると、*.json*の拡張子のファイルとしてダウンロードできます。
![nodered-vcap02.jpg](https://qiita-image-store.s3.amazonaws.com/0/73397/d37dd445-1694-e911-2cbe-ceee6aecff56.jpeg)