-
Notifications
You must be signed in to change notification settings - Fork 48
handle Graphhopper requests #514
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
…epts GraphHopper POST requests
Thanks for the PR @karussell! Will try to get this reviewed in greater detail within the next day or so!
Haha no worries :)
Correct; no complaints with extra commits from us!
Yeaaaaaaahhhhh.... there were some complications we ran into with trying to test the full stack, JNA bits and all, from a "regular" JUnit test. These questions were never fully resolved. So, for Android, we have to run a lot of tests that should theoretically be boring JUnit tests as "connected Android checks" on an emulator / device.
I'll have to give that a bit of thought as a review this.
Do you have a specific example? The methods I'm aware of are query string and header-based auth, both of which are supported. JWT is also starting to be used (Apple Maps for JavaScript is the only geospatial related one I can think of), but I think the current set of interfaces still work for that.
No worries; we can handle the other platforms :) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Some initial comments. Overall looking simple enough. Will let @ianthetechie critique the rust stuff.
@@ -248,7 +248,8 @@ class ValhallaCoreTest { | |||
} | |||
val core = | |||
FerrostarCore( | |||
valhallaEndpointURL = URL(valhallaEndpointUrl), | |||
routingEndpointURL = URL(valhallaEndpointUrl), | |||
routingEngine = "valhalla", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should probably consider a strategy where this is a sealed class with options. E.g.
sealed class RoutingEngine {
data class Valhalla(val endpoint: String) : RoutingEngine
data class GraphHopper(val endpoint: String): RoutingEngine
// TODO: we might be able to move the CustomRouteProvider in here somehow as well.
}
For swift this would look something like:
enum RoutingEngine {
case valhalla(String)
case graphHopper(String)
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, agreed. I can take another pass at that. This is one of those weird Kotlin things ;)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not sure if I fully understand this but I have added this approach in the last commit. Please see the change and let me know if this is what you meant. (I also included the routing profile as it is dependent on the routing engine)
@@ -157,8 +158,12 @@ class FerrostarCore( | |||
options: Map<String, Any> = emptyMap(), | |||
) : this( | |||
RouteProvider.RouteAdapter( | |||
RouteAdapter.newValhallaHttp( | |||
valhallaEndpointURL.toString(), profile, jsonAdapter.toJson(options))), | |||
if (routingEngine == "graphhopper") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Accepting the sealed class above, this would become. when
statement.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sorry this took a bit for me to get around to! This is really great! I've just done some cleanup + added docs. If you could review the questions (esp verifying the JSON output :D), we can get this merged pretty quickly + I'll handle the iOS side.
// SimulatedLocationProvider().apply { | ||
// warpFactor = 2u | ||
// lastLocation = | ||
// UserLocation(GeographicCoordinate(51.049315, 13.73552), 1.0, null, Instant.now(), null) | ||
// } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not sure why this was commented out...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please have a look. I made it configurable with a boolean now.
...shots/ferrostar__routing_adapters__graphhopper__tests__request_body_with_custom_profile.snap
Show resolved
Hide resolved
locale: L, | ||
voice_units: VoiceUnits, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
With Valhalla, we leave locale and voice units unspecified, but you had them hard-coded, which makes me wonder if these are required and/or strongly encouraged for every request. I've made some changes to the interface assuming the answer is "yes" but please let me know your thoughts. For Valhalla, we currently just handle this with extra JSON options, but I'd like to move toward making the options easier to use with strong types, so here's a first pass at this.
cc @Archdoog in case you have any comments.
Thanks for the review! (Sorry for the delay :) )
They are not required but I thought I make them explicit as they are often the first things users want to change beside profile and points. (Let's remove them to make it more similar to valhalla.)
Ah, ok. Thought only query string auth was supported. |
@ianthetechie @Archdoog anything missing that I can do? I can e.g. fix the merge conflicts but would prefer to do it close to the merge :) |
Please review carefully as I'm not a native speaker of Rust or Kotlin :)
My initial approach was to convert the "native" GraphHopper response inside ferrostar, but due to some problems and because it makes other situations also simpler I've created a server-side solution, where the endpoint accepts a "native" GraphHopper (POST) request and returns the OSRM-alike response, which is already supported from ferrostar and e.g. maxspeed annotations worked out of the box. (I kept the early commits mainly for myself and I think this is fine as you are squashing commits anyway?)
Currently there are no tests as I wasn't sure what to test and also there is this notice "move out of Android Tests ASAP". Is this still valid? I could test e.g. that the request is properly formed - just let me know if I should e.g. copy ValhallaCoreTest.kt or if I should do something else.
And should we create a more generic route adapter creation like this?
RouteAdapter.newHttp(routingEngine, routingEndpointURL.toString(), profile, jsonAdapter.toJson(options))
Otherwise we have to duplicate the cases of the different routing engines at a higher level in all different environment. One tricky part for other engines could be the authentication as it is often not done via a simple API key in the URL (like used from the Stadia Maps and the Graphhopper API).
Let me know which one you prefer and I could try to make the web/wasm environment working.
Currently there is also no support for iOS and react-native, but it should be only a few lines as you can see in the Kotlin code. Unfortunately, I probably won't be of much help here.