`

Restlet实战(三)使用Component让不同的Application对应不同的资源

    博客分类:
  • REST
 
阅读更多

Restlet实战(二)我给出的例子中,把Order和Customer两个资源attach到Order Application上,看如下代码:

 

Java代码  收藏代码
  1. public class OrderApplication extends Application {     
  2.      
  3.     @Override    
  4.     public synchronized Restlet createRoot() {     
  5.         Router router = new Router(getContext());     
  6.     
  7.         router.attach("/order/{orderId}/{subOrderId}", OrderResource.class);     
  8.         router.attach("/customer/{custId}", CustomerResource.class);     
  9.         return router;     
  10.     }     
  11.     
  12. }    

 

 

这显而易见不是一个好的应用,从关注点来看,Order Resource应该attach到Order Application,那么对应Customer Resource应该有一个Customer Application与之对应。

 

ok,基于这样的思路,我们从OrderApplication删除如下代码:

Java代码  收藏代码
  1. router.attach("/customer/{custId}", CustomerResource.class);     

 

另外我们创建一个CustomerApplication,并包含上述代码:

Java代码  收藏代码
  1. public class CustomerApplication extends Application{  
  2.     @Override  
  3.     public synchronized Restlet createRoot() {  
  4.         Router router = new Router(getContext());  
  5.           
  6.         router.attach("/customers/{custId}", CustomerResource.class);  
  7.         return router;  
  8.     }  
  9. }  

 

 有了CustomerApplication,那么如何设置才能生效呢?根据之前的配制,很容易想到的是在web.xml中把CustomerApplication配制进去,事实上是不行的,看看ServerServlet类里面这段代码:

Java代码  收藏代码
  1. private static final String APPLICATION_KEY = "org.restlet.application";     
  2.   
  3.  protected Application createApplication(Context parentContext) {  
  4.         Application application = null;  
  5.   
  6.         final String applicationClassName = getInitParameter(APPLICATION_KEY,  
  7.                 null);  

 

这段代码是根据参数名org.restlet.application来获得配制在web.xml中application,而之前我们已经配制了OrderApplication,所以,我们不能再把CustomerApplication配制的参数名设置为org.restlet.application。那么在ServerServlet加载application的时候,就加载不到。

 

那么怎么作能让这两个Application生效呢?答案是Component,实际上,从上一篇文章中的图可以看出,一个Component可以设置多个Virtual Host,而一个Virtual Host能attach多个Application。

 

至于使用Component的做法有两种,一种是在web.xml中配制一个名字为“org.restlet.component”的context参数,例如:

Xml代码  收藏代码
  1. <context-param>  
  2.                  <param-name>org.restlet.component</param-name>  
  3.                  <param-value>com.mycompany.MyComponent</param-value>  
  4.          </context-param>  

 

另外一种是,WEB-INF/下存在restlet.xml,可以在这个xml文件里定义包含application和connector的Commponent。

 

下面就第二种方式来解决上面出现的问题,首先在WEB-INF/下建立一个名为restlet.xml,这个名字不能改变成别的名字,为啥呢?仍然看一下ServerServlet里面的一段代码:

Java代码  收藏代码
  1. protected Component createComponent() {  
  2.     Component component = null;  
  3.   
  4.     // Look for the Component XML configuration file.  
  5.     Client client = createWarClient(new Context(), getServletConfig());  
  6.     Response response = client.get("war:///WEB-INF/restlet.xml");  

 

既然不让改,不改好了,在restlet.xml里面放入配制Component的代码:

Xml代码  收藏代码
  1. <?xml version="1.0"?>  
  2.  <component xmlns="http://www.restlet.org/schemas/1.1/Component"  
  3.                xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
  4.                xsi:schemaLocation="http://www.restlet.org/schemas/1.1/Component">  
  5.     <!--   
  6.     <client protocol="CLAP" />  
  7.     <client protocol="FILE" />  
  8.     <client protocols="HTTP HTTPS" />  
  9.     <server protocols="HTTP HTTPS" port="8080"/>  
  10.      -->  
  11.        
  12.     <defaultHost>  
  13.        <attach uriPattern="/customers/{custId}"   
  14.                   targetClass="com.mycompany.restlet.application.CustomerApplication" />  
  15.        <attach uriPattern="/orders/{orderId}/{subOrderId}"   
  16.                   targetClass="com.mycompany.restlet.application.OrderApplication" />             
  17.        <!-- <attach uriPattern="/efgh/{xyz}" targetDescriptor="clap://class/org/restlet/test/MyApplication.wadl" /> -->  
  18.     </defaultHost>  
  19.  </component>  

 

看上面的配制文件,很清楚的我们能知道,如果在浏览器输入http://localhost:8080/restlet/customers/1,那么CustomerApplication这个类应该被访问到。

 

咦,好象有点不对,好像CustomerApplication里面在attach资源的时候,也指定了同样的URL(/customers/{custId}),那么是当前这两个URL定义的URL重复了?还是有别的含义?

 

我们可以这样理解,在restlet.xml中定义的URL附加到Context上,而在application里面定义的URL会附加到restlet.xml中定义的URL上。

 

例如,如果想通过http://localhost:8080/restlet/customers/1 来使用CustomerResource,则需要在CustomerApplication中有如下代码:

Java代码  收藏代码
  1. router.attach("", CustomerResource.class);  

 而如果想通过http://localhost:8080/restlet/customers/1/orders/2 来使用CustomerResource,则需要在CustomerApplication中定义如下代码:

 

Java代码  收藏代码
  1. router.attach("/orders/{orderId}", CustomerResource.class);  

 

Ok,让我们测试一下,首先修改

CustomerApplication.java

 

Java代码  收藏代码
  1. public class CustomerApplication extends Application{  
  2.     @Override  
  3.     public synchronized Restlet createRoot() {  
  4.         Router router = new Router(getContext());  
  5.           
  6.         //router.attach("", CustomerResource.class);  
  7.         router.attach("/orders/{orderId}", CustomerResource.class);  
  8.         return router;  
  9.     }  
  10. }  

 

CustomerResource.java

 

Java代码  收藏代码
  1. public class CustomerResource extends Resource {  
  2.     String customerId;  
  3.     String orderId;  
  4.   
  5.     public CustomerResource(Context context, Request request, Response response) {  
  6.         super(context, request, response);  
  7.         customerId = (String) request.getAttributes().get("custId");  
  8.         orderId = (String) request.getAttributes().get("orderId");  
  9.         // This representation has only one type of representation.  
  10.         getVariants().add(new Variant(MediaType.TEXT_PLAIN));  
  11.     }  
  12.   
  13.     @Override  
  14.     public Representation getRepresentation(Variant variant) {  
  15.         Representation representation = new StringRepresentation(  
  16.                 "The customer which id is " + customerId  
  17.                         + " has the order which id  : " + orderId,  
  18.                 MediaType.TEXT_PLAIN);  
  19.         return representation;  
  20.     }  
  21. }  

 

 输入http://localhost:8080/restlet/customers/1/orders/2,结果如下:

 

The customer which id is 1 has the order which id  : 2

 

请注意,上面CustomerApplicaiton被注释的一行代码

Java代码  收藏代码
  1. router.attach("", CustomerResource.class);  

如果反注释这行代码,则所有基于http://localhost:8080/restlet/customers/1/****(除了/customers/{custId}/orders/{orderId} )的访问都会路由到同一个资源(CustomerResource),换句话说,如果我访问一个我没有定义的URL,如/customers/{customerId}/orders,则也会被路由到CustomerResource,这是不对的。。所以,应慎用之。

 

总结,现在我们可以分别用不同的Application来管理不同的资源了,并采用restlet.xml这种方式来定义包含applicaiton和connector的component.

分享到:
评论

相关推荐

    Restlet实战(二十六)事务 (Transaction)

    本文将深入探讨RESTful服务中的事务处理,并以《Restlet实战(二十六)事务 (Transaction)》为例进行解析。 首先,我们要理解RESTful服务中的核心原则之一是无状态(Stateless)。这意味着每个客户端请求都包含处理...

    Restlet开发实例

    本系列的开发实例将带你深入理解并掌握Restlet框架的使用,从基础的JAX-RS实现到高级的Component和Application结构,再到与Spring框架的整合。 首先,我们来看看"RESTLET开发实例(一)基于JAX-RS的REST服务.doc"。...

    Restlet 2.0 边学边写(八)使用jQuery和ajax实现对Restlet资源的CRUD操作

    在本篇博文中,我们将深入探讨如何利用jQuery和Ajax技术与Restlet 2.0框架进行交互,实现对Restful资源的创建(Create)、读取(Read)、更新(Update)和删除(Delete)操作,即CRUD操作。Restlet是一个开源的Java ...

    restlet实现最简单的restful webservice

    3. **定义路由**:在Restlet应用中,你需要创建一个路由(Route)来映射URL到对应的资源。这可以通过创建一个Application类来完成。 ```java import org.restlet.Application; import org.restlet.Restlet; ...

    RESTLET开发(三)

    ### RESTLET开发(三):基于Spring的REST服务 #### 一、基于Spring配置的Rest简单服务 在本文档中,我们将深入探讨如何利用RESTlet框架与Spring框架结合,构建高效的RESTful服务。Spring框架因其强大的功能和灵活...

    restlet2.1学习笔记项目代码

    4. **路由(Route)**:Restlet使用`org.restlet.routing.Router`来映射不同的URI路径到相应的资源。这允许我们创建灵活的URL结构,每个路径都可以指向不同的处理逻辑。 5. **过滤器(Filter)**:过滤器允许在请求...

    restlet入门示例

    本示例将带你入门Restlet,帮助你理解如何使用它来创建简单的Web服务。 首先,让我们了解REST的基本概念。REST架构基于HTTP协议,通过HTTP方法(GET、POST、PUT、DELETE等)来操作资源。资源通常由URI(Uniform ...

    Restlet所需要的所有jar包

    此外,理解RESTful设计原则,如资源的URI定位、状态码的使用、无状态通信等,对于有效利用Restlet构建高质量的Web服务也是十分必要的。 总之,"Restlet所需要的所有jar包"的压缩包提供了开发RESTful服务的基础环境...

    restlet restful

    在Restlet框架中,"RestApplication"可能是一个实现了Restlet Application接口的类,负责初始化和管理REST服务的路由和行为。 总的来说,"restlet restful"项目是一个基于RESTlet框架的RESTful Web服务实现,提供了...

    RESTLET开发

    定义一个名为`StudentApplication`的应用类,该类继承自`javax.ws.rs.core.Application`,用于管理和注册资源。 5. **定义资源类** 实现一个具体的资源类`StudentResource`,该类需要继承自`javax.ws.rs.core....

    restlet工程示例

    在本示例中,我们将深入探讨如何使用Restlet框架来创建和使用RESTful服务。 首先,理解REST的基本原则至关重要。RESTful服务基于HTTP协议,使用HTTP方法(GET、POST、PUT、DELETE等)来操作资源。资源通过URI...

    restlet

    RESTlet是一款开源框架,专为构建基于REST(Representational ...通过学习这些资料,开发者可以深入理解RESTlet的工作原理,掌握如何使用RESTlet构建RESTful服务和客户端应用,从而提升其在Web服务开发领域的专业技能。

    Restlet in action 英文 完整版

    在《Restlet in Action》的第一章“Introducing the Restlet Framework”中,作者们详细解释了Restlet框架的核心概念,包括组件模型、资源模型以及如何使用这些模型来构建Web服务。此外,还介绍了一些高级特性,如...

    Restlet与Spring 集成

    `BaseApplication`类是自定义的Restlet应用程序,它使用`component.context`和`restRoute`。`restRoute`是一个Spring路由器,通过`attachments`映射将URL路径与处理资源的Spring Bean关联。 - **userContext.xml**...

    restlet1.1文档

    1. **使用Maven进行配置**:如果您使用的是Maven作为构建工具,可以通过添加依赖项来轻松集成Restlet。 2. **使用Eclipse进行配置**:如果您使用的是Eclipse IDE,则可以通过导入项目模板或手动添加库文件来进行配置...

    基于Spring的Restlet实例

    标题"基于Spring的Restlet实例"意味着我们将探讨如何在Spring环境中集成和使用Restlet库来开发REST服务。这通常涉及以下几个关键知识点: 1. **RESTful服务基础**:REST是一种软件架构风格,强调通过HTTP协议暴露...

    Restlet开发的Basic认证

    Restlet是一个轻量级的Java Web服务开发框架,它提供了构建RESTful(Representational State Transfer)应用程序的工具和API。REST是一种架构风格,强调简洁、无状态和可缓存的网络交互,常用于构建高性能、高可用性...

Global site tag (gtag.js) - Google Analytics