The router is the component that translates each incoming HTTP request to an action call (a static, public method in a controller class).
router 组件的功能是把收到的HTTP request 转换成对action的调用(controller 里的一个 static,public 方法).
An HTTP request is seen as an event by the MVC framework. This event contains two major pieces of information:
一个HTTP请求被MVC框架看作是一个事件,这个事件包含两个主要的信息:
Routes are defined in the conf/routes file, which is compiled. This means that you’ll see route errors directly in your browser:
Routes 是在 conf/routes 文件中定义的,它会被编译,也就是说你可以直接在浏览器中看到route的错误。
conf/routes is the configuration file used by the router. This file lists all of the routes needed by the application. Each route consists of an HTTP method and URI pattern associated with a call to an action method.
conf/routes 是router使用的配置文件。这个文件列出了应用程序所需要的所有routes。每个route由一个HTTP方法和一个与action调用相关联的 URI pattern 组成。
Let’s see what a route definition looks like:
来看一下route是怎样定义的:
GET /clients/:id controllers.Clients.show(id: Long)
Note that in the action call, the parameter type comes after the parameter name, like in Scala.
注意在对action的调用中,参数类型在参数名称的后面,这有点像scala的定义方式。
Each route starts with the HTTP method, followed by the URI pattern. The last element of a route is the call definition.
每个route的开头是 HTTP方法,后面跟着 URI pattern ,最后面定义了会调用哪个action。
You can also add comments to the route file, with the # character:
你也可以在route文件中添加评论,用 # 来标识:
# Display a client. GET /clients/:id controllers.Clients.show(id: Long)
The HTTP method can be any of the valid methods supported by HTTP (GET, POST,PUT, DELETE, HEAD).
HTTP方法可以是HTTP支持的任何一种有效的方法(GET, POST,PUT, DELETE, HEAD).
The URI pattern defines the route’s request path. Some parts of the request path can be dynamic.
URI pattern表示route的请求路径. 这个请求路径的某些部分可以是动态的。
For example, to exactly match GET /clients/all incoming requests, you can define this route:
例如,为了提取与 GET /clients/all 相匹配的请求,你可以这样定义:
GET /clients controllers.Clients.list()
If you want to define a route that, say, retrieves a client by id, you need to add a dynamic part:
如果你想定义一个通过id来获取一个client的路由,你就需要添加一个动态的部分:
GET /clients/:id controllers.Clients.show(id: Long)
Note that a URI pattern may have more than one dynamic part.
注意一个URI pattern 可以有不止一个动态部分.
The default matching strategy for a dynamic part is defined by the regular expression [^/]+, meaning that any dynamic part defined as :id will match exactly one URI path segment.
对于动态部分的默认匹配策略是由正则表达式 [^/]+ 定义的,这意味着任何被定义成 :id 的动态部分将会被准确的匹配到一个URI的路径部分。
If you want a dynamic part to capture more than one URI path segment, separated by forward slashes, you can define a dynamic part using the *id syntax, which uses the .* regular expression:
如果你想用一个动态部分来捕获多个独立的URI路径段, 你可以使用正则表达式的*id 语法来定义一个动态部分:
GET /files/*name controllers.Application.download(name)
Here, for a request like GET /files/images/logo.png, the name dynamic part will capture the images/logo.png value.
对于一个像 GET /files/images/logo.png 的请求来说,name的动态部分将会捕获 images/logo.png 这个值
You can also define your own regular expression for a dynamic part, using the$id<regex> syntax:
你也可以使用$id<regex> 语法来为动态部分定义自己的正则表达式:
GET /clients/$id<[0-9]+> controllers.Clients.show(id: Long)
The last part of a route definition is the call. This part must define a valid call to an action method.
route定义的最后一部分是调用。这部分必须定义一个有效的对action方法的调用。
If the method does not define any parameters, just give the fully-qualified method name:
如果方法没有定义任何参数,就只需给出一个合法的方法名:
GET / controllers.Application.homePage()
If the action method defines parameters, the corresponding parameter values will be searched for in the request URI, either extracted from the URI path itself, or from the query string.
如果action方法定义了参数,相对应的参数值需要从请求的URI中寻找,或者从URI路径本身提取,或者从查询字符串中提取。
# Extract the page parameter from the path. # i.e. http://myserver.com/index GET /:page controllers.Application.show(page)
Or:
# Extract the page parameter from the query string. # i.e. http://myserver.com/?page=index GET / controllers.Application.show(page)
Here is the corresponding show method definition in the controllers.Applicationcontroller:
这是一个 在 controllers.Application 中定义的与show方法对应的controller
public static Result show(String page) { String content = Page.getContentOf(page); response().setContentType("text/html"); return ok(content); }
GET /client/:id controllers.Clients.show(id: Long)
Then use the same type for the corresponding action method parameter in the controller:
并且在controller中相应的action方法参数也需要使用相同的类型。
public static Result show(Long id) {
Client client = Client.findById(id);
return ok(views.html.Client.show(client));
}
Note: The parameter types are specified using a suffix syntax. Also The generic types are specified using the [] symbols instead of <>, as in Java. For example, List[String] is the same type as the Java List<String>.
注意:参数类型是使用后缀语法定义的,泛型是使用[] 符号定义,而不是像java一样使用<>定义。例如,
List[String]和Java List<String>是同一种类型
Sometimes you’ll want to use a fixed value for a parameter:
有时候你可能想使用固定值作为参数:
# Extract the page parameter from the path, or fix the value for / GET / controllers.Application.show(page = "home") GET /:page controllers.Application.show(page)
You can also provide a default value that will be used if no value is found in the incoming request:
你也可以提供一个默认值,如果收到的请求中没找到参数的值就会使用这个默认值。
# Pagination links, like /clients?page=3 GET /clients controllers.Clients.list(page: Integer ?= 1)
Many routes can match the same request. If there is a conflict, the first route (in declaration order) is used.
许多routes可以匹配相同的请求,如果有冲突的话就会使用声明中的第一个route。
The router can be used to generate a URL from within a Java call. This makes it possible to centralize all your URI patterns in a single configuration file, so you can be more confident when refactoring your application.
router可以根据一个java调用来产生一个URL。这使得在一个配置文件里集中配置所有你的URI pattern变得可能,这样,当你做重构是就会更加自信。
For each controller used in the routes file, the router will generate a ‘reverse controller’ in the routes package, having the same action methods, with the same signature, but returning a play.mvc.Call instead of a play.mvc.Result.
对于routes文件中的每一个controller,router都会在 routes 包里生成一个'反转controller', 它有相同的action方法,相同的特征,但是返回的却是一个 play.mvc.Call而不是 play.mvc.Result。
The play.mvc.Call defines an HTTP call, and provides both the HTTP method and the URI.
play.mvc.Call 定义了一个HTTP 调用,而且还提供了HTTP方法和URI.
For example, if you create a controller like:
举个例子,如果你创建一个像这样的controller:
package controllers;
import play.*;
import play.mvc.*;
public class Application extends Controller {
public static Result hello(String name) {
return ok("Hello " + name + "!");
}
}
And if you map it in the conf/routes file:
然后你在conf/routes文件中配置映射关系:
# Hello action GET /hello/:name controllers.Application.hello(name)
You can then reverse the URL to the hello action method, by using thecontrollers.routes.Application reverse controller:
你就可以通过使用controllers.routes.Application 反转 controller把 URL反转到 hello action 方法
// Redirect to /hello/Bob
public static Result index() {
return redirect(controllers.routes.Application.hello("Bob"));
}