`

用Spring MVC自己动手写TOP(Taobao Open Platform)

阅读更多
   最近在开发自己公司网站的开放API服务,较深入地研究了TOP(Top Open Platform:淘宝开放平台http://api.taobao.com)。在接触过这么多的网站API中,发现TOP真的是做得非常不错,结构清晰明了,使用简单轻便。但是TOP便没有开源,搞不到TOP的源码。所以只能“自己动手,丰衣足食”了。
   我基于Spring MVC 3.0进行开发,居然3天就完工了,现在已经在公司中使用,大家的反映相当不错,现已整理了一份PPT文档,奉献给大家。同时,我将其命名为ROP(Rest Open Platform),已经在github中发布,地址是:
   https://github.com/itstamen/rop
   欢迎大家讨论!
   ROP的快速开发完成,其实是借力于Spring MVC灵活的扩展性和其提供了各种好用且强大的工具类,ROP基于Spring MVC,在处理流程上进行了重新的组织,但是在实现上基本上直接利用Spring提供的工具类和组件,所以实现并不太难。
   以下是基于ROP开发Web Service的简单例子:
   例子说明:
   根据userName/password/salary这三个属性创建一个新用户。
   第1步:创建请求对象
package com.sample.rop.request;
import com.stamen.rop.RopRequest;
import org.springframework.format.annotation.NumberFormat;
import javax.validation.constraints.DecimalMax;
import javax.validation.constraints.DecimalMin;
import javax.validation.constraints.Pattern;

public class CreateUserRequest extends RopRequest {

@Pattern(regexp = "\\w{4,30}")//① 通过JSR303注解指定验证规则
private String userName;

@Pattern(regexp = "\\w{6,30}")//②
private String password;

@DecimalMin("1000.00")
@DecimalMax("100000.00")
@NumberFormat(pattern = "#,###.##")//③
private long salary;

//getter and setter...
}

   ①、②及③处通过JSR303注解指定请求参数的合法性规则,如果请求参数值违反了规则,ROP会产生相应的错误报文。

第2步:创建响应对象
package com.sample.rop;
import com.rop.RopResponse;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlRootElement;
@XmlAccessorType(XmlAccessType.FIELD) //①
@XmlRootElement(name = "sampleRopResponse1")
public class CreateUserResponse implements RopResponse{
    @XmlAttribute//②
    private String userId;
    @XmlAttribute//③
    private String createTime;
   //getter and setter...
}

    ①、②及③处通过JAXB(即JSR222 已经包含在JDK6中)的注解对响应对象的流化规则进行设置,ROP会自动将响应的对象流化成相应的响应报文,支持XML和JSON格式,仅需通过format的参数进行指定返回格式即可。

第3步:创建服务方法
package com.sample.rop;

import com.rop.ApiMethod;
import com.sample.rop.request.CreateUserRequest;
import com.sample.rop.response.CreateUserResponse;
import org.springframework.stereotype.Service;

@Service//① 服务方法所在的类必须标注成Bean
public class UserRestService {

    @ApiMethod("sample.user.add")//②指定对应的API方法
    public RopResponse addUser(CreateUserRequest request) {
        CreateUserResponse response = new CreateUserResponse();
        //add creaet new user here...
        response.setCreateTime("20120101010101");
        response.setUserId("1");
        return response;
    }
}

   首先,服务方法所在的类必须标注成Bean,如①所示,然后在服务方法中标注ROP的@ApiMethod注解,如②所示,这里的
@ApiMethod("sample.user.add")表示,addUser(...)将处理?method=sample.user.add&...的服务请求。
处理方法的签名规约如下:
  
  • 入参必须继承于RopRequest父类,也可以为空(无入参);
  • 返回值必须实现RopResponse接口,如果一般的服务方法都拥有错误的可能,因此一般直接使用RopResponse作为返回类型,这样不管是正确的响应对象,还是错误的响应对象,都可以满足签名的要求。
  •   

 
   这样,所有服务端的开发工作就完成了!下面来写客户端调用的代码,由于现在ROP还没有提供客户端调用包,所以我们直接使用Spring的RestTemplate来写:
package com.sample.rop;

import com.rop.validation.DefaultRopValidator;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;
import java.util.ArrayList;

public class UserRestServiceClient {

    public static void main(String[] args) {
        RestTemplate restTemplate = new RestTemplate();
        MultiValueMap<String, String> form = new LinkedMultiValueMap<String, String>();
        form.add("method", "sample.user.add");//<--指定服务名
        form.add("appKey", "00001");//<--指定客户端应用的key,我们在rop.appSecret.properties
                                    //中预定义了两个appKey,服务端可通过实现AppSecretManager
                                    //定义自己的appKey管理策略。
        form.add("v", "1.0");

        form.add("sessionId", "test");//真实系统时,必须是真正的sessionId.
        form.add("format", "xml");
        form.add("locale", "en");

        form.add("userName", "tomson");
        form.add("password", "123456");
        form.add("salary", "2,500.00");

        //对请求参数进行签名,对于"00001" appKey的密钥是"abcdeabcdeabcdeabcdeabcde"
        String sign = DefaultRopValidator.sign(new ArrayList<String>(
                            form.keySet()), form.toSingleValueMap(),
                            "abcdeabcdeabcdeabcdeabcde");

        form.add("sign", sign);

        //发送请求,调用服务
        String response = restTemplate.postForObject(
                "http://localhost:9080/router", form, String.class);
        System.out.println("response:\n" + response);
    }
}

   这里的系统级参数,我们直接模仿TOP设计,说明如下:
No  parmName    paramType   required    desc
1.  method          String          Y   API method name(sample.user.add)
2.  appKey          String          Y   design to application's appKey,you can define in rop.
                                        appSecret.properties which is in classpath.
3.  v               String          Y   API version,now only support:1.0。
4.  sign            String          Y   API parameters's sing,Use SHA1 encryption algorithm
5.  sessionId       String          N   use's sessionId.you can provide a rest api so client can
                                        get it and maintain locally.
6.  format          String          N   Optional, designated response format. The default XML,
                                        currently  support for an XML format, json
7.  locale          String          N   locale,such lick cn_ZH,en...

  参见:
http://open.taobao.com/doc/detail.htm?id=111

  启用服务端的服务后,执行该测试,将返回:
  <?xml version="1.0" encoding="utf-8" standalone="yes"?>
  <sampleRopResponse1 createTime="20120101010101" userId="1"/>

  如果将format参数设置为json,则其返回的报文为:
   {"sampleRopResponse1":{"userId":"1","createTime":"20120101010101"}}

  如果将salary参数改为"aaa",则将返回错误报文(假设format为xml):
<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<error solution="Invalid Arguments" message="Invalid Arguments " code="34">
    <subErrors>
        <subError>
            <code>isv.parameters-mismatch:salary-and-aaa</code>
            <message>incoming parameter salary and aaa does not match, both 

have a certain correspondence between</message>
        </subError>
    </subErrors>
</error>

   ROP使用到了Spring很多底层的功能,有兴趣的iteyeer可以看我的《Spring3.x企业应用开发实战》,书中有较详细的介绍。也欢迎各位高手参加ROP开源项目中,可以在iteye中给我短消息报名参加。谢谢!


   
分享到:
评论
4 楼 liangmk 2016-03-22  
rop.appSecret.properties这个文件在哪里啊?
没看到啊
3 楼 xosadan 2012-04-10  
这个top感觉是为了生成rest、webservice的api,这个和Jersey、cxf之类已经相对成熟的rest开源组件对比起来有哪些优势呢?能做到哪些特殊的应用呢
2 楼 wwwlike 2012-03-13  
response:
{"error":{"code":"27","message":"Invalid Method","solution":"Invalid Method"}}
1 楼 wwwlike 2012-03-10  
运行  结果是index.html页面的代码哦

相关推荐

    Rapid Open Platform

    Rop,即Rapid Open Platform,是一个参考淘宝开放平台(TOP Taobao Open Platform)的平台设计思路,充分借鉴Spring MVC的技术架构原理开发的一个快速服务开放平台开源框架项目,可以让您迅速构建成熟的SOA服务平台。...

    ROP(Rest Open Platform)用户开发手册

    Rop,即Rapid Open Platform,是一个参考淘宝开放平台(TOP Taobao Open Platform)的平台设计思路,充分借鉴Spring MVC的技术架构原理开发的一个快速服务开放平台开源框架项目,可以让您迅速构建成熟的SOA服务平台。...

    spring-boot-reference.pdf

    Auto-configured Spring REST Docs Tests with Mock MVC Auto-configured Spring REST Docs Tests with REST Assured 43.3.20. User Configuration and Slicing 43.3.21. Using Spock to Test Spring Boot ...

    java源码平台-java-platform:此工程不更新了,请移步到最新的工程https://github.com/xiangxik/cas

    platform Based on servlet3.1 module standardization, use spring MVC, JPA, spring data, querydsl, shiro, fastjson, Beetl, infinispan, redis etc. open source technology, build the modular extension of ...

    MISDEV:它是管理信息系统开发平台,J2EE BS框架。 使用它非常容易开发MIS项目。它结合了JQuery,Spring MVC,Apache Shiro,MyBatis等。 内置核心模块如

    and efficient, high performance, strong security of the open source J2EE development platform. MISDEV include the basic functions of the enterprise information system and efficient code generation ...

    开发用jar包合集

    spring-webmvc-5.0.6.RELEASE-javadoc.jar spring-webmvc-5.0.6.RELEASE-sources.jar spring-webmvc-5.0.6.RELEASE.jar spring-websocket-5.0.6.RELEASE-javadoc.jar spring-websocket-5.0.6.RELEASE-sources....

    sz-platform:ServiceZone 平台,基于开源

    ServiceZone Platform, based open source 基于开源产品构建 portal+bpm web UI: jquery ligerUI web controler: spring mvc siteMech(will remove) business: spring activiti backend: JPA(hibernate) + MyBatis ...

    JAVA上百实例源码以及开源项目源代码

     通过网络或磁盘等方式,把公钥编码传送给李四,李四接收到张三编码后的公钥,将其解码,李四用张三的公钥加密信息,并发送给李四,张三用自己的私钥解密从李四处收到的信息…… Java利用DES私钥对称加密代码实例 ...

    JAVA上百实例源码以及开源项目

     通过网络或磁盘等方式,把公钥编码传送给李四,李四接收到张三编码后的公钥,将其解码,李四用张三的公钥加密信息,并发送给李四,张三用自己的私钥解密从李四处收到的信息…… Java利用DES私钥对称加密代码实例 ...

    java面试题以及技巧

    │ Struts+Hibernate+Spring轻量级J2EE企业应用实战.pdf │ Struts中文手册.pdf │ Struts配置文件详解.txt │ 上海税友.txt │ 上海税友软件 面试题.doc │ 公司培训文档-混淆的基本概念.doc │ 基本算法.doc │ ...

    java面试题目与技巧1

    │ Struts+Hibernate+Spring轻量级J2EE企业应用实战.pdf │ Struts中文手册.pdf │ Struts配置文件详解.txt │ 上海税友.txt │ 上海税友软件 面试题.doc │ 公司培训文档-混淆的基本概念.doc │ 基本算法.doc │ ...

    java面试题及技巧4

    │ Struts+Hibernate+Spring轻量级J2EE企业应用实战.pdf │ Struts中文手册.pdf │ Struts配置文件详解.txt │ 上海税友.txt │ 上海税友软件 面试题.doc │ 公司培训文档-混淆的基本概念.doc │ 基本算法.doc │ ...

    java面试题及技巧3

    │ Struts+Hibernate+Spring轻量级J2EE企业应用实战.pdf │ Struts中文手册.pdf │ Struts配置文件详解.txt │ 上海税友.txt │ 上海税友软件 面试题.doc │ 公司培训文档-混淆的基本概念.doc │ 基本算法.doc │ ...

    java面试题以及技巧6

    │ Struts+Hibernate+Spring轻量级J2EE企业应用实战.pdf │ Struts中文手册.pdf │ Struts配置文件详解.txt │ 上海税友.txt │ 上海税友软件 面试题.doc │ 公司培训文档-混淆的基本概念.doc │ 基本算法.doc │ ...

Global site tag (gtag.js) - Google Analytics