Interactive Maps with AWS Location Service (Part 1)
2020’s Re:Invent saw AWS announce new service which provides interactive maps in the form of the AWS Location Service. AWS doesn’t have large range of services focused on frontend applications so I had to give it a try to see how it works compared to some of the existing services.
If you have ever needed a mapping solution for your application you will find that there are many different options. Some of the more popular options have mature, fully featured API and libraries like MapBox, Bing, and the comprehensive GoogleMaps API. Amazon’s initial offering is far from these existing fully featured APIs but it does include the basics: geo-coding, reverse geo-coding, map drawing, and an interesting geo-fencing and tracker solution that utilises AWS EventBridge.
Over the next couple of posts I will run through each of the Location Service features with an example implementation, finishing with some views on how it measures up against some of the other mapping services. To start with its worth stating that you will need some additional AWS services setup to gain the correct access level to the service from the browser, this includes IAM roles and a service to provide temporary AWS credentials for your application. Like with many AWS solutions you have a few different options to implement this, for example AWS Amplify or AWS Cognito are two possible routes. To keep things simple I’ve used a basic Cognito solution for these examples but if you are looking for a guide using Amplify then this AWS tutorial is very handy: Accessing Amazon Location Service.
The completed application that uses all of the Location Service’s new tools is split over two posts (Part 1 & 2). This post will focus on location lookup, geo-coding, and displaying map tiles; Part 2 will look at what we can do when we integrate the Location service with other AWS services. At the finish we should end up with an application like this:
For the frontend application Vue.js is used to build the example, however all the Location Service code can be dropped into whatever framework you like. To achieve the complete functionality a few other AWS services are required, mostly to provide API access to the Location Service from a user’s device, these are not required to use the Location Service but help paint a better picture of how it works. In each stage I will cover what the additional service does and how it can be setup, let’s get started!
To make calls to the Location Service APIs directly from the browser, we need some temporary AWS credentials. Credentials can be fetched from a Cognito identity provider pool and returned to browser. Typically you can create rules for the provider that cover two high level roles: authenticated using a provider (email/password, Google, etc) or unauthenticated (anonymous user). In this example we will be using an unauthenticated role to fetch some credentials for access (in a production app you might want to only give access to authenticated users).
To set this up we need to create a new identity pool, this can be done by navigating to Cognito service in your AWS account and follow the “create new identity pool” steps making sure to check the “Enable access to unauthenticated identities” option. After you have run through the quick start wizard steps you should have a new identity pool with the following default IAM role for unauthenticated users:
This role only has basic actions added to it so that the client can talk to Cognito, it will be expanded later to include access to the Location service resources.
We will need some application code code to talk to the Cognito identity provider:
You can find the Identity pool ID and region in the new pool that was just setup, click into the “identity browser” menu item and copy the ID from the list.
Next step is to get started with the Location Service features. First one to implement is a basic text search for addresses. This is supported by the Location Service’s Places API. Setting this up is really simple just navigate to the AWS Location Service — “place indexes” and create a new index.
There are a few options here mainly for working with Amazon’s different data providers, for this example we will keep to the defaults and use the Esri data provider. After creating the new place index, keep a note of the name of the index, you will need to provide this in the application code.
Before we can make search requests to the place index we need to allow access from the browser by updating the Cognito IAM role with some extra permissions:
Once the IAM role is updated, we can add the text based places search code to the application:
There is a good bit of data that is returned from the places search request, more details on the response data can be found in the AWS API Docs. For this example we just want the place data so we use a result to show on the application map. After making the request for places, you will want to show the result list to the user so they can pick the nearest place or make other search. For example of this checkout the Part 1 finished example application repo.
Now that the application can fetch some location information from the places API, it will be great to display a selected location on a map in the browser. To do this we will need to add a map from the Location service and a library to help render the map UI. Like the places that were setup previously, to create a new map open up the AWS Location Service console and run through the new map wizard. after creating a new map (for this example the Esri light map was selected) take note of the map name. Like with the places API we need to reference the new map name in an additional statement in the Cognito IAM role:
With the permissions in place we can now start requesting some map tiles to display in the app. At present Amazon doesn’t have a library for handling the map tile fetch and render, so for this example we will use the popular MapBox library. What we need to do is to modify the remote service which the library will fetch map data from to the Amazon Location Service. This can be easily done by extending a MapBox map instance with a custom map tile request transform:
Adding this functionality to the application will allow Mapbox to centre our map over the provided geo points.
This finishes off the first part of the application where the frontend map can search locations, and use a selected location to centre a map, the complete code is up on Github: https://github.com/tomwilderspin/aws-locations-poc. In Part 2 we will expand on this application adding in geo-fences, trackers, and using them to trigger real time notifications.
If you have any questions on the Locations Service or the example application, drop a comment below.