diff --git a/src/google.rs b/src/google.rs index 3fac807..b34c564 100644 --- a/src/google.rs +++ b/src/google.rs @@ -10,11 +10,16 @@ pub async fn calc_travel_path(path:&[crate::types::Coords])->anyhow::Result= 32 && *b != 127 || *b == b'\t').map(|n|char::from_u32(n as u32).unwrap()).collect::()) .header("X-Goog-FieldMask", "routes.duration,routes.polyline.encodedPolyline,routes.legs") - .send().await?; - let response = serde_json::from_str::(response.text().await?.as_str())?; - + .send().await; + let response = match response { + Ok(res) => res, + Err(e) => panic!("{:?}",e) + }; + let t = response.text().await?; + //println!("{}",t); + let response = serde_json::from_str::(t.as_str())?; Ok(response.into()) } impl From for TravelPathInfo{ @@ -53,14 +58,36 @@ struct LocIn{ longitude: f64 } fn build_route_body_pain(path:&[crate::types::Coords])->serde_json::Value{ - let inter = &path[1..path.len()-1]; + let inter = if path.len() >= 2 { + &path[1..25]//path.len()-1] + }else {[].as_slice()}; + let inter = inter.iter().map(|v|{ + serde_json::json!({ + "location": { + "latLng":{ + "latitude": v.lat, + "longitude": v.lon + } + } + }) + }).collect::>(); let val = serde_json::json!({ "origin":{ - "location": path[0], + "location":{ + "latLng":{ + "latitude": path[0].lat, + "longitude": path[0].lon, + } + }, "sideOfRoad": true }, "destination":{ - "location":path[path.len()-1] + "location":{ + "latLng":{ + "latitude":path[path.len()-1].lat, + "longitude":path[path.len()-1].lon + } + } }, "intermediates": inter, "travelMode": "DRIVE", diff --git a/src/main.rs b/src/main.rs index 42b8958..b928806 100644 --- a/src/main.rs +++ b/src/main.rs @@ -55,9 +55,17 @@ async fn transit_path(req: tide::Request)->tide::Result{ routes.append(&mut route::broome_county_routes_get().await?); let route = path_calc::calc_route(&mut routes,from,to).await?; - + + let path = route.into_iter().map(|(route,enter,exit)|{ + RetRoute{ + route_name:route.name, + route_id: route.id, + enter_stop_id:enter, + exit_stop_id:exit + } + }).collect(); let ret = TransitPathResult{ - path: route.into_iter().map(RetRoute::from).collect() + path }; let resp_body:String = serde_json::to_string(&ret)?.into(); let resp = tide::Response::builder(200) @@ -77,22 +85,16 @@ struct TransitPathQuery{ } #[derive(serde::Serialize)] struct TransitPathResult{ - path:Vec + path:Vec, } #[derive(serde::Serialize)] struct RetRoute{ route_name:String, - //enter_stop_id:u32, - //exit_stop_id:u32, + route_id: u32, + enter_stop_id:u32, + exit_stop_id:u32, //enter_stop_coords: types::Coords } -impl From for RetRoute{ - fn from(route: route::Route) -> Self { - Self{ - route_name: route.name, - } - } -} /// return the num of estimated seconds for stop ids given in query params, also need to specify /// service and route id @@ -120,7 +122,12 @@ async fn transit_estimate(req: tide::Request)->tide::Result{ let Some((to_idx,_)) = route.stops.iter().enumerate().find(|(_,stop)|stop.id == query.to) else {return Ok(tide::Response::builder(400).body("Error: invalid id").into())}; - Ok(format!("{}", path_calc::bus_travel_time(route, from_idx, to_idx).await?).into()) + let resp_body = format!("{}", path_calc::bus_travel_time(route, from_idx, to_idx).await?.num_seconds()); + let resp = tide::Response::builder(200) + .body(resp_body) + .header("Content-Type","application/json") + .build(); + Ok(resp) } #[derive(serde::Deserialize)] struct TransitEstimateQuery{ @@ -152,12 +159,18 @@ async fn bus_route_draw(req: tide::Request)->tide::Result{ }; let ret = stop::RouteDraw { color: route.color, - stops: route.stops.into_iter().map(|stop|{types::Coords{lat:stop.lat,lon:stop.lon}}).collect() + poly_line: route.poly_line + //stops: route.stops.into_iter().map(|stop|{types::Coords{lat:stop.lat,lon:stop.lon}}).collect() }; - Ok(serde_json::to_string(&ret)?.into()) + let resp_body:String = serde_json::to_string(&ret)?.into(); + let resp = tide::Response::builder(200) + .body(resp_body) + .header("Content-Type","application/json") + .build(); + Ok(resp) } -#[derive(serde::Deserialize)] +#[derive(serde::Deserialize, Debug, Clone)] struct RouteDrawQuery{ id: u32, service: String diff --git a/src/path_calc.rs b/src/path_calc.rs index c7cd85d..44c7ea2 100644 --- a/src/path_calc.rs +++ b/src/path_calc.rs @@ -22,7 +22,7 @@ fn sort_routes_by_measureu64+Clone>(measure: F, rout const BU: crate::types::Coords = crate::types::Coords{lat:42.08707019482314, lon:-75.96706048564714}; const BC_BUS_HUB: crate::types::Coords = crate::types::Coords{lat:42.10156942719183, lon:-75.91073683134701}; // return a list indicating the bus routes to take in order -pub async fn calc_route(routes:&mut [crate::route::Route], from:crate::types::Coords, to: crate::types::Coords)->anyhow::Result>{ +pub async fn calc_route(routes:&mut [crate::route::Route], from:crate::types::Coords, to: crate::types::Coords)->anyhow::Result>{ if routes.len() == 0 { return Ok(Vec::new()) } @@ -31,17 +31,21 @@ pub async fn calc_route(routes:&mut [crate::route::Route], from:crate::types::Co let measure_distance_from = walk_distance_measure(from); let measure_distance_bu = walk_distance_measure(BU); let measure_distance_bc_hub = walk_distance_measure(BC_BUS_HUB); + let tmp = measure_distance_to.clone(); let route_measure_dist_to = move |route: &crate::route::Route|{ - measure_distance_to(&route.stops.iter().min_by_key(measure_distance_to.clone()).unwrap()) + tmp(&route.stops.iter().min_by_key(tmp.clone()).unwrap()) }; + let tmp = measure_distance_from.clone(); let route_measure_dist_from = move |route: &crate::route::Route|{ - measure_distance_from(&route.stops.iter().min_by_key(measure_distance_from.clone()).unwrap()) + tmp(&route.stops.iter().min_by_key(tmp.clone()).unwrap()) }; + let tmp = measure_distance_bu.clone(); let route_measure_dist_bu = move |route: &crate::route::Route|{ - measure_distance_bu(&route.stops.iter().min_by_key(measure_distance_bu.clone()).unwrap()) + tmp.clone()(&route.stops.iter().min_by_key(tmp.clone()).unwrap()) }; + let tmp = measure_distance_bc_hub.clone(); let route_measure_dist_bc_hub = move |route: &crate::route::Route|{ - measure_distance_bc_hub(&route.stops.iter().min_by_key(measure_distance_bc_hub.clone()).unwrap()) + tmp(&route.stops.iter().min_by_key(tmp.clone()).unwrap()) }; let min_direct_route = routes.iter().min_by_key(|route|route_measure_dist_to(route)+route_measure_dist_from(route)).unwrap(); @@ -56,7 +60,21 @@ pub async fn calc_route(routes:&mut [crate::route::Route], from:crate::types::Co let min_to_bc_hub = crate::route::Route::default(); let min_from_bc_hub = crate::route::Route::default(); let bc_route_cost = u64::MAX; - Ok(select_min(vec![(direct_route_cost,vec![min_direct_route.clone()]), (bu_route_cost,vec![min_to_bu_route.clone(),min_from_bu_route.clone()]), (bc_route_cost, vec![min_to_bc_hub.clone(), min_from_bc_hub.clone()])])) + + let min = *[direct_route_cost,bu_route_cost,bc_route_cost].iter().min().unwrap(); + if min == direct_route_cost{ + Ok(vec![(min_direct_route.clone(), min_direct_route.stops.iter().min_by_key(measure_distance_from).unwrap().id, min_direct_route.stops.iter().min_by_key(measure_distance_to).unwrap().id)]) + } + else if min == bu_route_cost{ + Ok(vec![(min_to_bu_route.clone(), min_to_bu_route.stops.iter().min_by_key(measure_distance_from).unwrap().id, min_to_bu_route.stops.iter().min_by_key(measure_distance_bu.clone()).unwrap().id),(min_from_bu_route.clone(), min_from_bu_route.stops.iter().min_by_key(measure_distance_bu).unwrap().id, min_from_bu_route.stops.iter().min_by_key(measure_distance_to).unwrap().id)]) + + } + else { + Ok(vec![(min_to_bc_hub.clone(), min_to_bc_hub.stops.iter().min_by_key(measure_distance_from).unwrap().id, min_to_bc_hub.stops.iter().min_by_key(measure_distance_bc_hub.clone()).unwrap().id),(min_from_bc_hub.clone(), min_from_bc_hub.stops.iter().min_by_key(measure_distance_bc_hub).unwrap().id, min_from_bc_hub.stops.iter().min_by_key(measure_distance_to).unwrap().id)]) + + } + //let min = select_min(vec![(direct_route_cost,vec![min_direct_route.clone()]), (bu_route_cost,vec![min_to_bu_route.clone(),min_from_bu_route.clone()]), (bc_route_cost, vec![min_to_bc_hub.clone(), min_from_bc_hub.clone()])]); + } fn walk_distance_measure(pos: crate::types::Coords)->impl Fn(&&crate::stop::Stop)->u64+Clone{ @@ -65,8 +83,3 @@ fn walk_distance_measure(pos: crate::types::Coords)->impl Fn(&&crate::stop::Stop (((stop.lat-pos.lat).powi(2) + (stop.lon - pos.lon).powi(2)).powf(0.5)*1_000_000.0) as u64 } } - -fn select_min(dist_route_pairs:Vec<(u64,Vec)>)->Vec{ - let (_, ret) = dist_route_pairs.into_iter().min_by_key(|(dist,_)|dist.clone()).unwrap(); - ret -} diff --git a/src/route.rs b/src/route.rs index fa2da87..cfc0af2 100644 --- a/src/route.rs +++ b/src/route.rs @@ -1,5 +1,5 @@ -#[derive(Hash, Clone, Default)] +#[derive(Hash, Clone, Default, Debug)] pub struct Route { pub id:u32, pub name: String, diff --git a/src/stop.rs b/src/stop.rs index 14cbd6e..b586a9d 100644 --- a/src/stop.rs +++ b/src/stop.rs @@ -106,6 +106,6 @@ fn enc_float(num:f64)->String{ #[derive(serde::Serialize)] pub struct RouteDraw{ pub color:String, - pub stops:Vec + pub poly_line:String }