目次


IBM Cloud Secure Gateway を利用して Docker コンテナーをエンタープライズ・サービスに接続する

Comments

IBM Cloud Secure Gateway は、バックエンドのエンタープライズ・サービスへのセキュアな接続を作成するために利用することができます。このチュートリアルでは、IBM Cloud 内で Secure Gateway サービスを構成する方法、この Secure Gateway サービスにローカル・マシンから接続するように Docker コンテナーを構成する方法、そしてこの Secure Gateway サービスを IBM Cloud アプリ内で利用して、ローカル・マシンから利用できる任意のサービスに Docker コンテナーを介してセキュアにトンネル接続する方法を説明します。

アプリケーションを作成するために必要となるもの

IBM Cloud アカウントが必要です。

以下のものがローカル・マシン上にセットアップ済みで、実行されている必要もあります。

  • 2 GB の RAM が割り当てられた Ubuntu 仮想マシン (私が使用しているのはバージョン v14.04.3 です)
  • Docker コンテナー
  • CouchDB v1.6.1 インスタンス

この例では、Secure Gateway サーバーを使用して、Node.js IBM Cloud アプリから CouchDB に接続する方法を具体的に説明します。

ステップ 1. アプリに Secure Gateway を追加する

  1. IBM Cloud 内でサンプル・アプリを作成します。ランタイムには「SDK for Node.js」を選択してください。このランタイムを使用すると、アプリを迅速に稼働させることができます。この例でのアプリには、「DLJGatewayDemo1」という名前を付けています。
  2. アプリが起動したら、アプリの概要ページをブラウザーで開いて、画面の右上にある「ADD GIT (GIT の追加)」をクリックします。
  3. 「CREATE GIT REPOSITORY (Gt リポジトリーの作成)」画面で、リポジトリーにスターター・アプリが取り込まれるようにチェック・マークを付けて「CONTINUE (続行)」をクリックします。
  4. アプリの概要ページで、「ADD A SERVICE OR API (サービスまたは API の追加)」をクリックします。
  5. 「Integration (統合)」サービスのセクションまでスクロールダウンして、「Secure Gateway」サービスを選択します。このサービスを素早く見つけるには、左側の「Services (サービス)」フィルターを使用して、「Integration (統合)」を選択します。
  6. 「CREATE (作成)」をクリックしてサービスを追加し、アプリを再ステージングします。

ステップ 2. Secure Gateway を構成する

  1. アプリの概要ページで、「Secure Gateway」サービスをクリックして Secure Gateway ダッシュボードを開きます。
  2. 「ADD GATEWAY (ゲートウェイの追加)」をクリックして新しいゲートウェイを作成し、ゲートウェイに名前を付けます (例えば、「DemoDB」など)。
  3. 「ADD DESTINATIONS (宛先の追加)」をクリックします。ゲートウェイを作成する画面のスクリーンショット
    ゲートウェイを作成する画面のスクリーンショット
  4. 1 つのゲートウェイで、複数の宛先をサポートすることができます。つまり、1 つのゲートウェイをローカル・マシンに対してセットアップし、そのゲートウェイを使用して、ローカルにあるさまざまな宛先に接続することができます。宛先とは、ローカル・マシンが Secure Gateway を介して公開するエンドポイントのことです。この例では CouchDB を公開するので、Docker コンテナーを実行しているローカル・マシンからアクセスできる CouchDB として、私が使用している CouchDB インスタンスの IP アドレスとポートを指定します。宛先を作成する画面のスクリーンショット
    宛先を作成する画面のスクリーンショット
  5. 次に、使用するセキュリティーを決定します。TCP または HTTP を選択すれば、クライアント側でセキュリティーを追加する必要はなくなります。こうすれば、開発するのに好都合ですが、実際に「セキュアなゲートウェイ」にするには、セキュリティーを追加する必要があります。私が選択するのは、「TLS: Mutual Auth (TLS: 相互認証)」です。この場合、私のローカル・マシンの CouchDB を使用する IBM Cloud アプリは、この CouchDB に接続するために証明書を提供する必要があります。「Advanced (拡張)」をクリックし、「TLS options (TLS オプション)」の下にある「Mutual Auth (相互認証)」を選択します。
  6. 「Auto generate cert and private key (証明書と秘密鍵の自動生成)」にチェック・マークが付いていることを確認します。チェック・マークが付いていないと、後ほど自分で生成する必要が出てきます。オプションで、自分で用意した証明書をアップロードすることもできます。宛先の情報を入力したら、宛先の行の終わりにあるプラス・アイコンをクリックします。これで、その宛先が追加されます。最後に「I'M DONE (完了)」をクリックします。宛先を作成する画面のスクリーンショット
    宛先を作成する画面のスクリーンショット

ステップ 3. 構成の詳細を確認する

  1. アプリの概要ページで、「Secure Gateway」サービスをクリックして Secure Gateway ダッシュボードを開きます。
  2. CouchDB 宛先の情報アイコンをクリックします。すると、ゲートウェイに関する以下の情報が表示されます。
    • Cloud Host: Port (クラウド ホスト:ポート)
    • Destination Host: Port (宛先 ホスト:ポート)
    • Destination ID (宛先 ID)

「Cloud Host:Port (クラウド ホスト:ポート)」の値は、IBM Cloud アプリがローカル CouchDB に接続する際に使用します。「Destination Host:Port (宛先 ホスト:ポート)」の設定によって、ローカル・マシン上で実行されている Docker コンテナーからアクセス可能な「ホスト:ポート」が指定されます。

構成の詳細を示す画面のスクリーンショット
構成の詳細を示す画面のスクリーンショット

ステップ 4. ローカル・マシンに Docker をインストールする

Docker を実行する Ubuntu 仮想マシンがセットアップ済みになっている必要があります。私が使用しているのは、Ubuntu v14.04.3 仮想マシンです。さまざまなバージョンの Ubuntu に Docker をインストールする方法についての説明は、Docker Web サイトにアクセスしてください。

ステップ 5. Docker コンテナーで使用する証明書をダウンロードする

  1. アプリの概要ページをブラウザーで開き、「Secure Gateway」サービスをクリックして Secure Gateway ダッシュボードを開きます。
  2. 宛先 (この例の場合、「CouchDB」) をクリックしてダッシュボードを開きます。
  3. この宛先に対する操作を選択するための歯車アイコンをクリックし、「Download Keys (鍵のダウンロード)」を選択します。これにより、証明書を格納した zip ファイルがダウンロードされます。「Download Keys (鍵のダウンロード)」を選択する画面のスクリーンショット
    「Download Keys (鍵のダウンロード)」を選択する画面のスクリーンショット

ステップ 6. デフォルトで TLS セキュリティーを使用するように Docker をセットアップする

  1. Ubuntu ローカル・マシン上のホーム・ディレクトリー内に「.docker」という名前の新しいフォルダーを作成し、そこに証明書をコピーします。
  2. ダウンロードした zip ファイルには、5 つのファイルが含まれています。そのうち、以下の 3 つのファイルをコピーします (ここで、xxx は宛先 ID です)。
    • DigiCertCA2.pem を .docker/ca.pem にコピーします。
    • Copy xxx_cert.pem を .docker/cert.pem にコピーします。
    • xxx_key.pem を .docker/key.pem にコピーします。
  3. 環境変数 DOCKER_HOST および DOCKER_TLS_VERIFY を設定します (オプションで、実行時に -H フラグと -tlsverify フラグを使用することができます)。
    $ mkdir -pv ~/.docker
    $ cp DigiCertCA2.pem ~/.docker/ca.pem
    $ cp xxx_cert.pem ~/.docker/cert.pem
    $ cp xxx_key.pem ~/.docker/key.pem
    $ export DOCKER_HOST=tcp://$HOST:2376 DOCKER_TLS_VERIFY=1

ステップ 7. Docker コンテナーを起動してセキュア・トンネルを確立する

Ubuntu ローカル・マシンからのセキュア・トンネル接続を確立するには、Docker コンテナーを起動して、IBM Cloud Secure Gateway の宛先 ID を参照させる必要があります。以下の例では、-D フラグを使用してデバッグを有効にしています。こうすることにより、Docker コンテナーからのあらゆるデバッグ・メッセージが表示されるようになります。また、Docker コンテナーを実行しているローカル・サーバー (Ubuntu ローカル・マシン) と Docker コンテナーがネットワーク・スタックを共有できるように、--net="host" フラグも使用します。以下のコマンドを初めて実行すると、イメージがダウンロードされます。

$ sudo docker -D run --net="host" -it ibmcom/secure-gateway-client qxWAtZ2JWWM_prod_ng
[sudo] password for bluemix:
IBM Bluemix Secure Gateway Client version 1.0.3
<press enter for the command line>
[YYYY-MM-DD HH:MM:SS:MS][INFO] secure tunnel connected

Docker コマンド (上述のフラグを除く) を表示するには、アプリの概要ページをブラウザーで開き、「Secure Gateway」サービスをクリックして Secure Gateway ダッシュボードを開きます。次に、宛先 (「CouchDB」) をクリックして、そのダッシュボードを開きます。最後に「CONNECT GATEWAY (ゲートウェイの接続)」ボタンをクリックすると、接続方法が表示され、具体的な Docker コマンド・ラインも表示されます。

ゲートウェイに接続する方法を選択する画面のスクリーンショット
ゲートウェイに接続する方法を選択する画面のスクリーンショット

ステップ 8. 接続をテストする

ブラウザーを開いて、http://cap-sg-prd-5.integration.ibmcloud.com:15133 にアクセスします (別の方法として、コマンド・ラインから cURL を使用することもできます)。

すると、ERR_CONNECTION_REFUSED または ERR_EMPTY_RESPONSE のいずれかのエラーが発生するはずです。エラーが発生する理由は、このアプリは「TLS: Mutual Auth (TLS: 相互認証)」を使用するように構成されており、クライアント・アプリは接続する際に TLS を使用しなければならないためです。次のステップで、接続を許可してもらうために証明書を渡すようアプリをセットアップする方法を説明します。

ステップ 9. セキュア・トンネルを確立するための Node.js アプリを作成する

このステップでは、ゲートウェイからローカル・マシンへのセキュア・トンネルをセットアップする簡単な Node.js アプリを作成します。

  1. まず、securetunnel.js という名前のファイルを作成し、このファイルが以下の内容のコードで構成されるようにします。ここでは、ネットワーク・ラッパーを作成するために net モジュールを使用し、証明書を使用して接続を確立するために tls モジュールを使用しています。net モジュールは、tls モジュールによって作成されたセキュア・トンネルを通じて接続される新しいエンドポイントを localHost:8888 で公開します。
    var tls = require('tls');
    var fs = require('fs');
    var net = require('net');
    var tunnelPort = process.env.VCAP_APP_PORT || 8888;
    var server;
    var gatewayOptions = {
    	//host local test to bluemix
    		host: 'cap-sg-prd-5.integration.ibmcloud.com',
    		port: '15133',		
    		key: fs.readFileSync('key.pem'),
    		cert: fs.readFileSync('cert.pem'),
    		ca: fs.readFileSync('ca.pem')
    	}
    	
    //create a server end point to use as a network wrapper for the secure gateway	
    server = net.createServer(function (connListener) {
    	console.warn("net server created");
    	connListener.on('end', function() {
    		console.warn('client disconnected')
    	});
    
    	//connect to farside, local/private server
    	connectFarside(connListener, function(err, remoteSocket) {
    		if (err){
    			console.error(err);
    		}
    		console.warn('connection made')
    		remoteSocket.pipe(connListener);
    		console.warn('remote socket connected to local connListener');
    		connListener.pipe(remoteSocket);
    		console.warn('local connListener connected to remote socket');		
    	});
    });
    
    //setup listener for network wrapper on localhost:tunnelPort
    //function called when connection established and ready to tunnel requests
    //when in the function we invoke the callbackRunInTunnel which is where the code
    //runs to communicate to through the bluemix secure gateway
    server.listen(tunnelPort, function(){
    	console.warn('tunnel created at: '+ server.address().address +":"+ server.address().port);
    });
    
    //create a TLS connection to the secure gateway
    function connectFarside(conn, callback) {
        try {
        console.warn("initiating farside connection");
            var socket = tls.connect(gatewayOptions, function() {
                console.warn('tunnel connected to '+ gatewayOptions.host +":"+ gatewayOptions.port);
                callback(null, socket);
            });
            socket.on('error', function(err){
                console.warn('Socket error: ' + JSON.stringify(err));
            });
        } catch(err) {
            console.error(err)
            callback(err);
        }
    };

ステップ 10. Node.js アプリを実行する

securetunnel.js アプリを実行するには、その前に、Secure Gateway サービスによって生成されて Docker コンテナーで使用されている証明書ファイルを入手する必要があります。前にダウンロードした zip ファイルに含まれている 5 つのファイルのうち、以下の 3 つのファイルを以下のようにコピーします。

  • DigiCertCA2.pem を ca.pem にコピーします。
  • Copy xxx_cert.pem を cert.pem にコピーします。
  • xxx_key.pem を key.pem にコピーします (ここで、xxx は宛先 ID です)。

これら 3 つのファイルを、secure-conn.js アプリと同じディレクトリーに置くようにします。securetunnel.js アプリを実行すると、トンネルが確立された先のホスト名とポートを通知してきます。

$ node securetunnel.js
tunnel created at: 0.0.0.0:8888

ステップ 11. 接続を再度テストする

今回は、先ほどのステップで Node.js アプリによって確立されたトンネルを使用します。そのため、http://cap-sg-prd-5.integration.ibmcloud.com:15133 に接続するのではなく、http://localhost:8888 に接続します。前と同じく、ブラウザーか cURL のいずれかを使用して接続しますが、私は以下に示す cURL を使用します。今回の接続では、Node.js アプリによって IBM Cloud Secure Gateway への TLS 接続が確立されて、その接続がローカル・マシンまで、さらにはローカル・マシンの CouchDB インスタンスにまで達するようになるため、接続に成功するはずです。

$ curl http://127.0.0.1:8888
{"couchdb":"Welcome","uuid":"b03e6f754ca999e2d7a5c919954dc33e","version":"1.6.1","vendor":{"version":"1.6.1-1","name":"Homebrew"}}

ステップ 12. IBM Cloud 内で Node.js アプリを実行する

  1. アプリの概要ページで、「EDIT CODE (コードの編集)」をクリックします。
  2. ca.pem、cert.pem、key.pem、securetunnel.js をアプリのコードのメイン・フォルダーにドラッグ・アンド・ドロップします。
  3. 次に、package.json ファイルを編集して、app.js ではなく securetunnel.js を実行するように指定します。変更を加えるのは以下の部分です。
    "scripts": {
    	"start": "node app.js"
    },

    変更後は、以下のようになります。

    "scripts": {
    	"start": "node securetunnel.js"
    },
  4. コードを保存してデプロイします。

ステップ 13. IBM Cloud で接続をテストする

今回は、IBM Cloud にデプロイした Node.js アプリによって確立されたトンネルを使用します。そのため、http://localhost:888 に接続するのではなく、http://<皆さんのアプリ名>.mybluemix.net に接続します。ブラウザーと cURL のどちらを使用して接続しても、同じ結果が得られるはずです。「/_utils/」をパス名に追加して (http://<皆さんのアプリ名>.mybluemix.net/_utils/)、この URL をブラウザーで開くと、IBM Cloud 内で確立されたセキュア・トンネルを使用して CouchDB をフルに操作することができます。

$ curl http://yourappname.mybluemix.net:8888
{"couchdb":"Welcome","uuid":"b03e6f754ca999e2d7a5c919954dc33e","version":"1.6.1","vendor":{"version":"1.6.1-1","name":"Homebrew"}}

まとめ

IBM Cloud 内に Secure Gateway を作成するのは、本当に説明が要らないほど簡単ですが、接続をセキュアにして利用する部分は、注意深く行う必要がありそうです。このチュートリアルの例と説明では、このプロセスに含まれる 2 つの微妙な部分を取り上げました。それは、Docker で TLS を使用することと、アプリで TLS を使用することです。証明書を配置する場所がわかりさえすれば、Docker で TLS を使用するのは簡単なことです。アプリで TLS を使用するのは、それよりも少し高度ですが、TLS を有効にした Secure Gateway を Node.js IBM Cloud アプリの中で使い始めるには、このチュートリアルのサンプルが最適な手段となります。

このチュートリアルでは、以下のことを行いました。

  • IBM Cloud 内で Secure Gateway を作成する
  • 宛先を構成して、「TLS: Mutual Auth (TLS: 相互認証)」を使用するようにセットアップする
  • TLS を使用するように Docker コンテナーを構成する
  • Docker コンテナーを実行して Secure Gateway に接続する
  • 「TLS を使用して接続を確立し、その接続を自分のアプリに対して公開する」という処理を行う Node.js ラッパー・アプリを作成する
  • Node.js アプリをローカルで実行してセキュア接続をテストする
  • Node.js アプリを IBM Cloud 内で実行してセキュア接続をテストする

ダウンロード可能なリソース


関連トピック


コメント

コメントを登録するにはサインインあるいは登録してください。

static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=60
Zone=セキュリティ, Cloud computing
ArticleID=1024264
ArticleTitle=IBM Cloud Secure Gateway を利用して Docker コンテナーをエンタープライズ・サービスに接続する
publish-date=12262018