add point finder from args
This commit is contained in:
+49
-1
@@ -1,6 +1,6 @@
|
||||
use std::fmt::{Debug, Display};
|
||||
|
||||
use anyhow::Result;
|
||||
use anyhow::{Context, Result};
|
||||
use chrono::{DateTime, Local, TimeZone, Utc};
|
||||
use serde::{de, Deserialize, Deserializer};
|
||||
|
||||
@@ -72,3 +72,51 @@ pub fn format_departures(response: Response) -> String {
|
||||
let departures: Vec<String> = response.departures.iter().map(|d| d.to_string()).collect();
|
||||
departures.join("\n\n")
|
||||
}
|
||||
|
||||
#[derive(Deserialize, Debug)]
|
||||
#[serde(rename_all = "PascalCase")]
|
||||
pub struct PointFinderResponse {
|
||||
#[serde(deserialize_with = "deserialize_points", rename = "Points")]
|
||||
pub point: Point,
|
||||
}
|
||||
|
||||
#[derive(Deserialize, Debug)]
|
||||
#[serde(rename_all = "PascalCase")]
|
||||
pub struct Point {
|
||||
pub stopid: String,
|
||||
pub name: String,
|
||||
pub area: Option<String>,
|
||||
}
|
||||
|
||||
impl From<(&str, &str, Option<&str>)> for Point {
|
||||
fn from(value: (&str, &str, Option<&str>)) -> Self {
|
||||
Self {
|
||||
stopid: value.0.into(),
|
||||
name: value.1.into(),
|
||||
area: value.2.map(|s| s.into()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Deserialize a Point Response in the form of
|
||||
/// '\"33000742|||Helmholtzstraße|5655904|4621157|0||\"'
|
||||
fn extract_data_from_response(line: &str) -> Result<Point> {
|
||||
let mut iter = line.trim_start_matches("\\\"").split_terminator('|');
|
||||
|
||||
let stopid = iter.next().context("getting stopid from line")?;
|
||||
let area = iter.nth(1).context("getting area from line").ok();
|
||||
let name = iter.next().context("getting stop name from line")?;
|
||||
Ok((stopid, name, area).into())
|
||||
}
|
||||
|
||||
fn deserialize_points<'de, D>(deserializer: D) -> Result<Point, D::Error>
|
||||
where
|
||||
D: Deserializer<'de>,
|
||||
{
|
||||
let stops: Vec<String> = Vec::deserialize(deserializer)?;
|
||||
let first_stop_line = stops
|
||||
.first()
|
||||
.ok_or_else(|| de::Error::custom("could not get first stop"))?;
|
||||
let point = extract_data_from_response(first_stop_line).map_err(de::Error::custom)?;
|
||||
Ok(point)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user