JAX-RSを使用してRESTfulサービス開発
先のエントリーの「JavaによるRESTfulシステム構築」を読んだので本の中のサンプルをベースに簡単に実装方法を紹介。
1. jerseyの取得
JAX-RSの実装として、Jerseyを使用します。
http://jersey.java.net/
Downloadページでは、Mavenを使用した説明が書いていますが、
zipファイルを取得するリンクがあるのでそちらからダウンロードします。
- jersey-archive-1.7.zip
展開すると以下のファイルが含まれています
-asm-3.1jar
-jackson-core-asl-1.7.1.jar
-jackson-jaxrs-1.7.1.jar
-jackson-mapper-asl-1.7.1.jar
-jackson-xc-1.7.1.jar
-jersey-client-1.7.jar
-jersey-core-1.7.jar
-jersey-json-1.7.jar
-jersey-server-1.7.jar
-jettison-1.1.jar
-jsr311-api-1.1.1.jar
2.jerseyの組み込み
Tomcatを使用してみます。開発環境は、Eclipseを使用します。
「Dynamic Web Project」を作成します。
上記のファイルを、WEB-INF/libに格納し、ビルドパスにも追加します。
3. web.xmlの設定
web.xmlに、JerseyのServletContainerを登録します。
<servlet>
<servlet-name>Jersey Web Application</servlet-name>
<servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Jersey Web Application</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>
4. モデルクラスの作成
Userというbeanモデルクラスを作成します。これを扱うサービスとします。
1@XmlRootElement(name="user")
2public class User {
3 private int id;
4 private String name;
5 private int age;
6
7 @XmlElement(name="id")
8 public int getId() {
9 return id;
10 }
11 public void setId(int id) {
12 this.id = id;
13 }
14
15 @XmlElement(name="name")
16 public String getName() {
17 return name;
18 }
19 public void setName(String name) {
20 this.name = name;
21 }
22
23 @XmlElement(name="age")
24 public int getAge() {
25 return age;
26 }
27 public void setAge(int age) {
28 this.age = age;
29 }
30}
5. Serviceクラスを作成
UserServiceというクラスを作成し、Userの取得、作成、更新、削除を出来るようにしてみます。
まずは、クラス定義とデータ操作メソッド。
@Pathで、このクラスが受け付けるパスを設定します。
usersは、DBの代わりです。
findUser, deleteUserで取得更新機能を提供します。
1@Path("/user")
2public class UserService {
3
4 private static Map<Integer, User> users = new ConcurrentHashMap<Integer, User>();
5
6 private User findUser(int id) {
7 User user = users.get(id);
8 return user;
9 }
10
11 private void deleteUser(int id) {
12 if (users.get(id) != null) {
13 users.remove(id);
14 }
15 }
GET
まずは、取得。メソッドはGETです。
@Pathと@PathParamでパラメータを引数に取れます。
また、@ProducesでレスポンスのContent-Typeを指定するとJAX-RSが勝手にreturnしたUserをJAXBで、XMLにして返却してくれます。
1@GET
2@Path("{id}")
3@Produces("application/xml")
4public User getUser(@PathParam("id") int id) {
5
6 User user = findUser(id);
7 if (user == null) {
8 throw new WebApplicationException(Response.Status.NOT_FOUND);
9 }
10 return user;
11}
GET /RestSample/user/23 HTTP/1.1
Host: localhost:8080
HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
Content-Type: application/xml
Transfer-Encoding: chunked
Date: Sun, 22 May 2011 03:17:03 GMT
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<user>
<age>34</age>
<id>23</id>
<name>Koshi Inaba</name>
</user>
POST
次は登録。メソッドはPOSTです。
@Consumesでリクエストの形式を指定します。
そうすると、メソッドの引数にUserを指定すると、こちらもリクエストを解析し、userに設定してくれます。
1@POST
2@Consumes("application/xml")
3@Produces("application/xml")
4public User create(User user) {
5 users.put(user.getId(), user);
6 return user;
7}
POST /RestSample/user/ HTTP/1.1
Content-Type: application/xml
Host: localhost:8080
Content-Length: 109
<?xml version="1.0" encoding="UTF-8" standalone="yes"?><user><age>34</age><id>34</id><name>TAK MATSUMOTO</name></user>
HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
Content-Type: application/xml
Content-Length: 109
Date: Sun, 22 May 2011 03:16:54 GMT
<?xml version="1.0" encoding="UTF-8" standalone="yes"?><user><age>34</age><id>34</id><name>TAK MATSUMOTO</name></user>
PUT
次は更新。メソッドはPUTです。
アノテーションとメソッド引数は取得と登録の組み合わせな感じ。
1@PUT
2@Path("{id}")
3@Consumes("application/xml")
4public Response update(@PathParam("id") int id, User update) {
5
6 User current = findUser(id);
7 if (current == null) {
8 throw new WebApplicationException(Response.Status.NOT_FOUND);
9 }
10 current.setName(update.getName());
11 current.setAge(update.getAge());
12
13 return Response.ok().build();
14}
1PUT /RestSample/user/23 HTTP/1.1
2Content-Type: application/xml
3Host: localhost:8080
4Content-Length: 115
5
6<?xml version="1.0" encoding="UTF-8" standalone="yes"?><user><age>34</age><id>23</id><name>mabushii_sign</name></user>
7
8HTTP/1.1 200 OK
9Server: Apache-Coyote/1.1
10Content-Length: 0
11Date: Sun, 22 May 2011 02:58:18 GMT
DELETE
最後に削除。メソッドはDELETEです。
1@DELETE
2@Path("{id}")
3public Response delete(@PathParam("id") int id) {
4
5 deleteUser(id);
6 return Response.ok().build();
7}
DELETE /RestSample/user/23 HTTP/1.1
Host: localhost:8080
HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
Content-Length: 0
Date: Sun, 22 May 2011 06:20:19 GMT
まとめ
このように、簡単にRESTサービスを組むことが出来ます。
また、application/xmlをapplication/jsonにすればJSONにすることも出来ます。
もちろん、他のHTTPヘッダーやCookieなども簡単に設定することが出来ます。