use openmeteo_rs::{Client, Result};
use wiremock::matchers::{method, path, query_param};
use wiremock::{Mock, MockServer, ResponseTemplate};
const GEOCODING_FIXTURE: &str = include_str!("fixtures/geocoding_zurich.json");
const EMPTY_GEOCODING_FIXTURE: &str = include_str!("fixtures/geocoding_empty_results.json");
#[tokio::test]
async fn geocoding_request_is_sent_and_decoded_against_fixture() -> Result<()> {
let server = MockServer::start().await;
Mock::given(method("GET"))
.and(path("/v1/search"))
.and(query_param("name", "Zurich"))
.and(query_param("count", "2"))
.and(query_param("language", "en"))
.and(query_param("country_code", "CH"))
.respond_with(
ResponseTemplate::new(200).set_body_raw(GEOCODING_FIXTURE, "application/json"),
)
.mount(&server)
.await;
let client = Client::builder()
.geocoding_base_url(server.uri())?
.build()?;
let locations = client
.geocode("Zurich")
.count(2)
.language("en")
.country_code("CH")
.send()
.await?;
assert_eq!(locations.len(), 2);
assert_eq!(locations[0].id, 2657896);
assert_eq!(locations[0].name, "Zurich");
assert_eq!(locations[0].country_code.as_deref(), Some("CH"));
assert_eq!(locations[0].timezone.as_deref(), Some("Europe/Zurich"));
assert_eq!(locations[0].postcodes.as_ref().unwrap()[0], "8000");
assert_eq!(locations[1].country.as_deref(), Some("The Netherlands"));
Ok(())
}
#[tokio::test]
async fn geocoding_empty_results_decode_to_empty_vec() -> Result<()> {
let server = MockServer::start().await;
Mock::given(method("GET"))
.and(path("/v1/search"))
.and(query_param("name", "not-a-real-place"))
.respond_with(
ResponseTemplate::new(200).set_body_raw(EMPTY_GEOCODING_FIXTURE, "application/json"),
)
.mount(&server)
.await;
let client = Client::builder()
.geocoding_base_url(server.uri())?
.build()?;
let locations = client.geocode("not-a-real-place").send().await?;
assert!(locations.is_empty());
Ok(())
}