Play! 框架上的 RESTful

我们正在计划一个项目,主要服务内容的移动应用程序,但需要有一个网站。

我的问题是,使用 Jersey 或 Restlet 为我们的移动应用程序开发 REST API,然后使用 Play 是否有意义!为网站提供服务。

Or does it make more sense to just use Play! to do it all? If so, how to do REST with Play! framework?

68724 次浏览

Use Play! to do it all. 在 Play 中编写 REST 服务非常非常容易。

首先,路由文件使得编写符合 REST 方法的路由变得非常简单。

然后,在控制器中为要创建的每个 API 方法编写操作。

根据您希望如何返回结果(XML、 JSON 等) ,有几种方法可以使用。例如,使用 renderJSON 方法,可以非常容易地呈现结果。如果您想呈现 XML,那么您可以使用与在视图中构建 HTML 文档相同的方法。

这里有一个简洁的例子。

路由档案

GET     /user/{id}            Application.getUser(format:'xml')
GET     /user/{id}/json       Application.getUserJSON
POST    /user/                Application.createUser
PUT     /user/{id}            Application.updateUser
DELETE  /user/{id}            Application.deleteUser

申请文件

public static void createUser(User newUser) {
newUser.save();
renderText("success");
}


public static void updateUser(Long id, User user) {
User dbUser = User.findById(id);
dbUser.updateDetails(user); // some model logic you would write to do a safe merge
dbUser.save();
renderText("success");
}


public static void deleteUser(Long id) {
// first check authority
User.findById(id).delete();
renderText("success");
}


public static void getUser(Long id)  {
User user = User.findById(id)
renderJSON(user);
}


public static void getUserJSON(Long id) {
User user = User.findById(id)
renderJSON(user);
}

Xml 文件

<user>
<name>${user.name}</name>
<dob>${user.dob}</dob>
.... etc etc
</user>

与 JAX-RS 实现集成是使用 Play 内置 HTTP 路由的一种可能的替代方法。有关 RESTEasy 示例,请参见 RESTEasy Play! 模块

如果您已经投资于 JAX-RS,或者需要 JAX-RS 提供的一些高级特性 REST,例如内容协商,那么这种方法是有意义的。如果没有,那么直接使用 Play 来响应 HTTP 请求为 JSON 或 XML 提供服务会更简单。

根据请求,采用简单的类 REST 方法。它的工作方式与 Codemwncis 的解决方案几乎相同,但使用 Accept 头进行内容协商。首先是路线文件:

GET     /user/{id}            Application.user
POST    /user/                Application.createUser
PUT     /user/{id}            Application.updateUser
DELETE  /user/{id}            Application.deleteUser

这里不指定任何内容类型。恕我直言,这样做只有在您希望对某些资源拥有“特殊”URI 时才是必要的。就像在 Atom/RSS 中声明到 /users/feed/的路由始终返回。

应用程序控制器如下所示:

public static void createUser(User newUser) {
newUser.save();
user(newUser.id);
}


public static void updateUser(Long id, User user) {
User dbUser = User.findById(id);
dbUser.updateDetails(user); // some model logic you would write to do a safe merge
dbUser.save();
user(id);
}


public static void deleteUser(Long id) {
User.findById(id).delete();
renderText("success");
}


public static void user(Long id)  {
User user = User.findById(id)
render(user);
}

如您所见,我只是删除了 getUserJSON 方法并重命名了 getUser 方法。对于不同的内容类型,您现在必须创建几个模板。每个需要的内容类型一个。例如:

Xml:

<users>
<user>
<name>${user.name}</name>
. . .
</user>
</users>

Json:

{
"name": "${user.name}",
"id": "${user.id}",
. . .
}

网址:

<html>...</html>

这种方法总是为浏览器提供 HTML 视图,因为所有浏览器都在 Accept 头中发送一个文本/HTML 内容类型。所有其他客户端(可能是一些基于 JavaScript 的 AJAX 请求)都可以定义自己所需的内容类型。使用 jQuery ajax ()方法,您可以执行以下操作:

$.ajax({
url: @{Application.user(1)},
dataType: json,
success: function(data) {
. . .
}
});

它将以 JSON 格式提供关于 ID 为1的 User 的详细信息。Play 目前本地支持 HTML、 JSON 和 XML,但您可以通过遵循 正式文件或使用 内容协商模块内容协商模块轻松地使用不同的类型。

如果您正在使用 Eclipse 进行开发,我建议您使用 REST 客户端插件,它允许您测试路由及其相应的内容类型。

you should have a look at

Http://www.lunatech-labs.com/open-source/resteasy-crud-play-module

it's a module for play that automatically build a rest interface, just like the crud module automatically builds an admin area...

在 Play 版本1.2.3中,这种方法似乎被破坏了。如果下载由@seb 完成并在前面提到过的 https://github.com/sebhoss/play-user-sample源代码,那么使用 POST 和 JSON 对象创建新的用户对象就不再可能了。

您需要使用 json 和 xml POST 来创建特定的方法

这仍然是一个受欢迎的问题,但是投票最多的答案与当前的游戏版本不同。下面是一个使用 play 2.2.1的可用 REST 示例:

转乘/路线:

GET     /users                 controllers.UserController.getUsers
GET     /users/:id             controllers.UserController.getUser(id: Long)
POST    /users                 controllers.UserController.createUser
PUT     /users/:id             controllers.UserController.updateUser(id: Long)
DELETE  /users/:id             controllers.UserController.deleteUser(id: Long)

App/controller/UserController.java:

public static Result getUsers()
{
List<User> users = Database.getUsers();
return ok(Json.toJson(users));
}


public static Result getUser(Long id)
{
User user = Database.getUser(id);
return user == null ? notFound() : ok(Json.toJson(user));
}


public static Result createUser()
{
User newUser = Json.fromJson(request().body().asJson(), User.class);
User inserted = Database.addUser(newUser);
return created(Json.toJson(inserted));
}


public static Result updateUser(Long id)
{
User user = Json.fromJson(request().body().asJson(), User.class);
User updated = Database.updateUser(id, user);
return ok(Json.toJson(updated));
}


public static Result deleteUser(Long id)
{
Database.deleteUser(id);
return noContent(); // http://stackoverflow.com/a/2342589/1415732
}