这次用JAVA代码来复现一次调用。基于JFinal框架。(上次PHP调用看上一篇文章)
一、在控制器创建BaidumapController
package Controller;
import Calculation.SnCal;
import com.jfinal.core.Controller;
import com.jfinal.kit.HttpKit;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.LinkedHashMap;
import java.util.Map;
public class BaidumapController extends Controller {
public void index() throws UnsupportedEncodingException {
String sk = "yoursk";
String uri = "/direction/v2/transit?";
String ak = "yourak";
String origin = "22.693621,113.817503";
String destination = "22.579575,114.143696";
String origin_uid = "桥头-地铁站";
String destination_uid = "太安-地铁站";
String departure_time = "10:00-12:00";
String tactics_incity = "5";
int timestamp = (int) (System.currentTimeMillis() / 1000);
SnCal snCal = new SnCal();
/* 计算sn跟参数对出现顺序有关,get请求请使用LinkedHashMap保存<key,value>,该方法根据key的插入顺序排序;post请使用TreeMap保存<key,value>,该方法会自动将key按照字母a-z顺序排序。所以get请求可自定义参数顺序(sn参数必须在最后)发送请求,但是post请求必须按照字母a-z顺序填充body(sn参数必须在最后)。以get请求为例:http://api.map.baidu.com/geocoder/v2/?address=百度大厦&output=json&ak=yourak,paramsMap中先放入address,再放output,然后放ak,放入顺序必须跟get请求中对应参数的出现顺序保持一致。 */
Map paramsMap = new LinkedHashMap<String, String>();
paramsMap.put("origin", origin);
paramsMap.put("destination", destination);
paramsMap.put("origin_uid", origin_uid);
paramsMap.put("destination_uid", destination_uid);
paramsMap.put("departure_time", departure_time);
paramsMap.put("tactics_incity", tactics_incity);
paramsMap.put("ak", ak);
paramsMap.put("timestamp", Integer.toString(timestamp));
// 调用下面的toQueryString方法,对LinkedHashMap内所有value作utf8编码,拼接返回结果
String paramsStr = snCal.toQueryString(paramsMap);
// 对paramsStr前面拼接上uri,后面直接拼接yoursk
String wholeStr = new String(uri + paramsStr + sk);
// 对上面wholeStr再作utf8编码
String tempStr = URLEncoder.encode(wholeStr, "UTF-8");
// 调用下面的MD5方法得到最后的sn签名
String sn= snCal.MD5(tempStr);
// 用返回的sn拼接进URL
String url = "http://api.map.baidu.com/direction/v2/transit?origin="+URLEncoder.encode(origin)+"&destination="+URLEncoder.encode(destination)+"&origin_uid="+URLEncoder.encode(origin_uid)+"&destination_uid="+URLEncoder.encode(destination_uid)+"&departure_time="+URLEncoder.encode(departure_time)+"&tactics_incity="+tactics_incity+"&ak="+ak+"&sn="+sn+"×tamp="+timestamp;
// 模拟http get请求
String json = HttpKit.get(url);
// 返回json
renderJson(json);
}
}
二、在公共函数包中创建SnCal类
package Calculation;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.Map;
import java.util.Map.Entry;
//java版计算signature签名
public class SnCal {
// 对Map内所有value作utf8编码,拼接返回结果
public String toQueryString(Map<?, ?> data) throws UnsupportedEncodingException
{
StringBuffer queryString = new StringBuffer();
for (Entry<?, ?> pair : data.entrySet()) {
queryString.append(pair.getKey() + "=");
queryString.append(URLEncoder.encode((String) pair.getValue(), "UTF-8") + "&");
}
if (queryString.length() > 0) {
queryString.deleteCharAt(queryString.length() - 1);
}
return queryString.toString();
}
// 来自stackoverflow的MD5计算方法,调用了MessageDigest库函数,并把byte数组结果转换成16进制
public String MD5(String md5) {
try {
java.security.MessageDigest md = java.security.MessageDigest.getInstance("MD5");
byte[] array = md.digest(md5.getBytes());
StringBuffer sb = new StringBuffer();
for (int i = 0; i < array.length; ++i) {
sb.append(Integer.toHexString((array[i] & 0xFF) | 0x100).substring(1, 3));
}
return sb.toString();
} catch (java.security.NoSuchAlgorithmException e) {
}
return null;
}
}