GoogleMap API ジオコーダーを Java で使う

Javascript からの Geocorder の利用が、1回で連続して変換できるのが 10件 に制限されているので、大量データの変換に不向きなので、調べて実装しました。



package mapaddress.dbupdate;

import java.util.*;
import java.io.*;

import com.google.maps.GeoApiContext;
import com.google.maps.*;
import com.google.maps.model.GeocodingResult;
import com.google.maps.model.LatLng;
import java.net.InetSocketAddress;
import java.net.Proxy;
import java.net.SocketAddress;
import org.apache.ibatis.session.SqlSession;

//import com.google.maps.GeoApiContextBuilder;
/**
 * GoogleMap API ジオコーダー用クラス
 */
public class Geocorder {

  /**
   * プロキシ設定
   */
  private final String PROXY_HOST = "?????????";
  private final int PROXY_PORT = 0;

  private final String API_KEY = "???????????????????????????????";

  private GeoApiContext context;

  private String addr;
  private double lat;
  private double lon;
  private String zip = "";

  /**
   * デフォルトコンストラクタ
   */
  public Geocorder() {
    context = new GeoApiContext.Builder()
            .apiKey(API_KEY)
            .build();
  }

  /**
   * APIキー指定コンストラクタ
   */
  public Geocorder(String apikey) {
    context = new GeoApiContext.Builder()
            .apiKey(apikey)
            .build();
  }

  /**
   * プロキシ用コンストラクタ
   *
   * @param isUseProxy
   */
  public Geocorder(boolean isUseProxy) {

    if (isUseProxy) {
      SocketAddress addr = new InetSocketAddress(this.PROXY_HOST, this.PROXY_PORT);
      Proxy proxy = new Proxy(Proxy.Type.HTTP, addr);
      context = new GeoApiContext.Builder()
              .apiKey(API_KEY)
              .proxy(proxy)
              .build();
    }
    else {
      context = new GeoApiContext.Builder()
              .apiKey("????????????????????????????????????????")
              .build();
    }
  }

  /**
   * @return the addr
   */
  public String getAddr() {
    return addr;
  }

  /**
   * @param addr the addr to set
   */
  public void setAddr(String addr) {
    this.addr = addr;
  }

  /**
   * @return the lat
   */
  public double getLat() {
    return lat;
  }

  /**
   * @param lat the lat to set
   */
  public void setLat(double lat) {
    this.lat = lat;
  }

  /**
   * @return the lon
   */
  public double getLon() {
    return lon;
  }

  /**
   * @param lon the lon to set
   */
  public void setLon(double lon) {
    this.lon = lon;
  }

  /**
   * @return the zip
   */
  public String getZip() {
    return zip;
  }

  /**
   * @param zip the zip to set
   */
  public void setZip(String zip) {
    this.zip = zip;
  }

  /**
   * 正ジオコーダーの実行
   */
  public void execGeoCorder() {

    try {
      GeocodingResult results[] = this.getResults(this.addr);
      //LatLng latLng = results[0].geometry.location; // とりあえず一番上のデータを使う

      if (results != null && results.length > 0) {
        //if (results.length > 0) {
        LatLng latLng = results[0].geometry.location; // とりあえず一番上のデータを使う
        System.out.println("緯度 : " + latLng.lat);
        System.out.println("経度 : " + latLng.lng);
        int len = results[0].addressComponents.length;
        String zip = results[0].addressComponents[len - 1].longName;
        System.out.println("ZIP : " + zip);

        this.lat = latLng.lat;
        this.lon = latLng.lng;
        if (zip != null && !zip.equals("")) {
          this.zip = zip;
        }

      }

    }
    catch (Exception e) {
      e.printStackTrace();
    }

  }

  /**
   * 正ジオコーダー応答取得
   *
   * @param address
   * @return
   * @throws InterruptedException
   * @throws IOException
   */
  public GeocodingResult[] getResults(String address) throws InterruptedException, IOException {

    GeocodingApiRequest req = GeocodingApi.newRequest(context)
            .address(address)
            // .components(ComponentFilter.country("JP"))
            .language("ja");

    try {
      GeocodingResult[] results = req.await();
      if (results == null || results.length == 0) {
        // ZERO_RESULTSはresults.length==0の空配列がsuccessful扱いで返ってくる
        System.out.println("zero results.");
      }
      //results[0].geometry;

      return results;

    }
    catch (Exception e) {
      System.out.println("error.");
      System.out.println(e);
      return null;
    }
  }

  /**
   * 逆ジオコーダーの実行
   */
  public void execRVGeoCorder(String lat_lon) {
    
      try {
      GeocodingResult results[] = this.getRVResults(lat_lon);
      //LatLng latLng = results[0].geometry.location; // とりあえず一番上のデータを使う

      if (results != null && results.length > 0) {
        
        int len = results[0].addressComponents.length;
        String zip = results[0].addressComponents[len - 1].longName;
        System.out.println("ZIP : " + zip);
        this.addr = results[0].formattedAddress.replaceAll("日本、", "");
        System.out.println("ADDR : " + this.addr);
        if (zip != null && !zip.equals("")) {
          this.zip = zip;
        }

      }

    }
    catch (Exception e) {
      e.printStackTrace();
    }


  }

  public GeocodingResult[] getRVResults(String lat_lon) throws InterruptedException, IOException {
    
    

    GeocodingApiRequest req = GeocodingApi.newRequest(context)
            .address(lat_lon)
            // .components(ComponentFilter.country("JP"))
            .language("ja");

    try {
      GeocodingResult[] results = req.await();
      if (results == null || results.length == 0) {
        // ZERO_RESULTSはresults.length==0の空配列がsuccessful扱いで返ってくる
        System.out.println("zero results.");
      }
      //results[0].geometry;

      return results;

    }
    catch (Exception e) {
      System.out.println("error.");
      System.out.println(e);
      return null;
    }
  }

  public static void main(String[] args) {
    
    Geocorder G = new Geocorder(false);  
    G.execRVGeoCorder("31.62457 131.8521498");
    System.out.println(G.addr);
    


  }

}

ここで教えていただきました : http://developers.goalist.co.jp/entry/2017/10/16/150000

逆ジオコーダーも必要あるので、試したところ、Javascript の住所指定と同じく、緯度 + ” ” + 経度 を住所として渡せば出来ました。