Apache Geronimo に Web サービスをデプロイする

Amazon Web サービスを使ってデプロイ手順を学ぶ

Webサービスの開発をサポートするアプリケーション・サーバーを決定しようとしているのであれば、Apache Software Foundationの最新プロジェクトの1つ、Apache Geronimoアプリケーション・サーバーを試してみてください。この記事では、Java™の専門家である Kunal Mittalが、GeronimoのWebサービス機能の紹介として、標準的なJ2EE Webサービス・コードをGeronimoで書き、開発する方法を解説します。基礎となるSOAP(Simple Object Access Protocol)実装にApache Axisを使用し、AmazonのWebサービスを利用する方法を学びます。また、単純なJSP(JavaServer Pages)ベースのクライアントを使ってWebサービスにアクセスする方法も学びます。

Kunal Mittal (kunal@kunalmittal.com), Portal/J2EE architect, consultant, freelance writer

Kunal Mittalはコンサルタントとして、Java技術やJ2EE、Webサービス技術などを専門としています。これらの分野に関する本を何冊か共同執筆しており、また記事も寄稿しています。現在はソニー・ピクチャーズエンタテインメント用のポータル・プロジェクトに従事しています。詳しくは彼のWebページを見てください。



2005年 6月 28日

GeronimoがWebサービスの標準をサポートする

新しいApache Geronimoプロジェクトは、強力な、オープンソースのJ2EEアプリケーション・サーバーであり、J2EE 1.4標準の上に構築されています。Apache Geronimoは全てのオープンソース実装を使用しており、間もなくJ2EE準拠となるはずです。面白いことに、Geronimoは他の多くのオープンソース・プロジェクトから集められたコードの上に作られています。GeronimoはApache AxisとApache Scout(参考文献)を使って、次のようなWebサービス標準をサポートしています。

  • Java Specification request (JSR) 109 (implementing Enterprise Web Services 1.1)
  • Java API for XML-based Remote Procedure Call (JAX-RPC)
  • SOAP with Attachments API for Java (SAAJ) 1.2
  • Java API for XML Registries (JAXR) 1.0

こうした標準をサポートしているため、GeronimoはWebサービスの開発作業をサポートするアプリケーション・サーバーとして、実際的な選択肢となっています。Geronimoを構成しているオープンソース・プロジェクトを既に使ったことがある人にとっては、デプロイメント・コンテナーとしてGeronimoに移行することは自然でしょう。また、幾つかのEclipseプラグインも入手できるため、J2EEアプリケーションの開発やデプロイは、さらに容易になっています。こうしたプラグインは、EclipseのWTP(Web Tools Platform・・・2005年7月に1.0がリリースされる予定)の一部です。WTPと、その関連情報については、参考文献にあるリンクを見てください。

ここではAWS(Amazon Web Services)を例として使いながら、GeronimoでWebサービスを利用する方法を学びます。まずAWS用のWSDL(Web Services Description Language)を取り上げ、Apache Axisを使ってコンスーマー・コードを構築します。次に、このWebサービスを利用する単純なJavaクラスを導入し、Webサービスの結果を表示するために、このクラスをJSPファイルから呼び出す方法を学びます。最後に、J2EE WARファイルとしてコードをバンドルし、Geronimoにデプロイします。


Amazon Web Servicesを利用する

AWSを利用するためには、SOAP実装としてApache Axisを使うことによって、サービス・コンスーマーを構築する必要があります。(AxisはGeronimoがサポートする、基礎となるSOAP実装です。)この構築に経験があり、コードを持っている人は、遠慮なく先に進んでください。

この記事の執筆時点では、まだGeronimoは実稼働可能なアプリケーション・サーバーではありませんが、J2EE認証の手続きが行われている最中です。リリースされれば、J2EE 1.4認証済みとなるはずです。

AWSコードを生成するために必要なもの

まず、環境を設定するところから始めます。AWSのコンシューマー・コード(consumer code)を生成するためには、下記の4つのものが必要です。

  • JDK(Java software development kit)の1.4.2、またはそれ以上(参考文献にJavaのWebサイトへのリンクがあります)
  • Apache Axisの1.1、またはそれ以上(参考文献にApache Axis Webへのリンクがあります)
  • このWebサービスに対するWSDL(Web Services Description Language、参考文献に、このWSDLをダウンロードするためのリンクがあります。)
  • AmazonのWebサービスを利用するための、Amazonが発行AWSサブスクリプションID(参考文献に、無料のIDを取得するためのリンクがあります。)

環境を設定する

上に挙げた要素をダウンロードし、次のステップで環境を設定します。

  • JDKをC:\jdk_142_05にインストールし、JAVA_HOMEをこのディレクトリーに設定します。
  • C:\axis1-2の中にApache Axisを解凍し、AXIS_HOMEをこのディレクトリーに設定します。
  • WSDLファイルをAXIS_HOMEディレクトリーにコピーします。
  • AWSサブスクリプションIDを登録します。

これで基本的な環境は整ったので、Webサービスを利用するためのコードを生成することができます。

WSDLからJavaコードを生成する

最初に、Webサービスを利用するJavaコードをWSDLファイルから生成します。Apache Axisには、このためにWSDL2Javaと呼ばれるユーティリティーが用意されています。このツールを実行するためには、次のJAR(Java Archive)ファイルがクラスパスにあることを確認しておく必要があります。そのためのサンプル・スクリプトを、リスト1のsetenv.batに示します。

リスト1. Setenv.bat
set AXIS_HOME=c:\axis-1-2
set CLASSPATH=.
set CLASSPATH=%AXIS_HOME%\lib\axis.jar;%CLASSPATH%
set CLASSPATH=%AXIS_HOME%\lib\commons-discovery.jar;%CLASSPATH%
set CLASSPATH=%AXIS_HOME%\lib\commons-logging.jar;%CLASSPATH%
set CLASSPATH=%AXIS_HOME%\lib\jaxrpc.jar;%CLASSPATH%
set CLASSPATH=%AXIS_HOME%\lib\saaj.jar;%CLASSPATH%
set CLASSPATH=%AXIS_HOME%\lib\log4j-1.2.8.jar;%CLASSPATH%
set CLASSPATH=%AXIS_HOME%\lib\wsdl4j.jar;%CLASSPATH%

次に、AXIS_HOMEディレクトリーから次のコマンドを実行して、Javaコードを生成します。

java org.apache.axis.wsdl.WSDL2Java AWSECommerceService.wsdl

このプロセスには数秒かかります。このプロセスが終わると、AXIS_HOMEの下にcomと呼ばれるディレクトリーが作られます。これで、最終的にGeronimoでデプロイする予定の、WAR(Web Archive)ファイルを作り始めることができます。

C:\amazon-clientというディレクトリーを作ります。このディレクトリーを使って、WARファイル用のコードを保存するのです。このディレクトリーの下に、WEB-INFというディレクトリーと、srcというディレクトリーを作ります。comディレクトリーを、AXIS_HOMEからC:\amazon-client\WEB-INF\srcにコピーします。

このコードが、Webサービスを利用するための基本コードです。この時点では、このコードの詳細に踏み込む必要はありません。

Webサービスを利用するコードを書く

次に、このWebサービス用のクライアントを書きます。この例では、WSDL2Javaを使って生成された適当なクラス群を呼ぶ、単純なJavaクラスを書くことにします。(EclipseやIBM® Rational® Application Developerでは、このコードのスタブ版が自動的に生成されます。ですから、このコードの書き方の説明は簡単にすませることにします。)

私は単純にするために、WSDL2Javaを使って生成されたパッケージ構造(com.amazon.xml.AWSECommerceServer)と同じパッケージ構造の中に、AmazonClientというクラスを作りました。このクラスのコードをリスト2に示します。このクラスは、lookupISBNという1つのメソッドをエクスポーズします。名前からも分かる通り、このメソッドはAWSを呼び、渡されたISBN番号で表現された本に関する情報を返します。

リスト2. AmazonClient.java
package com.amazon.xml.AWSECommerceServer;

import java.lang.*; 
import java.util.*;

public class  AmazonClient {

    public AmazonClient() {    }

    public Items[] lookupISBN(String isbn) throws Exception {

        try {

            System.out.println("Given ISBN is " + isbn);

            AWSECommerceServiceLocator locator = 
                    new AWSECommerceServiceLocator(); 

            AWSECommerceServicePortType type = 
                    locator.getAWSECommerceServicePort(); 

            String itemId[] = {isbn.trim()}; 
            ItemLookup lookup = new ItemLookup(); 
            lookup.setAssociateTag("MY ID");   // fill in your own 
            lookup.setSubscriptionId("MY ID"); // fill in your own 
            ItemLookupRequest lookupReq = new ItemLookupRequest(); 
            lookupReq.setMerchantId("All"); 
            lookupReq.setItemId(itemId); 
            lookupReq.setResponseGroup(new String[] 
            {"Medium", "OfferFull", "Variations", "Images"}); 
            ItemLookupRequest[] requests = lookup.getRequest(); 
            requests = new ItemLookupRequest[1]; 
            requests[0] = lookupReq; 
            lookup.setRequest(requests); 
            ItemLookupResponse response = 
                     type.itemLookup(lookup); 
            Items[] items = response.getItems(); 
            if (items != null && items.length > 0) { 
                System.out.println("Number of results "+ items.length); 
                return items; 
            } 
        } catch (javax.xml.rpc.ServiceException se) { 
            throw new Exception(se.getMessage()); 
        } 
        return new Items[0]; 
    } 
}

AmazonのサブスクリプションIDを取得するためには、Amazonに登録する必要があります(上記の「Amazon Web Servicesを利用する」を見てください)。サブスクリプションIDを取得したら、リスト2のコードを、そのIDで置き換えます。

これで、このコードをコンパイルする準備が整いました。setenv.batファイルを実行すると、その後はjavac *.java:を実行するだけで、簡単にコードのコンパイルができるはずです。コンパイルすると、このディレクトリーの中に幾つかのクラス・ファイルができます。私はパッケージングを簡単にするため、srcディレクトリー全体を、WEB-INF/classesという新しいディレクトリーにコピーしています。次に、WEB-INF/classesからJavaソースファイルをすべて削除し、WEB-INF/srcからクラス・ファイルをすべて削除します。EclipseのようなIDE(integrated development environment)を使っていれば、こうした手作業の多くは自動的に行われます。

次に、Webサービスを呼び出し、結果を見ます。このためにはJSPファイルを使います。

Webサービスからの結果を表示するためのJSPファイルを書く

amazonclientディレクトリーの下に、searchAmazon.jspというJSPファイルを作ります。このコードをリスト3に示します。

リスト3.searchAmazon.jsp

リスティングを見るにはここをクリック

リスト3.searchAmazon.jsp

<%@ page language="java" contentType="text/html;charset=UTF-8"%>
<%@page import ="com.amazon.xml.AWSECommerceServer.*" %>
<html>
    <head>
        <title>
            Search Amazon
        </title>
    </head>
    <body>

<% 

try {
    AmazonClient ac = new AmazonClient();
    out.println("Searching Amazon Web Services with ISBN 1590595157 <br>");
    out.println("<br>Results are<br><br>");
    
    Items [] resultItems =  ac.lookupISBN("1590595157");
    if(resultItems!=null && resultItems.length>0)  {
        for (int i = 0; i < resultItems.length; i++) {
            Item[] itemvalues = resultItems[i].getItem();
            if (itemvalues != null) {
                for (int j = 0; j < itemvalues.length; j++) {
                    String [] authors= itemvalues[j].getItemAttributes().getAuthor();
                    StringBuffer authorBuffer=new StringBuffer();
                    If (authorBuffer!=null) {
                        for( int k=0;k<authors.length;k++) {
                            authorBuffer.append(authors[k]);
                            authorBuffer.append(" ");
                        }
                    }
                    out.println("<br>Authors :"+ authorBuffer.toString());
                    out.println("<br>ISBN : "+ itemvalues[j].getItemAttributes().getISBN());
                    out.println("<br>Label : "+ itemvalues[j].getItemAttributes().getLabel());
                    out.println("<br>Price : "+ itemvalues[j].getItemAttributes().getListPrice().getFormattedPrice());
                    out.println("<br>No of pages : "+ itemvalues[j].getItemAttributes().getNumberOfPages());
                    out.println("<br>Publisher : "+ itemvalues[j].getItemAttributes().getPublisher());
                    out.println("<br>Title : "+ itemvalues[j].getItemAttributes().getTitle());
                 }
            }
        }
    }
} catch (Exception e) {}
%>
</body>
</html>

リスト3に示すJSPファイルでは、先に定義したAmazonClientクラスを呼び、Itemオブジェクトの配列を受信しています。次に、この配列に対して繰り返しを行い、値を表示します。

ここでの要点は、良きJ2EEコーディング習慣を示すことではありません。書いているコードが全て標準的なJ2EEコードであること、そしてIBM WebSphere®プラットフォームやApache Tomcat、Apache Geronimo、JBossあるいはBEA WebLogicなどで容易にデプロイできることを示すことが要点です。

これで、必要なコードが全て揃いました。

コードをデプロイする前の最終ステップ

最後のステップとして、GeronimoにWARファイルがデプロイできるように、デプロイメント記述子を設定します。WEB-INFディレクトリーの下に、2つの単純なXMLデプロイメント記述子を作ります。その2つのうち最初の方は、web.xmlという、標準のJ2EE WARデプロイメント記述子です(リスト4)。

リスト4. web.xml
<?xml version="1.0"  encoding="ISO-8859-1" ?>

<web-app xmlns="http://java.sun.com/xml/ns/j2ee"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee 
http://java.sun.com/xml/ns/j2ee/web-app_2_3.xsd"
    version="2.3">
 
  <display-name>Amazon Sample</display-name>
  <welcome-file-list>
      <welcome-file>t;searchAmazon.jsp</welcome-file>
  </welcome-file-list>
</web-app>

Geronimoでは、geronimo-jetty.xml記述子が必要です。このコードをリスト5に示します。

リスト5. geronimo-jetty.xml記述子
<?xml version="1.0" encoding="ISO-8859-1"?>
<web-app
xmlns="http://geronimo.apache.org/xml/ns/web/jetty"
xmlns:naming="http://geronimo.apache.org/xml/ns/naming"
configId="amazonclient"
parentId="amazonClient">
   <context-root>/amazonclient</context-root>
   <context-priority-classloader>true</context-priority-classloader>
</web-app>

これで、このファイルをamazon.warというWARファイルとして保存することができます。そのためには、amazonclientディレクトリーから次のコマンドを実行します。

jar cf amazon.war

これで、このコードをGeronimoにデプロイする準備が整いました。


Geronimoにコンスーマー・コードをデプロイする

作ったのは標準のJ2EEのWARファイルですが、このWARファイルは、どんなアプリケーション・サーバー(あるいはサーブレット・エンジン)にも容易にデプロイすることができます。次のセクションでは、このコードをGeronimoにデプロイする方法を説明します。

Geronimoをインストールする

まず、Geronimoのダウンロードとインストールから始めます(参考文献にダウンロード・サイトへのリンクがあります)。Geronimo 1.0 M3 Installerをダウンロードします。インストーラーを実行するには、次のコマンドを使います。

java -jar geronimo-1.0-M3-installer.jar

指示される手順に従って、C:\geronimoとして定義されるGERONIMO_HOMEにGeronimoをインストールします。

Geronimoを起動する

サーバーを起動するには、GERONIMO_HOMEディレクトリーから次のコマンドを実行します。

java -jar bin/server.jar

Amazon.warファイルをデプロイする

クラスパスにあるsetenvバッチ・ファイルには、全てのJARファイルが定義されているはずです。これらのファイルを、AXIS_HOME\libからGERONIMO_HOME\libにコピーします。こうしたJARファイルの多くは、既にGERONIMO_HOME\libに存在しています。たとえコピーしようとしているファイルの方が新しいバージョンであっても、絶対に既存のファイルを上書きしてはなりません。既存のファイルを置き換えるかどうか指示するように促されたら、Noをクリックします。

アプリケーション・サーバーにamazon.warファイルをデプロイするには、このWARファイルをGERONIMO_HOMEにコピーします。このディレクトリーから、次のコマンドを実行します。

java -jar bin/deployer.jar deploy amazon.war

searchAmazon.jspを実行する

残った作業は、皆さんが書いたJSPファイルを実行することだけです。ブラウザーを開き、アドレス・バーでhttp://localhost:8080/amazon/searchAmazon.jspをタイプします。

その結果を図1に示します。JSPファイルを修正すれば、ISBN番号の入力と検索結果の表示のためのフォーム・フィールドを含めることができます。

図1. searchAmazon.jspを実行する
図1. searchAmazon.jspを実行する

これで、皆さんのWebサービス・コンスーマー第1号が、無事Geronimoにデプロイできました。


標準のJ2EE Webサービス

この記事で取り上げた例は単純なものですが、Geronimoが標準のJ2EE Webサービスをサポートしていることを示しています。Webサービスを使うための練習として、AWSで利用できる他のオプションも試すこともできます。例えばISBNでの検索を、本の題名や著者名での検索に変更してみるのです。その次に、Webサービスの結果からAmazon.comにリンクするURLを表示し、また本の画像を表示するにはどうすべきかを考えるのです。

あるいは、他のJ2EE技術をApache Axisと組み合わせてWebサービスを利用し、それをGeronimoにデプロイする、というのも面白い練習です。例えば、AmazonClient.javaというPOJO(Plain Old Java Object)を、ステートレス・セッションEJB(Enterprise JavaBean)コンポーネントと置き換え、それをGeronimoにデプロイするのです。

そうした例としては、webMethodsあるいはGoogleのWebサービスにある、どんなWebサービスでも使うことができます。この記事で説明したステップと同じステップを踏んで行けば、こうしたWebサービスのコンスーマーを、手軽にGeronimoにデプロイできるのです。


まとめ

この記事では、Geronimoを知り、そのWebサービス機能を見ることができました。これで、皆さんのWebサービス開発作業の中で、いつでもGeronimoアプリケーション・サーバーが使えるはずです

参考文献

コメント

developerWorks: サイン・イン

必須フィールドは(*)で示されます。


IBM ID が必要ですか?
IBM IDをお忘れですか?


パスワードをお忘れですか?
パスワードの変更

「送信する」をクリックすることにより、お客様は developerWorks のご使用条件に同意したことになります。 ご使用条件を読む

 


お客様が developerWorks に初めてサインインすると、お客様のプロフィールが作成されます。会社名を非表示とする選択を行わない限り、プロフィール内の情報(名前、国/地域や会社名)は公開され、投稿するコンテンツと一緒に表示されますが、いつでもこれらの情報を更新できます。

送信されたすべての情報は安全です。

ディスプレイ・ネームを選択してください



developerWorks に初めてサインインするとプロフィールが作成されますので、その際にディスプレイ・ネームを選択する必要があります。ディスプレイ・ネームは、お客様が developerWorks に投稿するコンテンツと一緒に表示されます。

ディスプレイ・ネームは、3文字から31文字の範囲で指定し、かつ developerWorks コミュニティーでユニークである必要があります。また、プライバシー上の理由でお客様の電子メール・アドレスは使用しないでください。

必須フィールドは(*)で示されます。

3文字から31文字の範囲で指定し

「送信する」をクリックすることにより、お客様は developerWorks のご使用条件に同意したことになります。 ご使用条件を読む

 


送信されたすべての情報は安全です。


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=60
Zone=Open source, Java technology, SOA and web services
ArticleID=232902
ArticleTitle=Apache Geronimo に Web サービスをデプロイする
publish-date=06282005