Geoposición y Clima#

En este ejemplo se utilizan dos APIs:

  • Geocoding API: Dado el nombre de una ciudad retorna la latitud y longitud.

  • Free Weather API: Dada una latitud y longitud retorna el estado del clima (hora loca, temperatura actual, descripción del clima, etc).

Código fuente Weather.java.

Dependencias de Maven#

%%loadFromPOM
<!-- https://mvnrepository.com/artifact/org.json/json -->
<dependency>
    <groupId>org.json</groupId>
    <artifactId>json</artifactId>
    <version>20240303</version>
</dependency>

Código de Java#

// Tomado y adaptado de: https://www.youtube.com/watch?v=WS_H44tvZMI
import org.json.JSONArray;
import org.json.JSONObject;
import org.json.JSONTokener;

import java.io.IOException;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.URI;
import java.net.URL;
import java.util.Scanner;

public class WeatherAPIData {
    public static void main(String[] args) {
        try{
            for(String city: args){
                System.out.print("City Entered: %s\n".formatted(city));

                BigDecimal[] coordenadas = getLocationData(city);
                displayWeatherData(coordenadas);
                //System.out.println("");
            }   

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

    private static BigDecimal[] getLocationData(String city){
        city = city.replaceAll(" ", "+");
        String urlString = "https://geocoding-api.open-meteo.com/v1/search?name=" +
                city + "&count=1&language=en&format=json";
        
        try{
            // 1. Fetch the API response based on API Link
            HttpURLConnection apiConnection = fetchApiResponse(urlString);

            // check for response status
            // 200 - means that the connection was a success
            if(apiConnection.getResponseCode() != 200){
                System.out.println("Error: Could not connect to API");
                return null;
            }

            // 2. Read the response and convert store String type
            URI uri = new URI(urlString);
            JSONTokener jsonResponse = new JSONTokener(uri.toURL().openStream());

            // 3. Parse the string into a JSON Object
            JSONObject resultsJsonObj = new JSONObject(jsonResponse);

            // 4. Retrieve Location Data
            JSONArray locationData = (JSONArray) resultsJsonObj.get("results");

            // Get location data
            JSONObject cityLocationData = (JSONObject) locationData.get(0);
            BigDecimal latitude = (BigDecimal) cityLocationData.get("latitude");
            BigDecimal longitude = (BigDecimal) cityLocationData.get("longitude");
            
            System.out.print("""
                - URL Geoposition: %s
                    Longitude: %.2f
                    Latitude: %.2f
                    """.formatted(urlString, longitude.doubleValue(), latitude.doubleValue()));

            BigDecimal[] coordenadas = {latitude, longitude};
            return coordenadas;

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

    private static void displayWeatherData(BigDecimal[] coordenadas ){
        try{
            BigDecimal latitude = coordenadas[0], longitude = coordenadas[1];
            // 1. Fetch the API response based on API Link
            String url = "https://api.open-meteo.com/v1/forecast?latitude="+latitude+"&longitude="+longitude+"&current=temperature_2m,wind_speed_10m&hourly=temperature_2m,relative_humidity_2m,wind_speed_10m&format=json";
            //System.out.println(" - URL Weather: "+url);

            HttpURLConnection apiConnection = fetchApiResponse(url);

            // check for response status
            // 200 - means that the connection was a success
            if(apiConnection.getResponseCode() != 200){
                System.out.println("Error: Could not connect to API");
                return;
            }

            // 2. Read the response and convert store String type
            URI uri = new URI(url);
            JSONTokener jsonResponse = new JSONTokener(uri.toURL().openStream());
            
            // 3. Parse the string into a JSON Object
            JSONObject jsonObject = new JSONObject(jsonResponse);
            JSONObject currentWeatherJson = (JSONObject) jsonObject.get("current");

            // 4. Store the data into their corresponding data type
            String time = (String) currentWeatherJson.get("time");
            //System.out.println("    Current Time: " + time);

            BigDecimal temperature = (BigDecimal) currentWeatherJson.get("temperature_2m");
            // System.out.println("    Current Temperature (C): " + temperature.doubleValue());

            // long relativeHumidity = (long) currentWeatherJson.get("relative_humidity_2m");
            // System.out.println("Relative Humidity: " + relativeHumidity);

            BigDecimal windSpeed = (BigDecimal) currentWeatherJson.get("wind_speed_10m");
            // System.out.println("    Weather Description: " + windSpeed.doubleValue()+"\n");

            System.out.print("""
                    - URL Weather: %s
                        Current Time: %s
                        Current Temperature (C): %.2f
                        Weather Description: %.2f
                    """.formatted(url, time, temperature.doubleValue(), windSpeed.doubleValue()));
        }catch(Exception e){
            e.printStackTrace();
        }
    }

    private static HttpURLConnection fetchApiResponse(String urlString){
        try{
            // attempt to create connection
            URL url = new URL(urlString);
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();

            // set request method to get
            conn.setRequestMethod("GET");

            return conn;
        }catch(IOException e){
            e.printStackTrace();
        }

        // could not make connection
        return null;
    }
}
// Probado la clase WeatherAPIData
String [] ciudades = {"Bogota", "New York", "Cali"};
new WeatherAPIData().main(ciudades);
City Entered: Bogota
- URL Geoposition: https://geocoding-api.open-meteo.com/v1/search?name=Bogota&count=1&language=en&format=json
    Longitude: -74.08
    Latitude: 4.61
- URL Weather: https://api.open-meteo.com/v1/forecast?latitude=4.60971&longitude=-74.08175&current=temperature_2m,wind_speed_10m&hourly=temperature_2m,relative_humidity_2m,wind_speed_10m&format=json
    Current Time: 2024-12-03T01:00
    Current Temperature (C): 13.80
    Weather Description: 4.30
City Entered: New York
- URL Geoposition: https://geocoding-api.open-meteo.com/v1/search?name=New+York&count=1&language=en&format=json
    Longitude: -74.01
    Latitude: 40.71
- URL Weather: https://api.open-meteo.com/v1/forecast?latitude=40.71427&longitude=-74.00597&current=temperature_2m,wind_speed_10m&hourly=temperature_2m,relative_humidity_2m,wind_speed_10m&format=json
    Current Time: 2024-12-03T01:00
    Current Temperature (C): -1.50
    Weather Description: 8.10
City Entered: Cali
- URL Geoposition: https://geocoding-api.open-meteo.com/v1/search?name=Cali&count=1&language=en&format=json
    Longitude: -76.52
    Latitude: 3.44
- URL Weather: https://api.open-meteo.com/v1/forecast?latitude=3.43722&longitude=-76.5225&current=temperature_2m,wind_speed_10m&hourly=temperature_2m,relative_humidity_2m,wind_speed_10m&format=json
    Current Time: 2024-12-03T01:00
    Current Temperature (C): 23.00
    Weather Description: 3.10

Descripción del Código#

Recursos Adicionales#