测试查询ip地理位置的api调用情况

尝试多个查询ip地理位置的api

首先看代码:

public static void main(String[] args) throws UnsupportedEncodingException {
		long l = System.currentTimeMillis();
		for (int i = 0; i < 100; i++) {
		System.out.println(getIpLocation("114.114.114.114"));
		}
		long l1 = System.currentTimeMillis();
		System.out.println("总耗时: "+(l1-l) + "ms");
	}


 public static String getIpLocation(String ip) {
		//只能支持少量低频次调用,做了限流,循环100条只有前6次成功,后面都是限流失败,4631ms
			String taobaoApi = "http://ip.taobao.com/service/getIpInfo.php?ip="+ip;
			//已经关闭
			String sinaApi = "http://int.dpool.sina.com.cn/iplookup/iplookup.php?format=js&ip="+ip;
			//需要ak参数(注册账号),有并发限制,100条6357ms,普通已认证开发者账号1天3w请求,未认证1天1k,限流1秒10次,网址 http://lbsyun.baidu.com/apiconsole/auth/privilege
			//并且返回的中文是unicode编码,很坑
			String baiduApi = "http://api.map.baidu.com/location/ip?ak=xxxxxxx&ip="+ip;
			//返回页面
			String pconlineApi = "https://whois.pconline.com.cn/?ip="+ip;
			//速度尚可 100条4521ms
			String ws126Api = "http://ip.ws.126.net/ipquery?ip="+ip;
			//速度很慢,一个月免费3w条,100条24808ms,apiKey需要注册账号
			String geoApi = "https://api.ipgeolocation.io/ipgeo?apiKey=xxxxxxx&ip="+ip;
			//速度很慢,100条79133ms
			String ip_Api = "http://ip-api.com/json/?ip="+ip;
			//一个月3w条免费, 100条耗时 37394ms
			String ipapi = "https://ipapi.co/"+ip+"/json";
			HttpResult httpResult = HttpClientUtil.get(baiduApi);
			if (HttpClientUtil.is200OK(httpResult)){
				return httpResult.getRespStr();
			}
			return "无法确定";
		}

其中尝试了好几种api,包括淘宝的,新浪的,百度的,以及国外的。(国外的返回的地址是拼音,准确的说是地址的英文)

其中大多都有并发限制和额度限制。而且返回速度有快有慢,我以100条测试,基本最快也要5秒,最慢可达1分钟。

其中有一些比较坑,比如淘宝的api,使用浏览器和postman都可以正常调用,但是使用HttpClient就返回不了数据,后面发现需要将User-Agent 改为postman或者chrome, 让淘宝api以为你是页面调用的。默认HttpClient的User-Agent是Apache-HttpClient/4.5.10 (Java/1.8.0_181)

最后附上HttpClientUtil的代码:

package com.zgd.base.spring.util.http;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import io.swagger.models.Scheme;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.*;
import org.apache.http.client.HttpClient;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.entity.UrlEncodedFormEntity;
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.client.utils.URLEncodedUtils;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.message.BasicHeader;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.springframework.http.MediaType;

import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.stream.Collectors;

/**
 * HttpClientUtil
 *
 * @author zgd
 * @date 2019/8/13 15:46
 */
@Slf4j
public class HttpClientUtil {

  private static HttpClient httpClient;

  public static HttpResult get(String url) {
    return get(url, null);
  }

  static {
    getHttpClient();
  }

  /**
   * 发起get请求
   *
   * @return java.lang.String
   * @author zgd
   * @date 2019/8/13 15:52
   */
  public static HttpResult get(String url, List<NameValuePair> params) {
    HttpGet get = null;
    try {

      URIBuilder uriBuilder = new URIBuilder(url);
      uriBuilder.setCharset(StandardCharsets.UTF_8);
      if (CollectionUtils.isNotEmpty(params)) {
        uriBuilder.setParameters(params);
      }
      get = new HttpGet(uriBuilder.build());
      log.info("请求的参数 url: {}\treq: {}", get.getURI(), params);

      HttpResponse response = httpClient.execute(get);
      String resp = EntityUtils.toString(response.getEntity(), StandardCharsets.UTF_8);
      int code = response.getStatusLine().getStatusCode();
      log.info("返回的信息 resp: {}", resp);
      return new HttpResult(code, resp);
    } catch (Exception e) {
      log.warn("请求异常 --  error!", e);
    } finally {
      if (get != null) {
        get.releaseConnection();
      }
    }
    return null;
  }

  /**
   * 发送POST请求(普通表单形式)
   *
   * @return java.lang.String
   * @author zgd
   * @date 2019/8/13 15:56
   */
  public static HttpResult postForm(String url, HashMap<String, String> form) {
    List<BasicNameValuePair> params = form.entrySet().stream().map(en -> new BasicNameValuePair(en.getKey(), en.getValue()))
            .collect(Collectors.toList());
    HttpEntity entity = new UrlEncodedFormEntity(params, StandardCharsets.UTF_8);
    return postRequest(url, MediaType.APPLICATION_FORM_URLENCODED_VALUE, entity);
  }


  /**
   * 发送POST请求(JSON形式)
   *
   * @return java.lang.String
   * @author zgd
   * @date 2019/8/13 15:56
   */
  public static HttpResult postJSON(String url, String json) {
    StringEntity entity = new StringEntity(json, StandardCharsets.UTF_8);
    return postRequest(url, MediaType.APPLICATION_JSON_VALUE, entity);
  }


  /**
   * 发送post请求
   *
   * @param url
   * @param mediaType
   * @param entity
   * @return
   */
  public static HttpResult postRequest(String url, String mediaType, HttpEntity entity) {
    log.info("[postRequest] resourceUrl: {}", url);
    HttpPost post = null;
    try {
      URIBuilder uriBuilder = new URIBuilder(url);
      post = new HttpPost(uriBuilder.build());
      post.addHeader(HttpHeaders.CONTENT_TYPE, mediaType);
      post.setEntity(entity);
      HttpResponse response = httpClient.execute(post);
      String resp = EntityUtils.toString(response.getEntity());
      int code = response.getStatusLine().getStatusCode();
      log.info("返回的信息 resp:{}", resp);
      return new HttpResult(code, resp);
    } catch (Exception e) {
      log.warn("请求异常 --  error!", e);
    } finally {
      if (post != null) {
        post.releaseConnection();
      }
    }
    return null;
  }


  public static boolean is200OK(HttpResult result) {
    return result != null && result.getCode() == HttpStatus.SC_OK;
  }


  public static String getValue(HttpResult result, String key) {
    if (is200OK(result)) {
      try {
        JSONObject jsonObject = JSON.parseObject(result.getRespStr());
        return jsonObject.getString(key);
      } catch (Exception e) {
        log.warn("解析失败 ", e);
      }
    }
    return null;
  }


  /**
   * 获取默认的httpClient
   *
   * @return
   */
  public static HttpClient getHttpClient() {
    if (httpClient == null) {
      RequestConfig requestConfig = RequestConfig.custom()
              .setConnectTimeout(3000)
              .setConnectionRequestTimeout(3000)
              .setSocketTimeout(5000).build();
      httpClient = HttpClientBuilder.create().setDefaultRequestConfig(requestConfig)
              .setMaxConnTotal(1000)
              .setMaxConnPerRoute(100)
              .setDefaultHeaders(getDefaultHeaders())
              .build();
    }
    return httpClient;
  }


  /**
   * 设置默认的请求头
   *
   * @return
   */
  public static List<Header> getDefaultHeaders() {
    List<Header> headers = new ArrayList<>();
    headers.add(new BasicHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36"));
    headers.add(new BasicHeader("Accept-Encoding", "gzip,deflate"));
    headers.add(new BasicHeader("Accept-Language", "zh-CN"));
    headers.add(new BasicHeader("Connection", "Keep-Alive"));
    headers.add(new BasicHeader("Accept", "*/*"));
    return headers;
  }


}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章