Find a route and directions

Learn how to find a route and directions with the route service.

Routing is the process of finding the path from an origin to a destination in a street network. You can use the route service to find routes, get driving directions, calculate drive times, and solve complicated, multiple vehicle routing problems. To create a route, you typically define a set of stops (origin and one or more destinations) and use the service to find a route with directions. You can also use a number of additional parameters such as barriers and mode of travel to refine the results.

In this tutorial, you define an origin and destination by clicking on the map. These values are used to get a route and directions from the route service. The directions are also displayed on the map.

Prerequisites

You need an ArcGIS account to access the developer dashboard and create an API key.

Steps

Create a new pen

  1. To get started, either complete the Display a map tutorial or .

Set the API key

To access location services, you need an API key or OAuth 2.0 access token.

  1. Go to your dashboard to get an API key. The API key must be scoped to access the services used in this tutorial.

  2. In CodePen, update apiKey to use your key.

                                                             
    Change line
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    <!DOCTYPE html>
    <html>
    
    <head>
      <meta charset="utf-8">
      <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
      <title>Esri Leaflet</title>
    
      <!-- Load Leaflet from CDN -->
      <link rel="stylesheet" href="https://unpkg.com/leaflet@1.7.1/dist/leaflet.css"
        integrity="sha512-xodZBNTC5n17Xt2atTPuE1HxjVMSvLVW9ocqUKLsCC5CXdbqCmblAshOMAS6/keqq/sMZMZ19scR4PsZChSR7A=="
        crossorigin=""/>
      <script src="https://unpkg.com/leaflet@1.7.1/dist/leaflet.js"
        integrity="sha512-XQoYMqMTK8LvdxXYG3nZ448hOEQiglfqkJs1NOQV44cWnUrBc8PkAOcXy20w0vlaXaVUearIOBhiXZ5V3ynxwA=="
        crossorigin=""></script>
    
      <!-- Load Esri Leaflet from CDN -->
      <script src="https://unpkg.com/esri-leaflet@3.0.0/dist/esri-leaflet.js"></script>
      <script src="https://unpkg.com/esri-leaflet-vector@3.0.0/dist/esri-leaflet-vector.js"></script>
    
      <style>
        body { margin:0; padding:0; }
        #map {
            position: absolute;
            top:0;
            bottom:0;
            right:0;
            left:0;
            font-family: Arial, Helvetica, sans-serif;
            font-size: 14px;
            color: #323232;
      </style>
    
    </head>
    
    <body>
      <div id="map"></div>
    
      <script>
        const apiKey = "YOUR_API_KEY";
        const basemapEnum = "ArcGIS:Streets";
    
        const map = L.map('map', {
          minZoom: 2
        }).setView([34.02,-118.805], 13);
    
        L.esri.Vector.vectorBasemapLayer(basemapEnum, {
          apiKey: apiKey
        }).addTo(map);
      </script>
    
    </body>
    
    </html>

Add references to ArcGIS REST JS

Import the ArcGIS REST JS library from the CDN.

                                                                                                                                                        
Add line.Add line.Add line.Add line.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8">
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Esri Leaflet</title>

  <!-- Load Leaflet from CDN -->
  <link rel="stylesheet" href="https://unpkg.com/leaflet@1.7.1/dist/leaflet.css"
    integrity="sha512-xodZBNTC5n17Xt2atTPuE1HxjVMSvLVW9ocqUKLsCC5CXdbqCmblAshOMAS6/keqq/sMZMZ19scR4PsZChSR7A=="
    crossorigin=""/>
<script src="https://unpkg.com/leaflet@1.7.1/dist/leaflet.js"
    integrity="sha512-XQoYMqMTK8LvdxXYG3nZ448hOEQiglfqkJs1NOQV44cWnUrBc8PkAOcXy20w0vlaXaVUearIOBhiXZ5V3ynxwA=="
    crossorigin=""></script>

  <!-- Load Esri Leaflet from CDN -->
  <script src="https://unpkg.com/esri-leaflet@3.0.0/dist/esri-leaflet.js"></script>
  <script src="https://unpkg.com/esri-leaflet-vector@3.0.0/dist/esri-leaflet-vector.js"></script>


  <!-- Load ArcGIS REST JS from CDN -->
  <script src="https://unpkg.com/@esri/arcgis-rest-request@3.0.0/dist/umd/request.umd.js"></script>
  <script src="https://unpkg.com/@esri/arcgis-rest-routing@3.0.0/dist/umd/routing.umd.js"></script>
  <script src="https://unpkg.com/@esri/arcgis-rest-auth@3.0.0/dist/umd/auth.umd.js"></script>


  <style>
    body { margin:0; padding:0; }
    #map {
      position: absolute;
      top:0;
      bottom:0;
      right:0;
      left:0;
      font-family: Arial, Helvetica, sans-serif;
      font-size: 14px;
      color: #323232;
    #directions {
      position: absolute;
      z-index: 1000;
      width: 30%;
      max-height: 50%;
      right: 20px;
      top: 20px;
      overflow-y: auto; /* Show a scrollbar if needed */
      background: white;
      font-family: Arial, Helvetica, Verdana;
      line-height: 1.5;
      font-size: 14px;
      padding: 10px;
  </style>

</head>

<body>

  <div id="map"></div>

  <script>
    const apiKey = "YOUR_API_KEY";
    const basemapEnum = "ArcGIS:Navigation";
    const map = L.map('map', {
      minZoom: 2
    }).setView([43.6532,-79.3832], 12); // Toronto
      apiKey: apiKey
    // Add a DOM Node to display the text routing directions
    const directions = document.createElement("div");
    directions.id = "directions";
    directions.innerHTML = "Click on the map to create a start and end for the route.";
    document.body.appendChild(directions);
    // Layer Group for start/end-points
    const startLayerGroup = L.layerGroup().addTo(map);
    const endLayerGroup = L.layerGroup().addTo(map);
    // Layer Group for route lines
    const routeLines = L.layerGroup().addTo(map);
    let currentStep = "start";
    let startCoords, endCoords;
    function updateRoute() {
      // Create the arcgis-rest-js authentication object to use later.
      const authentication = new arcgisRest.ApiKey({
        key: apiKey
      // make the API request
          stops: [startCoords, endCoords],
          endpoint: "https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World/solve",
        .then((response) => {
          // Show the result route on the map.
          // Show the result text directions on the map.
          const directionsHTML = response.directions[0].features.map((f) => f.attributes.text).join("<br/>");
          startCoords = null;
          endCoords = null;
        .catch((error) => {
          console.error(error);
          alert("There was a problem using the route service. See the console for details.");
    // When the map is clicked, get the coordinates, store the start or end
    // state, and pass them to the updateRoute function which calls the REST endpoint.
    map.on("click", (e) => {
      const coordinates = [e.latlng.lng, e.latlng.lat];
      if (currentStep === "start") {
        currentStep = "end";
      } else {
        currentStep = "start";
      if (startCoords && endCoords) {
  </script>

</body>

</html>

Add code to create a route

Add the following code to allow the user to click twice on the map and then display a route and directions:

  • Add styles for the route directions.
  • Change the basemap layer to Navigation and set the location to Toronto.
  • Create and style a div element to display directions.
  • Create a click handler to create an origin and destination.
  • Use ArcGIS REST JS to call the service to get route and directions.
  • Display the route on the map and the results in the div element.
                                                                                                                                                        
Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Change lineChange lineAdd line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.Add line.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8">
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Esri Leaflet</title>

  <!-- Load Leaflet from CDN -->
  <link rel="stylesheet" href="https://unpkg.com/leaflet@1.7.1/dist/leaflet.css"
    integrity="sha512-xodZBNTC5n17Xt2atTPuE1HxjVMSvLVW9ocqUKLsCC5CXdbqCmblAshOMAS6/keqq/sMZMZ19scR4PsZChSR7A=="
    crossorigin=""/>
<script src="https://unpkg.com/leaflet@1.7.1/dist/leaflet.js"
    integrity="sha512-XQoYMqMTK8LvdxXYG3nZ448hOEQiglfqkJs1NOQV44cWnUrBc8PkAOcXy20w0vlaXaVUearIOBhiXZ5V3ynxwA=="
    crossorigin=""></script>

  <!-- Load Esri Leaflet from CDN -->
  <script src="https://unpkg.com/esri-leaflet@3.0.0/dist/esri-leaflet.js"></script>
  <script src="https://unpkg.com/esri-leaflet-vector@3.0.0/dist/esri-leaflet-vector.js"></script>


  <!-- Load ArcGIS REST JS from CDN -->
  <script src="https://unpkg.com/@esri/arcgis-rest-request@3.0.0/dist/umd/request.umd.js"></script>
  <script src="https://unpkg.com/@esri/arcgis-rest-routing@3.0.0/dist/umd/routing.umd.js"></script>
  <script src="https://unpkg.com/@esri/arcgis-rest-auth@3.0.0/dist/umd/auth.umd.js"></script>


  <style>
    body { margin:0; padding:0; }
    #map {
      position: absolute;
      top:0;
      bottom:0;
      right:0;
      left:0;
      font-family: Arial, Helvetica, sans-serif;
      font-size: 14px;
      color: #323232;
    }
    #directions {
      position: absolute;
      z-index: 1000;
      width: 30%;
      max-height: 50%;
      right: 20px;
      top: 20px;
      overflow-y: auto; /* Show a scrollbar if needed */
      background: white;
      font-family: Arial, Helvetica, Verdana;
      line-height: 1.5;
      font-size: 14px;
      padding: 10px;
    }
  </style>

</head>

<body>

  <div id="map"></div>

  <script>

    const apiKey = "YOUR_API_KEY";

    const basemapEnum = "ArcGIS:Navigation";

    const map = L.map('map', {
      minZoom: 2

    }).setView([43.6532,-79.3832], 12); // Toronto

    L.esri.Vector.vectorBasemapLayer(basemapEnum, {
      apiKey: apiKey
    }).addTo(map);

    // Add a DOM Node to display the text routing directions
    const directions = document.createElement("div");
    directions.id = "directions";
    directions.innerHTML = "Click on the map to create a start and end for the route.";
    document.body.appendChild(directions);

    // Layer Group for start/end-points
    const startLayerGroup = L.layerGroup().addTo(map);
    const endLayerGroup = L.layerGroup().addTo(map);

    // Layer Group for route lines
    const routeLines = L.layerGroup().addTo(map);

    let currentStep = "start";
    let startCoords, endCoords;

    function updateRoute() {
      // Create the arcgis-rest-js authentication object to use later.
      const authentication = new arcgisRest.ApiKey({
        key: apiKey
      });

      // make the API request
      arcgisRest
        .solveRoute({
          stops: [startCoords, endCoords],
          endpoint: "https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World/solve",
          authentication
        })
        .then((response) => {
          // Show the result route on the map.
          routeLines.clearLayers();
          L.geoJSON(response.routes.geoJson).addTo(routeLines);

          // Show the result text directions on the map.
          const directionsHTML = response.directions[0].features.map((f) => f.attributes.text).join("<br/>");
          directions.innerHTML = directionsHTML;
          startCoords = null;
          endCoords = null;
        })
        .catch((error) => {
          console.error(error);
          alert("There was a problem using the route service. See the console for details.");
        });
    }

    // When the map is clicked, get the coordinates, store the start or end
    // state, and pass them to the updateRoute function which calls the REST endpoint.
    map.on("click", (e) => {
      const coordinates = [e.latlng.lng, e.latlng.lat];

      if (currentStep === "start") {
        startLayerGroup.clearLayers();
        endLayerGroup.clearLayers();
        routeLines.clearLayers();
        L.marker(e.latlng).addTo(startLayerGroup);
        startCoords = coordinates;
        currentStep = "end";
      } else {
        L.marker(e.latlng).addTo(endLayerGroup);
        endCoords = coordinates;
        currentStep = "start";
      }

      if (startCoords && endCoords) {
        updateRoute();
      }
    });

  </script>

</body>

</html>

Run the app

In CodePen, run your code to display the map.

When the map displays, you should be able to click on it once to create an origin point and again to create a destination point. The routing service should then display the resulting route and turn-by-turn directions.

What's next?

Learn how to use additional ArcGIS location services in these tutorials:

Your browser is no longer supported. Please upgrade your browser for the best experience. See our browser deprecation post for more details.