ラベル jersey の投稿を表示しています。 すべての投稿を表示
ラベル jersey の投稿を表示しています。 すべての投稿を表示

2014年2月22日土曜日

Jersey2.6(JAX-RS2.2) with Jetty9 セットアップ


JAX-RS2.*を使いたいと思って、Jersey2.6をJetty9に組み込もうとしたのですが、
四苦八苦したのでメモ

いろいろdependancyに入れすぎてたのが問題だったようです。
jsr311-apiをdependancyから取り除くとうまくいきました。

JAX-RS2.*では、Pojomappingを指定するのではなく
JAX-RS JSON Providerに対応するライブラリを追加することでJSONに対応します。
下の例では、jackson-jaxrs-json-providerを追加しています。

JavaEE3以上は、jersey-container-servlet-coreを使うよう言われますが
自分は以前のweb.xmlでの指定方法が好みなので
jersey-container-servletを使っています。


pom.xml :

 <略>

<properties>
    <java.version>1.7</java.version>
    <jettyVersion>9.1.2.v20140210</jettyVersion>
    <jerseyVersion>2.6</jerseyVersion>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
   
<dependencies>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>3.8.1</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.eclipse.jetty</groupId>
            <artifactId>jetty-server</artifactId>
            <version>${jettyVersion}</version>
        </dependency>
        <dependency>
            <groupId>org.eclipse.jetty</groupId>
            <artifactId>jetty-servlet</artifactId>
            <version>${jettyVersion}</version>
        </dependency>
        <dependency>
            <groupId>org.glassfish.jersey</groupId>
            <artifactId>jersey-bom</artifactId>
            <version>${jerseyVersion}</version>
            <type>pom</type>
        </dependency>
        <dependency>
            <groupId>org.glassfish.jersey.containers</groupId>
            <artifactId>jersey-container-servlet</artifactId>
            <version>${jerseyVersion}</version>
        </dependency>
        <dependency>
            <groupId>com.fasterxml.jackson.jaxrs</groupId>
            <artifactId>jackson-jaxrs-json-provider</artifactId>
            <version>2.2.3</version>
        </dependency>
    </dependencies>
    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-war-plugin</artifactId>
                <version>2.3</version>
            </plugin>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>2.3.2</version>
                <configuration>
                    <source>${java.version}</source>
                    <target>${java.version}</target>
                </configuration>
            </plugin>
            <plugin>
                <groupId>org.eclipse.jetty</groupId>
                <artifactId>jetty-maven-plugin</artifactId>
                <version>${jettyVersion}</version>
                <configuration>
                    <webAppSourceDirectory>${basedir}/webapp</webAppSourceDirectory>
                    <webXmlFile>${basedir}/webapp/WEB-INF/web.xml</webXmlFile>
                    <jettyEnvXml>${basedir}/webapp/WEB-INF/jetty-env.xml</jettyEnvXml>
                    <contextPath>/</contextPath>
                </configuration>
            </plugin>
        </plugins>
    </build>




WEB-INF/web.xml:


<?xml version="1.0" encoding="UTF-8"?>
<web-app>

    <servlet>
        <servlet-name>jersey</servlet-name>
        <servlet-class>org.glassfish.jersey.servlet.ServletContainer
        </servlet-class>
        <init-param>
            <param-name>jersey.config.server.provider.packages</param-name>
            <param-value>パッケージ</param-value>
        </init-param>
        <load-on-startup>10</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>jersey</servlet-name>
        <url-pattern>/api/*</url-pattern>
    </servlet-mapping>
</web-app>




WEB-INF/jetty-env.xml:


<?xml version="1.0"?>
<!DOCTYPE Configure PUBLIC "-//Mort Bay Consulting//DTD Configure//EN" "http://www.eclipse.org/jetty/configure_9_0.dtd">
<Configure id='wac' class="org.eclipse.jetty.webapp.WebAppContext">

  <Call name="setAttribute">
      <Arg>org.eclipse.jetty.webapp.configuration</Arg>
      <Arg>
          <Array type="java.lang.String">
              <Item>org.eclipse.jetty.webapp.WebInfConfiguration</Item>
              <Item>org.eclipse.jetty.webapp.WebXmlConfiguration</Item>
              <Item>org.eclipse.jetty.webapp.MetaInfConfiguration</Item>
              <Item>org.eclipse.jetty.webapp.FragmentConfiguration</Item>
              <Item>org.eclipse.jetty.plus.webapp.EnvConfiguration</Item>
              <Item>org.eclipse.jetty.plus.webapp.PlusConfiguration</Item>
              <Item>org.eclipse.jetty.webapp.JettyWebXmlConfiguration</Item>
              <Item>org.eclipse.jetty.webapp.TagLibConfiguration</Item>
          </Array>
      </Arg>
    </Call>
 

  <Set name="war"><SystemProperty name="jetty.home" default="."/>/</Set>
 
</Configure>

2013年11月15日金曜日

Jersey ApacheHttpClientをつかう

Javaでhttpから何かを取得する場合に、
一番簡単に扱えてかつ拡張性が高いのは
Jersey ApacheHttpClient だとおもいますという話。


通常の使い方


ApacheHttpClientの特徴は、オブジェクトマッピングをしてくれるという点です

String型で取得する場合は次のようにすればよい


String res = ApacheHttpClient.create().resource(urlString).get(String.class);


一行ですんじゃいます。

またJSONやXMLを取得する場合にJAXBによる変換を行うことができます。
取得するXMLがつぎのような場合、

<?xml version="1.0"?>
<date>2012/10/11</date>
<hash>hogehogegeee</hash>
<rank>1</rank>
<value>2</value>
<addTime>2012/10/11 12:00</addTime>

マッピングをするクラスを次のように定義して、

Ranking.java :

import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;


@XmlRootElement
public class Ranking {
    @XmlElement
    public Date date;

    @XmlElement
    public String hash;

    @XmlElement
    public int rank;

    @XmlElement
    public long value;

    @XmlElement
    public Date addTime;


    public Ranking(){}

}


で、次のようにすれば指定したクラスにマッピングして取得することができます。

Ranking ranking = restClient.resource(urlString).get(Ranking.class);

 

 

 

よくある設定


タイムアウトの設定
接続タイムアウト

ApacheHttpClient client = ApacheHttpClient.create();
client.setConnectTimeout(360000);

読み込みタイムアウト

client.setReadTimeout(900000);



フィルターの定義


フィルターを定義することによって、通信の前後の挙動を
ファンクションクラス?として定義して使いまわすことができます。


Cookieの管理  

クッキーは検証してないのですが、コンフィグで渡せば使えそうです。
クッキーを管理してセッション等を保持する場合は下のような
フィルターを登録すればよいようです。


ApacheHttpClientConfig config = new DefaultApacheHttpClientConfig();
config.getProperties().put(ApacheHttpClientConfig.PROPERTY_HANDLE_COOKIES, true);

ApacheHttpClient client = ApacheHttpClient.create(config);
client.addFilter(new ClientFilter() {
    private ArrayList cookies = new ArrayList();

    @Override
    public ClientResponse handle(ClientRequest request)
            throws ClientHandlerException {
        if (cookies != null) {
            request.getHeaders().put("Cookie", cookies);
        }

        ClientResponse response = getNext().handle(request);
        if (response.getCookies() != null) {
            if (cookies == null) {
                cookies = new ArrayList();
            }
            cookies.addAll(response.getCookies());
        }
        return response;
    }
});



単にCookieを渡したいだけならWebResourceから指定もできます。


ApacheHttpClient client = ApacheHttpClient.create();

String res = client
        .resource(url)
        .header(HttpHeaders.COOKIE, cookieString)
        .get(String.class);

 

 

 

UserAgentの設定

UserAgentの設定は2つの方法があります。
Jersey Clientと同じようにFilterで登録するかWebResourceにヘッダーを追加する方法です。


Filterを追加する場合:

ApacheHttpClient client = ApacheHttpClient.create();

client.addFilter(new ClientFilter() {
    @Override
    public ClientResponse handle(ClientRequest request)
            throws ClientHandlerException {
        request.getHeaders().put("UserAgent", "Mozilla/5.0 (Macintosh; U; Intel Mac OS X 10.4; en-US; rv:1.9b5) Gecko/2008032619 Firefox/3.0b5");
        return getNext().handle(request);
    }
});



WebResourceに追加する場合:

ApacheHttpClient client = ApacheHttpClient.create();

String res = client
        .resource(url)
        .header(HttpHeaders.USER_AGENT, userAgent)
        .get(String.class);



プロキシの設定

HTTP プロクシの設定にはApacheHttpClientConfigを
Client作成時に渡します。


ApacheHttpClientConfig config = new DefaultApacheHttpClientConfig();
config.getProperties().put(
                        ApacheHttpClientConfig.PROPERTY_PROXY_URI,
                        "proxyurl");

ApacheHttpClient client = ApacheHttpClient.create(config);

SocksプロクシとHTTPプロクシの優先順位

SocksプロクシにはApacheHttpClient自体は対応していないので、
Java自体の機能を利用します。


System.setProperty("socksProxyHost", "127.0.0.1");
System.setProperty("socksProxyPort", "9050");



SocksプロクシとApacheHttpClientのconfigでのプロクシの設定は
同時に利用可能です。両方設定した場合、Socksが優先されます。


2013年10月5日土曜日

JAXB アノテーションを利用したJSON マッピング

Jerseyを使っているとレスポンス用のJSONの定義クラスに
アノテーションの@XmlTransitで省略したり
@XmlElement(name="element")で名前変更したりして
ObjectをJAXB経由でJSONに自動でパースさせてたりしますが
その定義を他でも使いまわして各々の処理でJSON文字列にパースする場合には

JacksonJAXBAnnotations

を利用すればいいです。

これは利用すればJAXBアノテーションを利用したマッピングが可能です。


mavenでpom.xmlに追加

        <dependency>
            <groupId>org.codehaus.jackson</groupId>
            <artifactId>jackson-xc</artifactId>
            <version>1.9.13</version>
        </dependency>



Javaでは次のようにするればobjをJSONにパース可能
例ではやってないけどObjectMapperはthread safeなので使いまわしましょう

import org.codehaus.jackson.map.ObjectMapper;
import org.codehaus.jackson.map.ObjectWriter;
import org.codehaus.jackson.xc.JaxbAnnotationIntrospector;


…
        JaxbAnnotationIntrospector introspector  = new JaxbAnnotationIntrospector();
        ObjectWriter ow = new ObjectMapper().setAnnotationIntrospector(introspector).writer()
                .withDefaultPrettyPrinter();
       
        String json = ow.writeValueAsString(obj);

       


最初は、jerseyの内部ロジックを利用しようとしましたが
ひとつのオブジェクトしかないリストがオブジェクトでパースされる問題が発生したり
いちいちクラスタイプ指定しないといけないので面倒でやめました


ちなみに 最初はこんなかんじにしてました

        private Class[] types = {
            MyClass.class,  

            ArrayList.class,
        };


        String result = null;
        JSONConfiguration config = JSONConfiguration.natural().build();
        JSONJAXBContext ctx = new JSONJAXBContext(config, types);
       
        JSONMarshaller m = ctx.createJSONMarshaller();
        StringWriter sw = new StringWriter();
        m.marshallToJSON(xmlObj, sw);
        result = sw.toString();

        return result;



JAXBContextResolverと似たような感じですね
POJOMappingFeatureで問題はどうにかなるかと思ったんですが
JacksonJAXBAnnotationsを使ったほうが楽だし早い

2013年9月16日月曜日

Jetty SSL設定

Jetty 8.*での情報です
9.*でも利用可能かもしれません


#証明書作成用キーの作成

openssl genrsa -des3 -out jetty.key
openssl req -new -x509 -key jetty.key -out jetty.crt


#サーバへ送る証明書の作成

openssl req -new -key jetty.key -out jetty.csr


#2048bit以上が必要な場合
#openssl req -nodes -newkey rsa:2048 -keyout jetty.key -out jetty.csr


#keytoolがない場合${JAVA_HOME}/jre/bin/keytool



#証明書の登録
#jetty.csrの内容を証明サーバに送る
#jetty.crtに帰ってきた証明書を保存する
#keystoreへ登録

keytool -keystore keystore -import -alias jetty -file jetty.crt -trustcacerts



#pkcs12形式を登録
openssl pkcs12 -export -inkey jetty.key -in jetty.crt -certfile etc/SSL_CA.cer(中間証明書)  -out jetty.pkcs12
keytool -importkeystore -srckeystore jetty.pkcs12 -srcstoretype PKCS12 -destkeystore etc/keystore



#jetty-ssl.xml修正

<New id="sslContextFactory" class="org.eclipse.jetty.http.ssl.SslContextFactory">

    <Set name="KeyStore"><Property name="jetty.home" default="." />/etc/keystore</Set>

    <Set name="KeyStorePassword">[keystore password]</Set>

    <Set name="KeyManagerPassword">[key password]</Set>

    <Set name="TrustStore"><Property name="jetty.home" default="." />/etc/keystore</Set>

    <Set name="TrustStorePassword">[keystore password]</Set>

 </New>


#verify
openssl s_client -connect {対象サーバ}:443 -showcerts


参考
http://wiki.eclipse.org/Jetty/Howto/Configure_SSL

2013年1月5日土曜日

HttpServletRequestのthread内共有

ASP.NETを利用していると
static HttpContext HttpContext.Current からリクエスト情報を取得して
IPADDRESS等の情報をどこででも取得することができます

似たような意識でJavaで実装していると
どうしてもHttpServletRequestの取得でつまずいてしまいます。

そこで、スレッド毎に値を保持するThreadLocalを利用して
HttpServletRequest をスレッド内で参照できるようにします


private final static ThreadLocal<HttpServletRequest> servletRequests = new ThreadLocal<HttpServletRequest>();

public static void setServletRequest(HttpServletRequest request) {
    servletRequests.set(request);
}

public static HttpServletRequest getServletRequest() {
    return servletRequests.get();
}


もちろん非同期な実装では参照できなくなる(かな?)
リクエスト初期化時にセットする必要があります。
リクエスト終了後はガベージコレクション対象になります。

2012年12月28日金曜日

Jersey (JAX-RS) での JSON 取り扱いTIPS

JerseyはレスポンスとしてXMLを前提にしていて
JSON扱おうとするとたまに問題が起こるのでその対応をメモ


1.Listに要素がひとつしかないとArrayではなくObject渡してくる

このあたり参考にして、サーブレットを登録しているパッケージ中に
@Providerを定義する
http://tugdualgrall.blogspot.jp/2011/09/jax-rs-jersey-and-single-element-arrays.html

2.…to be continued


もしくは、stackoverflowにJSONパーサをJacksonに変更する方法が乗っていたので
これを利用すると全て解決しそう(うまく動かなかった)
how-can-i-customize-serialization-of-a-list-of-jaxb-objects-to-json


追記:
JSONの扱いは上記の方法を取る必要はなく、POJOMappingFeatureを利用すればいいもよう
Web.xmlのサーブレット定義に追加します

<init-param>
    <param-name>com.sun.jersey.api.json.POJOMappingFeature</param-name>
    <param-value>true</param-value>
</init-param> 

2012年12月6日木曜日

Jersey の HttpServletRequest.getParameter仕様

Jerseyの開発でつまづいたので共有

JerseyでPost時のパラメータを取得するには、普段は@FormParamを利用します。
が、既存のライブラリを利用する際に、HttpServletRequest.getParameter, getParameterMap
を通して取得したい場合があります。

ただ、Jerseyの仕様でgetParameterはnullが返ってきます。
(内部のinputstreamがなくなっているからとか)

その場合には手段がいくつかあります。
1.filterを利用する
2.ServletContainerをextendsする


追記(2014/04/15): 
jetty 9あたリから@Injectを利用した方法があるようです要調査


上記を利用して@FormParam生成前に内部的にparameterを保持しておく
という案がありますが、資料なさ過ぎて私にはむりです。
 そこでとりあえず


3.@Consumesを使ってFormデータを直接受け取る

を利用して既存ライブラリのほうを修正しました。
Postは"application/x-www-form-urlencoded"のcontent-typeでデータを渡してくるので


 @POST
    @Consumes(MediaType.APPLICATION_FORM_URLENCODED)
    public void post(MultivaluedMap formParams) {

         … 

というふうにデータ取得ができます。
でこれをHttpServletRequestのgetPrameterに詰め込めればいいのですが
あきらめ。
既存ライブラリでgetParameterする際にデータを結合しました。

2012年1月15日日曜日

jetty + jersey + Amazon Product Advertising APIのサンプル

●xsdからjarファイルの作成

 AmazonのAmazon Product Advertising APIを利用する際には、
jaxbでxmlをパースするためにクラスの定義が必要です。
ここでは、アマゾンの提供しているxsdからクラス定義を含むjarファイルを作成します。

まず、アマゾンからAWSECommerceService.xsd をダウンロードし、
src/main/resourcesに設置。

pom.xmlを下記のように追加。
maven-compiler-pluginは、1.5以上に設定する。

<groupId>test</groupId>
<artifactId>aws-test</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>AWSECommerceService</name>

<dependencies>
<dependency>
      <groupId>javax.xml.bind</groupId>
      <artifactId>jaxb-api</artifactId>
      <version>2.2.6</version>
  </dependency> 
  </dependencies>
  <build>
      <plugins>
           <plugin>
          <groupId>org.apache.maven.plugins</groupId>
          <artifactId>maven-compiler-plugin</artifactId>
            <configuration>
                <source>6</source>
                <target>6</target>
            </configuration>
      </plugin>
     <plugin>
          <groupId>org.jvnet.jaxb2.maven2</groupId>
          <artifactId>maven-jaxb22-plugin</artifactId>
          <version>0.8.0</version>
      </plugin> 
     </plugins>
  </build>

maven packageを実行すると、target以下にjarファイルが作成されます。
(著者は、target/generated-sources/xjc以下のjavaファイルをインポートして
利用しているのでjarが使用可能か未確認です。)


●signerの実装
2009年8月15日以降、Product Advertising APIは、リクエストに署名認証を含めなければならなくなりました。

下記にAmazonの提供している署名のサンプルがあります。
 Java Sample Code for Calculating Signature Version 2 Signatures


このサンプルのままでは、リクエストに改行が入ってしまって動かないので、
 76行目の
 Base64 encoder = new Base64();
を
  Base64 encoder = new Base64(0);
に変更する必要があります。

それと、日本での検索をしたい場合は、
 33行目 endpoint を "ecs.amazonaws.jp"に変更します。


 ●取得してみる
 作成したjar、signerをインポートしてjerseyを利用して検索結果をそのまま表示する
 サンプルを作ってみます。

src/main/java/gauuud/amazon/service/ItemSearchResource.java

package gauuud.amazon.service;

import java.util.HashMap;
import java.util.Map;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

import com.amazon.associates.sample.SignedRequestsHelper;
import com.sun.jersey.api.client.Client;
import com.amazon.webservices.awsecommerceservice._2011_08_01.ItemSearchResponse;

@Path("/item_search")
@Produces({MediaType.APPLICATION_JSON,MediaType.APPLICATION_XML})
public class ItemSearchResource {
    @GET
    public ItemSearchResponse get(String word) throws Exception {

        SignedRequestsHelper signer = new SignedRequestsHelper();
       
        Map map = new HashMap();
        map.put("Service","AWSECommerceService");
        map.put("Operation","ItemSearch");
        map.put("Version","2011-08-01");
        map.put("SearchIndex","Books");
        map.put("Keywords","java");
       
        map.put("AssociateTag","[アソシエートID]");
       
        String url = signer.sign(map);
       
        Client c = Client.create();           

        ItemSearchResponse result = c.resource(url).get(ItemSearchResponse.class);

        return result;
    }
}



pom.xml  //いらないものが過分に含まれています。

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <groupId>gauuud</groupId>
  <artifactId>aws-sample</artifactId>
  <version>0.0.1-SNAPSHOT</version>
  <packaging>war</packaging>
  <name>aws-sample</name>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  </properties>

  <dependencies>
  <dependency>
   <groupId>org.codehaus.jettison</groupId>
   <artifactId>jettison</artifactId>
   <version>1.3</version>
  </dependency>
  <dependency>
   <groupId>com.sun.jersey</groupId>
   <artifactId>jersey-core</artifactId>
   <version>1.11</version>
  </dependency>
  <dependency>
   <groupId>com.sun.jersey</groupId>
   <artifactId>jersey-client</artifactId>
   <version>1.11</version>
  </dependency>
  <dependency>
   <groupId>com.sun.jersey</groupId>
   <artifactId>jersey-server</artifactId>
   <version>1.11</version>
  </dependency>
  <dependency>
   <groupId>com.sun.jersey</groupId>
   <artifactId>jersey-servlet</artifactId>
   <version>1.11</version>
  </dependency>
  <dependency>
   <groupId>javax.servlet</groupId>
   <artifactId>servlet-api</artifactId>
   <version>2.5</version>
   <scope>provided</scope>
  </dependency>
  <dependency>
   <groupId>com.sun.jersey</groupId>
   <artifactId>jersey-json</artifactId>
   <version>1.11</version>
  </dependency>
  </dependencies>
  <build>
   <plugins>
      <plugin>
        <groupId>org.mortbay.jetty</groupId>
        <artifactId>jetty-maven-plugin</artifactId>
       <version>8.0.0.v20110901</version>
        <configuration>
          <scanIntervalSeconds>10</scanIntervalSeconds>
          <webAppSourceDirectory>${basedir}/webapp</webAppSourceDirectory>
          <webXmlFile>${basedir}/webapp/WEB-INF/web.xml</webXmlFile>
          <contextPath>/</contextPath>
          <connectors>
            <connector implementation="org.eclipse.jetty.server.nio.SelectChannelConnector">
              <port>8080</port>
              <maxIdleTime>60000</maxIdleTime>
            </connector> 
          </connectors>
          <systemProperties>
            <systemProperty>
              <name>org.apache.commons.logging.Log</name>
              <value>org.apache.commons.logging.impl.SimpleLog</value>
            </systemProperty>
          </systemProperties>
        </configuration>
      </plugin>      
      <plugin>
       <groupId>org.apache.maven.plugins</groupId>
       <artifactId>maven-compiler-plugin</artifactId>
   <configuration>
    <source>6</source>
    <target>6</target>
   </configuration>
      </plugin>
   </plugins>
  </build>
</project>
 
 
src/main/webapp/WEB-INF/web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
 xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
 version="3.0">
 <display-name>aws-sample</display-name>
     <welcome-file-list>
      <welcome-file>index.html</welcome-file>
     </welcome-file-list>

 <servlet>
  <servlet-name>jersey</servlet-name>
  <servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
  <init-param>
   <param-name>com.sun.jersey.config.property.packages</param-name>
   <param-value>gauuud.amazon.service</param-value>
  </init-param>
  
        <load-on-startup>10</load-on-startup>
 </servlet>

 <servlet-mapping>
  <servlet-name>jersey</servlet-name>
  <url-pattern>/rest/*</url-pattern>
 </servlet-mapping>
 
</web-app>

maven jettry:run
を実行して
localhost:8080/rest/search_item
にアクセスするとxmlが取得できるはず。

2011年12月15日木曜日

Jersey Client 利用時の文字化け on CentOS5

Sakura VPS 上でJersey Client API を使った、
JSONを取得して、加工、受け渡しするようなRESTful APIを作成していたときに
文字化けが発生しました。

すべてUTF-8で統一されているのになぜ?とあせりました。
Java内部の問題なのかとも思いましたが、開発環境のUbuntuでは
発生してなかったので、ない。

受信周りの問題だなといろいろ調べた結果、
結局はロケールの設定の問題でした。
開発環境のUbuntuでは、

$ locale

の結果が、

$ locale
LANG=ja_JP.utf8
LC_CTYPE="ja_JP.utf8"
LC_NUMERIC="ja_JP.utf8"
LC_TIME="ja_JP.utf8"
LC_COLLATE="ja_JP.utf8"
LC_MONETARY="ja_JP.utf8"
LC_MESSAGES="ja_JP.utf8"
LC_PAPER="ja_JP.utf8"
LC_NAME="ja_JP.utf8"
LC_ADDRESS="ja_JP.utf8"
LC_TELEPHONE="ja_JP.utf8"
LC_MEASUREMENT="ja_JP.utf8"
LC_IDENTIFICATION="ja_JP.utf8"
LC_ALL=

のようになっているのに対してCentOSは、

$ locale
LANG=C
LC_CTYPE="C"
…

 C…、よくわからない値が入っていました。
なので、localeを編集 して、再起動しました。

$ vi /etc/sysconfig/i18n
LANG="ja_JP.UTF-8"


結果、JSON取得時の文字化けはなくなりました。
Jerseyは賢い子