1. введение
В этой статье мы рассмотрим, как получить данные о географическом местоположении с IP-адреса с помощью Java API MaxMind GeoIP2 с бесплатной базой данных GeoLite2.
Мы также увидим это в действии, используя простое веб-демонстрационное приложение Spring MVC.
2. Начало работы
Для начала вам нужно загрузить API GeoIP2 и базу данных GeoLite2 из MaxMind.
2.1. Зависимость от Maven
Чтобы включить API MaxMind GeoIP2 в свой проект Maven, добавьте следующее в pom.xml файл:
com.maxmind.geoip2 geoip2 2.8.0
Чтобы получить последнюю версию API, вы можете найти ее на Maven Central .
2.2. Загрузка базы данных
Далее вам нужно будет загрузить базу данных GeoLite2 . Для этого урока мы используем двоичную сжатую версию базы данных городов GeoLite2.
После распаковки архива у вас будет файл с именем GeoLite2-City.mmdb . Это база данных сопоставлений IP-адресов с местоположением в собственном двоичном формате MaxMind.
3. Использование Java API GeoIP2
Давайте используем Java API GeoIP2 для извлечения данных о местоположении для данного IP-адреса из базы данных. Во-первых, давайте создадим Средство чтения базы данных для запроса базы данных:
File database = new File(dbLocation); DatabaseReader dbReader = new DatabaseReader.Builder(database).build();
Затем давайте используем метод city() для получения данных о городе для IP-адреса:
CityResponse response = dbReader.city(ipAddress);
Объект City Response содержит несколько элементов информации, отличных от просто названия города. Вот пример теста JUnit, показывающий, как открыть базу данных, получить информацию о городе для IP-адреса и извлечь эту информацию из CityResponse :
@Test public void givenIP_whenFetchingCity_thenReturnsCityData() throws IOException, GeoIp2Exception { String ip = "your-ip-address"; String dbLocation = "your-path-to-mmdb"; File database = new File(dbLocation); DatabaseReader dbReader = new DatabaseReader.Builder(database) .build(); InetAddress ipAddress = InetAddress.getByName(ip); CityResponse response = dbReader.city(ipAddress); String countryName = response.getCountry().getName(); String cityName = response.getCity().getName(); String postal = response.getPostal().getCode(); String state = response.getLeastSpecificSubdivision().getName(); }
4. Использование GeoIP в веб-приложении
Давайте рассмотрим пример веб-приложения, которое извлекает данные о геолокации с общедоступного IP-адреса пользователя и отображает местоположение на карте.
Мы начнем с базового приложения Spring Web MVC . Затем мы напишем Контроллер , который принимает IP-адрес в запросе POST и возвращает ответ JSON, содержащий город, широту и долготу, выведенные из API GeoIP2.
Наконец, мы напишем некоторые HTML и JavaScript, которые загрузят общедоступный IP-адрес пользователя в форму , отправим запрос Ajax на наш Контроллер и отобразим результат в Картах Google.
4.1. Класс Сущности Ответа
Давайте начнем с определения класса, который будет содержать ответ о геолокации:
public class GeoIP { private String ipAddress; private String city; private String latitude; private String longitude; // constructors, getters and setters... }
4.2. Класс Обслуживания
Теперь давайте напишем класс сервиса, который извлекает данные о геолокации с помощью Java API GeoIP2 и базы данных GeoLite2:
public class RawDBDemoGeoIPLocationService { private DatabaseReader dbReader; public RawDBDemoGeoIPLocationService() throws IOException { File database = new File("your-mmdb-location"); dbReader = new DatabaseReader.Builder(database).build(); } public GeoIP getLocation(String ip) throws IOException, GeoIp2Exception { InetAddress ipAddress = InetAddress.getByName(ip); CityResponse response = dbReader.city(ipAddress); String cityName = response.getCity().getName(); String latitude = response.getLocation().getLatitude().toString(); String longitude = response.getLocation().getLongitude().toString(); return new GeoIP(ip, cityName, latitude, longitude); } }
4.3. Пружинный Контроллер
Давайте взглянем на Контроллер для Spring MVC, который отправляет параметр запроса “ip-адрес” в наш класс обслуживания, чтобы получить данные ответа о геолокации:
@RestController public class GeoIPTestController { private RawDBDemoGeoIPLocationService locationService; public GeoIPTestController() throws IOException { locationService = new RawDBDemoGeoIPLocationService(); } @PostMapping("/GeoIPTest") public GeoIP getLocation( @RequestParam(value="ipAddress", required=true) String ipAddress ) throws Exception { GeoIPLocationServicelocationService = new RawDBDemoGeoIPLocationService(); return locationService.getLocation(ipAddress); } }
4.4. HTML-форма
Давайте добавим интерфейсный код для вызова нашего контроллера Spring , , начиная с HTML-формы, содержащей IP-адрес:
...
4.5. Загрузка Общедоступного IP-адреса на Клиент
Теперь давайте предварительно заполним текстовое поле “ip-адрес” общедоступным IP-адресом пользователя, используя jQuery и ipify.org JavaScript API:
4.6. Отправка запроса на публикацию Ajax
Когда форма будет отправлена, мы отправим запрос Ajax POST на Spring Контроллер для получения ответа JSON с данными геолокации:
$( "#ipForm" ).submit(function( event ) { event.preventDefault(); $.ajax({ url: "GeoIPTest", type: "POST", contentType: "application/x-www-form-urlencoded; charset=UTF-8", data: $.param( {ipAddress : $("#ip").val()} ), complete: function(data) {}, success: function(data) { $("#status").html(JSON.stringify(data)); if (data.ipAddress !=null) { showLocationOnMap(data); } }, error: function(err) { $("#status").html("Error:"+JSON.stringify(data)); }, }); });
4.7. Пример ответа JSON
Ответ JSON от нашего Spring Контроллера будет иметь следующий формат:
{ "ipAddress":"your-ip-address", "city":"your-city", "latitude":"your-latitude", "longitude":"your-longitude" }
4.8. Отображение местоположения на Картах Google
Чтобы отобразить местоположение на Картах Google, вам необходимо включить API Google Maps в свой HTML-код:
Вы можете получить ключ API для карт Google с помощью консоли разработчика Google.
Вам также нужно будет определить HTML тег, содержащий изображение карты:
Вы можете использовать следующую функцию JavaScript для отображения координат на Картах Google:
function showLocationOnMap (location) { var map; map = new google.maps.Map(document.getElementById('map'), { center: { lat: Number(location.latitude), lng: Number(location.longitude)}, zoom: 15 }); var marker = new google.maps.Marker({ position: { lat: Number(location.latitude), lng: Number(location.longitude)}, map: map, title: "Public IP:"+location.ipAddress +" @ "+location.city }); }
После запуска веб-приложения откройте URL-адрес страницы карты:
http://localhost:8080/spring-mvc-xml/GeoIpTest.jsp
Вы увидите текущий общедоступный IP-адрес для вашего подключения, загруженный в текстовое поле:
Обратите внимание, что и GeoIP2, и ipify поддерживают адреса IPv4, а также адреса IPv6.
Когда вы отправите форму, вы увидите текст ответа JSON, включая город, широту и долготу, соответствующие вашему общедоступному IP-адресу, а ниже вы увидите карту Google, указывающую на ваше местоположение:
5. Заключение
В этом уроке мы рассмотрели использование Java API MaxMind GeoIP2 и бесплатной базы данных городов MaxMind GeoLite2 с помощью теста JUnit.
Затем мы создали Spring MVC Контроллер и сервис для получения данных геолокации (город, широта, долгота) с IP-адреса.
Наконец, мы создали интерфейс HTML/JavaScript, чтобы продемонстрировать, как эту функцию можно использовать для отображения местоположения пользователя на Картах Google.
Этот продукт включает в себя данные GeoLite2, созданные MaxMind, доступные по адресу http://www.maxmind.com .
Код для этого руководства можно найти на сайте Github .