您的位置:首页 > 其它

如何更方便快捷的调用restful服务

2016-04-15 19:31 253 查看
这里我提供我一个restful服务,地址http://restful.wozsz.com/service/application.wadl



我们如何调用这个服务呢,常规方式当然是用httpclient了,它的弊端是对于符合要求的请求json需要自己封装,对于响应的json需要自己解析拿数据,而且不能太过于复杂,不然解析起来相当费劲,一层层的。

package com.somnus.http;

import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import org.apache.commons.collections.MapUtils;
import org.apache.commons.lang.Validate;
import org.apache.http.HttpEntity;
import org.apache.http.HttpStatus;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.client.utils.URIBuilder;
import org.apache.http.conn.HttpHostConnectException;
import org.apache.http.entity.ContentType;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.alibaba.fastjson.JSON;
import com.somnus.exception.HttpStatusException;

/**
* @ClassName: HttpClientUtils.java
* @Description: TODO
* @author Somnus
* @version V1.0
* @Date 2016年10月13日 下午3:40:17
*/
public class HttpClientUtils {

private transient static Logger log = LoggerFactory.getLogger(HttpClientUtils.class);

/**
* @param url
* @param param
* @return
* @throws HttpHostConnectException
* 连接不可用
* @throws IOException
* 网络传输出错
*/
public static String doJsonPost(String url, Map<String,String> param) throws HttpHostConnectException, IOException{
Validate.notNull(url, "url is required.");
Validate.notEmpty(param);
return doJsonPost(url,JSON.toJSONString(param));
}

/**
* @param url
* @param json
* @return
* @throws HttpHostConnectException
* 连接不可用
* @throws IOException
* 网络传输出错
*/
public static String doJsonPost(String url, String json) throws HttpHostConnectException, IOException{
Validate.notNull(url, "url is required.");
Validate.notNull(json, "json is required.");
//创建HttpClient对象
CloseableHttpClient httpclient = HttpConnectionManager.getHttpClient();
String resultString = "";
CloseableHttpResponse httpResponse = null;
try {
// 创建HttpPost对象
HttpPost httpPost = new HttpPost(url);
httpPost.setEntity(new StringEntity(json,ContentType.APPLICATION_JSON));

// 开始执行http请求
long startTime = System.currentTimeMillis();
httpResponse = httpclient.execute(httpPost);
long endTime = System.currentTimeMillis();

// 获得响应状态码
int statusCode = httpResponse.getStatusLine().getStatusCode();
log.info("statusCode:" + statusCode);
log.info("调用API 花费时间(单位:毫秒):" + (endTime - startTime));

// 取出应答字符串
HttpEntity httpEntity = httpResponse.getEntity();
resultString = EntityUtils.toString(httpEntity,Charset.forName("UTF-8"));

// 判断返回状态是否为200
if (statusCode != HttpStatus.SC_OK) {
throw new HttpStatusException(String.format("\n\tStatus:%s\n\tError Message:%s", statusCode,resultString));
}
} finally{
if(httpResponse != null){
httpResponse.close();
}
httpclient.close();
}
return resultString;
}

}

@Test
public void doJsonPost(){
try {
String url = "http://120.26.68.243:8080/restful/service/com.somnus.resource.RestfulResource/getAccount";
Map<String,String> param = new HashMap<String, String>();
param.put("username", "admin");
param.put("password", "123456");
System.out.println("body:" + HttpClientUtils.doJsonPost(url, param));
} catch (HttpStatusException e){
log.error(e.getMessage(),e);
} catch (HttpHostConnectException e) {
log.error(e.getMessage(),e);
} catch (IOException e) {
log.error(e.getMessage(),e);
}
}


但是也有人肯定也知道基于jersey的api也是可以调用的

package com.somnus.support;

import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response.Status;

import org.junit.Test;

import com.somnus.domain.Request;
import com.somnus.domain.Response;
import com.somnus.resource.RestfulResource;
import com.somnus.rest.core.client.RESTfulJsonClientFactory;
import com.sun.jersey.api.client.Client;
import com.sun.jersey.api.client.ClientResponse;
import com.sun.jersey.api.client.WebResource;

public class ClientCase {

/**
* <p></p>
* @author:Somnus
 * @param args
*/
public static void main(String[] args) {
Client client = Client.create();
WebResource webResource = client.resource("http://120.26.68.243:8080/restful/service/com.somnus.resource.RestfulResource/getAccount");
ClientResponse response = webResource.entity(new Request("admin","123456"),
MediaType.APPLICATION_JSON).post(ClientResponse.class);
System.out.println(response.getStatus());
if(response.getStatus() == Status.OK.getStatusCode()){
Response r =  response.getEntity(Response.class);
System.out.println(r);
}

}


基于jersey的api调用,它需要你提供服务的接口java文件,请求和响应java文件,当然这需要服务提供方,额外进行打包抽取出自己服务相关的的接口到jar包中提供给调用者,这对于以httpclient调用的方式来说确实麻烦了点,不过在技术可行上来说,抽取工作相当方便,根本无需人工复制粘贴,只需用maven插件进行抽取。

这是我作为服务方给调用者提供的jar包



我已经打包好,并上传到nexus,http://maven.wozsz.com

<!-- 指定Maven仓库 -->
<repositories>
<!-- oschina的maven仓库 -->
<repository>
<id>repository</id>
<name>local private nexus</name>
<url>http://maven.wozsz.com:88/content/groups/public/</url>
<releases>
<enabled>true</enabled>
</releases>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
</repositories>


<dependency>
<groupId>com.somnus</groupId>
<artifactId>ruo</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>


写到这里,读者肯定会说,这有什么嘛,我要基于jersey的api调,也要对其封装啊,而且服务方多了抽取工作,调用者还得额外添加api-jar包

可是如果我已经提供了一个组件给你呢,专门用来调用jersey服务的

<dependency>
<groupId>com.somnus.rest.core</groupId>
<artifactId>rest-core</artifactId>
<version>3.2.0</version>
</dependency>


并且在spring项目中你可以以bean的形式把服务添加到项目中呢,比如这样

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

<bean id="restfulResource" class="com.somnus.rest.core.spring.RestfulJsonFactoryBean">
<property name="serviceInterface" value="com.somnus.resource.RestfulResource" />
<property name="serviceUrl" value="http://120.26.68.243:8080/restful/service/"/>
</bean>

</beans>


现在我们再次调用我提供的服务,你只需注入bean就可以了 

比如

package com.somnus.support;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.somnus.domain.Request;
import com.somnus.domain.Response;
import com.somnus.resource.RestfulResource;

@Service
public class TestServiceImpl {

@Autowired
private RestfulResource restfulResource;

public void rest(){
Response response = restfulResource.getAccount(new Request("admin","123456"));
System.out.println(response);
}
}


如果不是spring项目呢,可以用这个组件吗,回答是当然可以了,且看

package com.somnus.support;

import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response.Status;

import org.junit.Test;

import com.somnus.domain.Request;
import com.somnus.domain.Response;
import com.somnus.resource.RestfulResource;
import com.somnus.rest.core.client.RESTfulJsonClientFactory;
import com.sun.jersey.api.client.Client;
import com.sun.jersey.api.client.ClientResponse;
import com.sun.jersey.api.client.WebResource;

public class ClientCase {

private static final String BASE_URL = "http://120.26.68.243:8080/restful/service/";

RestfulResource resource = RESTfulJsonClientFactory.createClient(RestfulResource.class, BASE_URL);

@Test
public void rest(){

Response response = resource.getAccount(new Request("admin","123456"));

System.out.println(response);
}

}

POST方式

1、http://restful.wozsz.com/service/com.somnus.resource.RestfulResource/getAccount

{
"username": "admin",
"password": "123456"
}


2、http://restful.wozsz.com/service/com.somnus.resource.RestfulResource/getAccount2

<?xml version="1.0" encoding="utf-8"?>

<xml>
<username>admin</username>
<password>123456</password>
</xml>


GET方式

3、http://restful.wozsz.com/service/com.somnus.resource.RestfulResource/getAccount3/admin/123456

4、http://restful.wozsz.com/service/com.somnus.resource.RestfulResource/getAccount4?username=admin&password=123456
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: