Java调用第三方接口获取数据方法

java实现调用第三方接口获取数据

最近学习向第三方接口发出http请求,获取返回数据进行存储,把内容总结一下。

几种方法

查了一些资料,总共有这么几种方法发出http请求:

  1. java的Java.net.HttpURLConnection类实现
  2. commons的HttpClient
  3. Apache封装的CloseableHttpClient
  4. SpringBoot的RestTemplate

第一个java的net提供的HttpURLConnection功能相较而言较少;HttpClient 是实现客户端与服务器通信的实现库,一般步骤是首先新建一个httpclient对象,并进行初始设置,然后设置get、post方法对象,设置请求参数,之后执行get、post方法获取response响应结果,最后处理结果释放连接;CloseableHttpClient进行了优化,能够自动关闭连接,默认会创建一个大小为5的连接池;RestTemplate功能更广泛,程序也不复杂。因为是小程序,所以选了使用CloseableHttpClient,用不着SpringBoot。

实现

新建maven工程,在pom.xml中导入httpclient与fastjson包,httpclient用来请求,fastjson进行参数转换与处理数据。
get方法:利用 HttpClientBuilder创建连接对象

   public static String getMethod(String url){
    CloseableHttpClient httpClient = HttpClientBuilder.create().build();
    HttpGet get = new HttpGet(url); 
  try{  
   //这里可以设置请求参数,token等
  get.addHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.81 Safari/537.36");
    HttpResponse response = httpClient.execute(get);//执行获取响应
                if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK){//根据状态码处理
                    //返回字符串
                    String res = EntityUtils.toString(response.getEntity());
                    return res;
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
            return null;
}

post方法:

public static String postMethod(String url, JSONObject json){        
        try {
        CloseableHttpClient httpClient = HttpClientBuilder.create().build();
            HttpPost post = new HttpPost(url);
            post.addHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.81 Safari/537.36");
            StringEntity s = new StringEntity(json.toString());
            s.setContentEncoding("UTF-8");
           //发送json数据需要设置contentType
           s.setContentType("application/x-www-form-urlencoded");
            post.setEntity(s); //设置请求参数
           HttpResponse response = httpClient.execute(post);
          if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK){
                    //返回String
                    String res = EntityUtils.toString(response.getEntity());
                    return res;
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

获取token等可以根据需要编写

参数处理与解析数据

获得的响应参数可以使用json‘进行分析,[ ]为数组,{ }为对象,利用 JSONObject.parseObject(String text)将字符串转为json对象,调用getJSONArray(key)获取json数组JSONArray,getString(key)获取对应的值,getJSONObject()获取json对象。可以根据json结构层层解析,获取需要的数据。
新建json对象,调用put方法可以赋值,之后作为请求参数设置。

数字证书

发出请求链接可能出现数字证书无效,PKIX path building failed、unable to find valid certification path to requested target
可以在代码中创建忽略证书验证的CloseableHttpClient

public CloseableHttpClient getIgnoeSSLClient() throws Exception {
   SSLContext sslContext = SSLContexts.custom().loadTrustMaterial(null, new TrustStrategy() {
      @Override
public boolean isTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {
         return true;
      }
   }).build();

   //创建httpClient
CloseableHttpClient client = HttpClients.custom().setSSLContext(sslContext).
         setSSLHostnameVerifier(new NoopHostnameVerifier()).build();
   return client;
}

缓存

由于http请求需要token验证,调用不同接口需要将token放入请求参数,token有一定时限,为了避免不停获取token,可以将其放入缓存中,减少交互提高效率。利用并发的ConcurrentHashMap实现。

object对象存token,需要用token时从缓存中找,若是过期或者为null则获取token放入缓存

 //预缓存信息
    private static final Map CACHE_MAP = new ConcurrentHashMap();
//每个缓存生效时间10小时
public static final long CACHE_HOLD_TIME_24H = 24 * 60 * 60 * 1000L;
/**
 * 存放一个缓存对象,默认保存时间24小时
 * @param cacheName
 * @param obj
 */
/*public static void put(String cacheName, Object obj) {
    put(cacheName, obj, CACHE_HOLD_TIME_24H);
}*/
/**
 * 存放一个缓存对象,保存时间为holdTime
 * @param cacheName
 * @param obj
 * @param holdTime
 */
public static void put(String cacheName, Object obj, long holdTime) {
    CACHE_MAP.put(cacheName, obj);
    CACHE_MAP.put(cacheName + "_HoldTime", System.currentTimeMillis() + holdTime);//缓存失效时间
}
/**
 * 检查缓存对象是否存在,
 * 若不存在,则返回false
 * 若存在,检查其是否已过有效期,如果已经过了则删除该缓存并返回false
 * @param cacheName
 * @return
 */
public static boolean checkCacheName(String cacheName) {
    Long cacheHoldTime = (Long) CACHE_MAP.get(cacheName + "_HoldTime");
    if (cacheHoldTime == null || cacheHoldTime == 0L) {
        return false;
    }
    if (cacheHoldTime < System.currentTimeMillis()) {
        remove(cacheName);
        return false;
    }
    return true;
}
/**
 * 删除所有缓存
 */
/*public static void removeAll() {
    CACHE_MAP.clear();
}*/
/**
 * 删除某个缓存
 * @param cacheName
 */
public static void remove(String cacheName) {
    CACHE_MAP.remove(cacheName);
    CACHE_MAP.remove(cacheName + "_HoldTime");
}
/**
 * 取出一个缓存对象
 * @param cacheName
 * @return
 */
public static Object get(String cacheName) {
    if (checkCacheName(cacheName)) {
        return CACHE_MAP.get(cacheName);
    }
    return null;
}
/**
 * 获取缓存中的token,24小时更新
 * @param loginJson
 * @return
 */
public static String getCacheToken(JSONObject loginJson){
    if (get("token")==null || get("token").equals("")){
        put("token",getToken(loginJson),CACHE_HOLD_TIME_24H);
    }
    return String.valueOf(get("tokenString"));
}

还有个定时任务周期性执行,使用scheduleWithFixedDelay实现,这里传对象进去的话要声明为final

 ScheduledExecutorService service = Executors.newSingleThreadScheduledExecutor();
        Runnable runnable = new Runnable() {
            public void run() {
                try{
                    //执行内容
                }catch (Exception e){
                    e.printStackTrace();
                }
            }
        };
        service.scheduleWithFixedDelay(runnable,10,20, TimeUnit.MINUTES);
        service.execute(runnable);

参考: https://www.cnblogs.com/swordfall/p/10757499.html.
https://www.imooc.com/article/18585
https://blog.csdn.net/qb170217/article/details/81699439
https://blog.csdn.net/walle167/article/details/50957400
附一个Spring-boot的学习地址 https://github.com/ityouknow/spring-boot-examples

你可能感兴趣的:(httpclient,Java)