Chapter 28. Foundational Network Programmability Concepts

This chapter covers the following subjects:

Command-Line Interface (CLI): This section provides an overview of the pros and cons of managing devices with the traditional command-line interface approach.

Application Programming Interface (API): This section describes what APIs are, the different types of APIs, and how they are used.

Data Models and Supporting Protocols: This section describes some of the most common data models and associated tools

Cisco DevNet: This section provides a high-level overview of the various Cisco DevNet components and learning labs.

GitHub: This section illustrates different use cases for version control and the power of community code sharing.

Basic Python Components and Scripts: This section illustrates the components of Python scripts and how to interpret them.

This chapter discusses some of the ways that networks have been traditionally managed. It also focuses on some of the most common network programmability concepts and programmatic methods of management.

“Do I Know This Already?” Quiz

The “Do I Know This Already?” quiz allows you to assess whether you should read the entire chapter. If you miss no more than one of these self-assessment questions, you might want to move ahead to the “Exam Preparation Tasks” section. Table 28-1 lists the major headings in this chapter and the “Do I Know This Already?” quiz questions covering the material in those headings so you can assess your knowledge of these specific areas. The answers to the “Do I Know This Already?” quiz appear in Appendix A, “Answers to the ‘Do I Know This Already?’ Quiz Questions.”

Table 28-1 Do I Know This Already?” Foundation Topics Section-to-Question Mapping

Foundation Topics Section

Questions

Command-Line Interface (CLI)

13

Application Programming Interface (API)

2–6, 10

Cisco DevNet

11

GitHub

12

Data Models and Supporting Protocols

14

Basic Python Components and Scripts

1, 7–9

1. True or false: Python is considered one of the most difficult programming languages to learn and adopt.

  1. True

  2. False

2. To authenticate with Cisco’s DNA Center, which type of HTTP request method must be used?

  1. PUT

  2. PATCH

  3. GET

  4. POST

  5. HEAD

3. What does CRUD stand for?

  1. CREATE, RESTORE, UPDATE, DELETE

  2. CREATE, READ, UPDATE, DELETE

  3. CREATE, RETRIEVE, UPDATE, DELETE

  4. CREATE, RECEIVE, UPLOAD, DOWNLOAD

  5. CREATE, RECEIVE, UPLOAD, DELETE

4. When using the Cisco vManage Authentication API, what is the Headers Content-Type that is used?

  1. MD5

  2. X-Auth-Token

  3. SSH

  4. x-www-form-urlencoded

  5. JSON

5. Which of the following is in JSON data format?

  1. {
      "user": "root",
      "father": "Jason",
      "mother": "Jamie",
      "friend": "Luke"
    }
  2. <users>
          <user>
            <name>root</name>
          </user>
          <user>
            <name>Jason</name>
          </user>
          <user>
            <name>Jamie</name>
          </user>
          <user>
            <name>Luke</name>
          </user>
        </users>
  3. root
    Jason
    Jamie
    Luke
  4. [users[root|Jason|Jamie|Luke]]

6. What is the HTTP status code for Unauthorized?

  1. 201

  2. 400

  3. 401

  4. 403

  5. 404

7. In Python, why would you use three quotation marks in a row? (Choose two.)

  1. To begin a multiple-line string

  2. To start a function

  3. To represent a logical OR

  4. To end a multiple-line string

  5. To call a reusable line of code

8. Which of the following is a Python dictionary?

  1. dnac = {
        "host": "sandboxdnac.cisco.com",
        "port": 443,
        "username": "devnetuser",
        "password": "Cisco123!"
    }
  2. [users[root|Jason|Jamie|Luke]]
  3. def dnac_login(host, username, password):
        url = "https://{}/api/system/v1/auth/token".
              format(host)
    
        response = requests.request("POST", url,
                   auth=HTTPBasicAuth(username, password),
                   headers=headers, verify=False)
        return response.json()["Token"]
  4. print(dnac_devices)

9. Which of the following are Python functions? (Choose two.)

  1. dnac = {
        "host": "sandboxdnac.cisco.com",
        "port": 443,
        "username": "devnetuser",
        "password": "Cisco123!"
    }
  2. [users[root|Jason|Jamie|Luke]]
  3. def dnac_login(host, username, password):
        url = "https://{}/api/system/v1/auth/token".
               format(host)
        response = requests.request("POST", url,
                   auth=HTTPBasicAuth(username, password),
                   headers=headers, verify=False)
        return response.json()["Token"]
  4. print(dnac_devices)

10. When using the Cisco DNA Center Token API, what authentication method is used?

  1. MD5

  2. X-Auth-Token

  3. SSH

  4. Basic authentication

  5. JSON

11. What is the DevNet Community page used for? (Choose two.)

  1. To ask questions

  2. To exchange code

  3. To access learning labs

  4. To access DevNet ambassadors and evangelists

  5. To get news on local DevNet events

12. When using GitHub, what is the purpose of a repository? (Choose three.)

  1. Provides a place to store a developer’s code

  2. Provides a place to store music and photos

  3. Gives the option to share a developer’s code with other users

  4. Provides documentation on code examples

  5. Offers a sandbox to test custom code

13. Why is using the command-line interface (CLI) to configure a large number of devices considered difficult to scale? (Choose two.)

  1. The CLI is prone to human error and misconfiguration.

  2. The CLI is quick and efficient for configuring many devices simultaneously.

  3. Telnet access to the CLI is best practice.

  4. The command line is used on a device-by-device basis.

  5. Using APIs is considered a legacy method of configuration.

14. Which of the following are part of the YANG model? (Choose two.)

  1. Type

  2. Leaf

  3. Container

  4. String

  5. Method

Answers to the “Do I Know This Already?” quiz:

1 B

2 D

3 B

4 D

5 A

6 C

7 A, D

8 A

9 C, D

10 D

11 A, D

12 A, C, D

13 A, D

14 B, C

Foundation Topics

Command-Line Interface

There are many different ways to connect to and manage a network. The most commonly used method for the past 30 years has been by using the command-line interface (CLI). However, like almost everything else, the CLI has pros and cons. Perhaps one of the most glaring and biggest flaws with using CLI to manage a network is misconfiguration. Businesses often have frequent changes in their network environments, and some of those changes can be extremely complex. When businesses have increased complexity in their networks, the cost of something failing can be very high due to the increased time it takes to troubleshoot the issues in a complex network.

Failure in a network, however, doesn’t necessarily mean software or a hardware component is to blame. A majority of network outages are caused by human beings. Many outages occur because of misconfigurations due to lack of network understanding. While not all outages or failures can be avoided, there are tools that can assist in reducing the number of outages that are caused by human error due to misconfigurations in the CLI (see Chapter 29, “Introduction to Automation Tools”). Table 28-2 shows a brief list of common pros and cons associated with using the CLI.

Table 28-2 CLI PROs and CONs

PROs

CONs

Well known and documented

Difficult to scale

Commonly used method

Large number of commands

Commands can be scripted

Must know IOS command syntax

Syntax help available on each command

Executing commands can be slow

Connection to CLI can be encrypted (using SSH)

Not intuitive

 

Can execute only one command at time

 

CLI and commands can change between software versions and platforms

 

Using the CLI can pose a security threat if using Telnet (plaintext)

Of course there are programmatic ways of accomplishing the same configurations that are possible with the CLI, as discussed in the following sections.

Application Programming Interface

Another very popular method of communicating with and configuring a network is through the use of application programming interfaces (APIs). APIs are mechanisms used to communicate with applications and other software. They are also used to communicate with various components of the network through software. It is possible to use APIs to configure or monitor specific components of a network. There are multiple different types of APIs. However, the focus of this chapter is on two of the most common APIs: the Northbound and Southbound APIs. The following sections explain the differences between the two through the lens of network automation. Figure 28-1 illustrates the basic operations of Northbound and Southbound APIs.

A diagram is shown for the Basic API Operations. The Data Plane is interlinked with Controller through Southbound API. The Controller is further linked with the Applications through the Northbound API.

Figure 28-1 Basic API Operations

Northbound API

Northbound APIs are often used to communicate from a network controller to its management software. For example, Cisco DNA Center has a software graphical user interface (GUI) that is used to manage the network controller. Typically, when a network operator logs into a controller to manage the network, the information that is being passed from the management software is leveraging a Northbound REST-based API. Best practices suggest that the traffic should be encrypted using TLS between the software and the controller. Most types of APIs have the ability to use encryption to secure the data in flight.

Note

REST APIs are covered later in this chapter.

Southbound API

If a network operator makes a change to a switch’s configuration in the management software of the controller, those changes are then pushed down to the individual devices by using a Southbound API. These devices can be routers, switches, or even wireless access points. APIs interact with the components of a network through the use of a programmatic interface.

Representational State Transfer (REST) APIs

An API that uses REST is often referred to a RESTful API. RESTful APIs use HTTP methods to gather and manipulate data. Because there is a defined structure for how HTTP works, it offers a consistent way to interact with APIs from multiple vendors. REST uses different HTTP functions to interact with the data. Table 28-3 lists some of the most common HTTP functions and their associated use cases.

Table 28-3 HTTP Functions and Use Cases

HTTP Function

Action

Use Case

GET

Requests data from a destination

Viewing a website

POST

Submits data to a specific destination

Submitting login credentials

PUT

Replaces data in a specific destination

Updating an NTP server

PATCH

Appends data to a specific destination

Adding an NTP server

DELETE

Removes data from a specific destination

Removing an NTP server

HTTP functions are similar to the functions that most applications or databases use to store or alter data—whether the data is stored in a database or within the application. These functions are called “CRUD” functions. CRUD is an acronym that stands for CREATE, READ, UPDATE, and DELETE. For example, in a SQL database, the CRUD functions are used to interact with or manipulate the data stored in the database. Table 28-4 lists the CRUD functions and their associated actions and use cases.

Table 28-4 CRUD Functions and Use Cases

CRUD Function

Action

Use Case

CREATE

Inserts data in a database or application

Updating a customer’s home address in a database

READ

Retrieves data from a database or application

Pulling up a customer’s home address from a database

UPDATE

Modifies or replaces data in a database or application

Changing a street address stored in a database

DELETE

Removes data from a database or application

Removing a customer from a database

API Tools and Resources

Whether you’re trying to learn how APIs interact with applications or controllers, need to test code and outcomes, or want to become a full-time developer, one of the most important pieces of interacting with any software using APIs is testing. Testing code helps ensure that developers are accomplishing the outcome that was intended when executing the code. This section covers some tools and resources related to using APIs and REST functions. This information will help you hone development skills in order to become a more efficient network engineer with coding skills.

Introduction to Postman

Earlier, this chapter mentioned being able interact with a software controller using RESTful APIs. It also discussed being able to test code to see if the desired outcomes are accomplished when executing the code. Keep in mind that APIs are software interfaces into an application or a controller. Many APIs require authentication. This means that such an API is considered just like any other device to which a user needs to authenticate to gain access to utilize the APIs. A developer who is authenticated has access to making changes using the API, which can impact that application. This means if a REST API call is used to delete data, that data will be removed from the application or controller just as if a user logged into the device via the CLI and deleted it. It is best practice to use a test lab or the Cisco DevNet sandbox while learning or practicing any of these concepts to avoid accidental impact to a production or lab environment.

Note

Cisco DevNet is covered later in this chapter.

Postman is an application that makes it possible to interact with APIs using a console-based approach. Postman allows for the use of various data types and formats to interact with REST-based APIs. Figure 28-2 shows the main Postman application dashboard.

The Postman Dashboard online page is shown.

Figure 28-2 Postman Dashboard

Note

The screenshots of Postman used at the time of this writing may differ from the currently available version.

The Postman application has various sections that you can interact with. The focus here is on using the Builder portion of the dashboard. The following sections are the ones that require the most focus and attention:

  • History

  • Collections

  • New Tab

  • URL bar

The History tab shows a list of all the recent API calls made using Postman. Users have the option to clear their entire history at any time if they want to remove the complete list of API calls that have been made. This is done by clicking the Clear All link at the top of the Collection window (see Figure 28-3). Users also have the ability to remove individual API calls from the history list by simply hovering the mouse over an API call and clicking the trash can icon in the submenu that pops up.

The online Postman API History page is shown.

Figure 28-3 Clearing the Postman API History

API calls can be stored in groups, called collections, that are specific to a structure that fits the user’s needs. Collections can follow any naming convention and appear as a folder hierarchy. For example, it’s possible to have a collection called DNA-C to store all the Cisco DNA Center API calls. Saving API calls to a collection helps during testing phases as the API calls can easily be found and sorted. It is also possible to select a collection to be a favorite by clicking the star icon to the right of the collection name. Figure 28-4 shows a collection called DNA-C that is selected as a favorite.

The online Postman Collection page is shown.

Figure 28-4 A Favorite Postman Collection

Tabs provide another very convenient way to work with various API calls. Each tab can have its own API call and parameters that are completely independent of any other tab. For example, a user can have one tab open with API calls interacting with the Cisco DNA Center controller and another tab open that is interacting with a completely different platform, such as a Cisco Nexus switch. Each tab has its own URL bar to be able to use a specific API. Remember that an API call using REST is very much like an HTTP transaction. Each API call in a RESTful API maps to an individual URL for a particular function. This means every configuration change or poll to retrieve data a user makes in a REST API has a unique URL—whether it is a GET, POST, PUT, PATCH, or DELETE function. Figures 28-5 and 28-6 show two different tabs using unique URLs for different API calls.

The online Postman page shows the URL bar and Collections pane on the left side.

Figure 28-5 Postman URL Bar with Cisco DNA Center Token API Call

The URL bar and Collections pane on the left side are shown in the online Postman page.

Figure 28-6 Postman URL Bar with Cisco DNA Center Host API Call

Data Formats (XML and JSON)

Now that the Postman dashboard has been shown, it’s time to discuss two of the most common data formats that are used with APIs. The first one is called Extensible Markup Language (XML). This format may look familiar, as it is the same format that is commonly used when constructing web services. XML is a tag-based language, and a tag must begin with a < symbol and end with a > symbol. For example, a start tag named interface would be represented as <interface>. Another XML rule is that a section that is started must also be ended. So, if a start tag is called <interface>, the section needs to be closed by using an accompanying end tag. The end tag must be the same as the string of the start tag preceded by /. For example, the end tag for <interface> would be </interface>. Inside the start tag and end tag, you can use different code and parameters. Example 28-1 shows a snippet of XML output with both start and end tags as well as some configuration parameters.

Example 28-1 XML Code Snippet

<users>
   <user>
     <name>root</name>
   </user>
   <user>
     <name>Jason</name>
   </user>
   <user>
     <name>Jamie</name>
   </user>
   <user>
     <name>Luke</name>
   </user>
 </users>

Notice that each section of Example 28-1 has a start tag and an end tag. The data is structured so that it contains a section called “users,” and within that section are four individual users:

  • root

  • Jason

  • Jamie

  • Luke

Before and after each username is the start tag <user> and the end tag </user>. The output also contains the start tag <name> and the end tag </name>. These tags are used for each user’s name. If it is necessary to create another section to add another user, you can simply follow the same logic as used in the previous example and build out more XML code.

Remember that one of the key features of XML is that it is readable by both humans and applications. Indentation of XML sections is part of what makes it so readable. For instance, if indentation isn’t used, it is harder to read and follow the sections in XML output. Although indentation is not required, it is certainly a recommended best practice from a legibility perspective. Example 28-2 shows an XML snippet listing available interfaces on a device. In this case, the XML code snippet has no indentation, so you can see how much less readable this snippet is than the one in Example 28-1.

Example 28-2 XML Code Snippet Without Indentation

<interfaces>
<interface>
<name>GigabitEthernet1</name>
</interface>
<interface>
<name>GigabitEthernet11</name>
</interface>
<interface>
<name>Loopback100</name>
</interface>
<interface>
<name>Loopback101</name>
</interface>
</interfaces>

The second data format that is important to cover is called JavaScript Object Notation (JSON). Although JSON has not been around as long as XML, it is taking the industry by storm, and some say that it will soon replace XML. The reason this data format is gaining popularity is that it can be argued that JSON is much easier to work with than XML. It is simple to read and create, and the way the data is structured is much cleaner. JSON stores all its information in key/value pairs. As with XML, JSON is easier to read if the data is indented. However, even without indentation, JSON is extremely easy to read. As the name suggests, JSON uses objects for its format. Each JSON object starts with a { and ends with a }. (These are commonly referred to as curly braces.) Example 28-3 shows how JSON can be used to represent the same username example shown for XML in Example 28-1. You can see that it has four separate key/value pairs, one for each user’s name.

Example 28-3 JSON Code Snippet

{
  "user": "root",
  "father": "Jason",
  "mother": "Jamie",
  "friend": "Luke"
}

In this JSON code snippet, you can see that the first key is user, and the value for that key is a unique username, root.

Now that the XML and JSON data formats have been explained, it is important to circle back to actually using the REST API and the associated responses and outcomes of doing so. First, we need to look at the HTTP response status codes. Most Internet users have experienced the dreaded “404 Not Found” error when navigating to a website. However, many users don’t know what this error actually means. Table 28-5 lists the most common HTTP status codes as well as the reasons users may receive each one.

Table 28-5 HTTP Status Codes

HTTP Status Code

Result

Common Reason for Response Code

200

OK

Using GET or POST to exchange data with an API

201

Created

Creating resources by using a REST API call

400

Bad Request

Request failed due to client-side issue

401

Unauthorized

Client not authenticated to access site or API call

403

Forbidden

Access not granted based on supplied credentials

404

Not Found

Page at HTTP URL location does not exist or is hidden

Cisco DNA Center APIs

The Cisco DNA Center controller expects all incoming data from the REST API to be in JSON format. It is also important to note that the HTTP POST function is used to send the credentials to the Cisco DNA Center controller. Cisco DNA Center uses basic authentication to pass a username and password to the Cisco DNA Center Token API to authenticate users. This API is used to authenticate a user to the Cisco DNA Center controller to make additional API calls. Just as users do when logging in to a device via the CLI, if secured properly, they should be prompted for login credentials. The same method applies to using an API to authenticate to software. The key steps necessary to successfully set up the API call in Postman are as follows (see Figure 28-7):

Step 1. In the URL bar, enter https://sandboxdnac.cisco.com/api/system/v1/auth/token to target the Token API.

Step 2. Select the HTTP POST operation from the dropdown box.

Step 3. Under the Authorization tab, ensure that the type is set to Basic Auth.

Step 4. Enter devnetuser as the username and Cisco123! as the password.

Step 5. Select the Headers tab and enter Content-Type as the key.

Step 6. Select application/json as the value.

Step 7. Click the Send button to pass the credentials to the Cisco DNA Center controller via the Token API.

An online Postman page is shown for setting up Postman to authenticate with the Cisco DNA Center Control.

Figure 28-7 Setting Up Postman to Authenticate with the Cisco DNA Center Controller

You need a token for any future API calls to the Cisco DNA Center controller. When you are successfully authenticated to the Cisco DNA Center controller, you receive a token that contains a string that looks similar to the following:

"eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI1YTU4Y2QzN2UwNWJiYTAwOGVmNjJiOT
IiLCJhdXRoU291cmNlIjoiaW50ZXJuYWwiLCJ0ZW5hbnROYW1lIjoiVE5UMCIsInJvbGVzIjpbIjVhMz
E1MTYwOTA5MGZiYTY5OGIyZjViNyJdLCJ0ZW5hbnRJZCI6IjVhMzE1MTlkZTA1YmJhMDA4ZWY2
MWYwYSIsImV4cCI6MTUyMTQ5NzI2NCwidXNlcm5hbWUiOiJkZXZuZXR1c2VyIn0.tgAJfLc1OaUwa
JCX6lzfjPG7Om2x97oiTIozUpAzomM"

Think of it as a hash that is generated from the supplied login credentials. The token changes every time an authentication is made to the Cisco DNA Center controller. It is important to remember that when you are authenticated, the token you receive is usable only for the current authenticated session to the controller. If another user authenticates via the Token API, he or she will receive a unique token to be able to utilize the API based on his or her login credentials. Figure 28-8 shows the response from Cisco DNA Center after you issue the POST operation to the Token API.

A screenshot of the Postman My Workspace is shown.

Figure 28-8 Cisco DNA Center POST Operation

You can see in the top right of the screen shown in Figure 28-8 that the received HTTP status code from the Cisco DNA Center controller is 200 OK. Based on the list in Table 28-5, you can tell that the HTTP status code 200 means that the API call completed successfully. In addition, you can see how long it took to process the HTTP POST request: 980 ms.

Now we can take a look at some of the other available API calls. The first API call that is covered in this section is the Network Device API, which allows users to retrieve a list of devices that are currently in inventory that are being managed by the Cisco DNA Center controller. You need to prepare Postman to use the token that was generated when you successfully authenticated to the controller by following these steps (see Figure 28-9):

Step 1. Copy the token you received earlier and click a new tab in Postman.

Step 2. In the URL bar enter https://sandboxdnac.cisco.com/api/v1/network-device to target the Network Device API.

Step 3. Select the HTTP GET operation from the dropdown box.

Step 4. Select the Headers tab and enter Content-Type as the key.

Step 5. Select application/json as the value.

Step 6. Add another key and enter X-Auth-Token.

Step 7. Paste the token in as the value.

Step 8. Click Send to pass the token to the Cisco DNA Center controller and perform an HTTP GET to retrieve a device inventory list using the Network Device API.

A screenshot of the JSON script is shown in the Postman My Workspace online page.

Figure 28-9 Postman Setup for Retrieving the Network Device Inventory with an API Call

Note

The token you receive will be different from the one shown in this book. Remember that a token is unique to each authenticated user.

Based on the response received from the Cisco DNA Center controller, you can see the HTTP status code 200 OK, and you can also see that a device inventory was received, in JSON format. Example 28-4 shows a list of devices in the inventory that were pulled using the Network Device API.

Example 28-4 Device Inventory Pulled Using a Network Device API Call in Postman

{
    "response": [
        {
            "type": "Cisco ASR 1001-X Router",
            "family": "Routers",
            "location": null,
            "errorCode": null,
            "macAddress": "00:c8:8b:80:bb:00",
            "lastUpdateTime": 1521645053028,
            "apManagerInterfaceIp": "",
            "associatedWlcIp": "",
            "bootDateTime": "2018-01-11 15:47:04",
            "collectionStatus": "Managed",
            "interfaceCount": "10",
            "lineCardCount": "9",
            "lineCardId": "a2406c7a-d92a-4fe6-b3d5-ec6475be8477, 5b75b5fd-21e3-4deb-a8f6-6094ff73e2c8, 8768c6f1-e19b-4c62-a4be-51c001b05b0f, afdfa337-bd9c-4eb0-ae41-b7a97f5f473d, c59fbb81-d3b4-4b5a-81f9-fe2c8d80aead, b21b6024-5dc0-4f22-bc23-90fc618552e2, 1be624f0-1647-4309-8662-a0f87260992a, 56f4fbb8-ff2d-416b-a7b4-4079acc6fa8e, 164716c3-62d1-4e48-a1b8-42541ae6199b",
            "managementIpAddress": "10.10.22.74",
            "memorySize": "3956371104",
            "platformId": "ASR1001-X",
            "reachabilityFailureReason": "",
            "reachabilityStatus": "Reachable",
            "series": "Cisco ASR 1000 Series Aggregation Services Routers",
            "snmpContact": "",
            "snmpLocation": "",
            "tunnelUdpPort": null,
            "waasDeviceMode": null,
            "locationName": null,
            "role": "BORDER ROUTER",
            "hostname": "asr1001-x.abc.inc",
            "upTime": "68 days, 23:23:31.43",
            "inventoryStatusDetail": "<status><general code="SUCCESS"/></status>",
            "softwareVersion": "16.6.1",
            "roleSource": "AUTO",
            "softwareType": "IOS-XE",
            "collectionInterval": "Global Default",
            "lastUpdated": "2018-03-21 15:10:53",
            "tagCount": "0",
            "errorDescription": null,
            "serialNumber": "FXS1932Q1SE",
            "instanceUuid": "d5bbb4a9-a14d-4347-9546-89286e9f30d4",
            "id": "d5bbb4a9-a14d-4347-9546-89286e9f30d4"
        },
Output Snipped for brevity                                                           

By now you should see how powerful APIs can be. Within a few moments, users are able to gather a tremendous amount of information about the devices currently being managed by the Cisco DNA Center controller. In the time it takes someone to log in to a device using the CLI and issue all the relevant show commands to gather data, an API call can be used to gather that data for the entire network. APIs give network engineers time to do other things!

When using APIs, it is common to manipulate data by using filters and offsets. Say that a user wants to leverage the Network Device API to gather information on only the second device in the inventory. This is where the API documentation becomes so valuable. Most APIs have documentation that explains what they can be used to accomplish.

In Postman, it is possible to modify the Network Device API URL and add ?limit=1 to the end of the URL to show only a single device in the inventory. It is also possible to add the &offset=2 command to the end of the URL to state that only the second device in the inventory should be shown. These query parameters are part of the API and can be invoked using a client like Postman as well. Although it may sound confusing, the limit keyword simply states that a user only wants to retrieve one record from the inventory; the offset command states that the user wants that one record to be the second record in the inventory. Figure 28-10 shows how to adjust the Network Device API URL in Postman to show information on only the second device in the inventory.

A screenshot shows the Filtered Output of the Network Device API in the Postman My Workspace online page.

Figure 28-10 Filtered Output of the Network Device API

You can see from the response that the second device is consistent with the output that was shown in the initial Network Device API call (refer to Example 28-4). This device is a Cisco Catalyst 9300 switch with the MAC address f8:7b:20:67:62:80.

Cisco vManage APIs

This section discusses the various APIs available in the Cisco SD-WAN (specifically, the vManage controller). This section provides some examples of how to interact with APIs programmatically by using Postman. Leveraging Cisco SD-WAN APIs is a bit different from using the Cisco DNA Center APIs, but the two processes are quite similar. As when using a Cisco DNA Center API, with a Cisco SD-WAN API you need to provide login credentials to the API in order to be able to utilize the API calls. Some key pieces of information are necessary to successfully set up the API call in Postman:

  • The URL bar must have the API call to target the Authentication API.

  • The HTTP POST operation is used to send the username and password to Cisco vManage.

  • The Headers Content-Type key must be application/x-www-form-urlencoded.

  • The body must contain keys with the j_username devnetuser and thej_password Cisco123!.

The steps for connecting to APIs are different for Cisco SD-WAN than for Cisco DNA Center. Detailed steps for setting up the Postman environment for Cisco SD-WAN are available at https://developer.cisco.com/sdwan/. The Cisco DNA Center Postman environment setup steps are available at https://developer.cisco.com/learning/tracks/dnacenter-programmability/.

To set up a Postman environment, you can simply download steps into Postman from DevNet by going to https://developer.cisco.com/sdwan/. By doing so, you can quickly set up an environment that contains all the necessary authentication details and practice with the APIs without having to spend much time getting familiar with the details of Postman. Figure 28-11 shows the Postman environment set up for the Cisco SD-WAN API calls—specifically, the Authentication API.

A screenshot shows the highlighted entities present on the Postman My Workspace online page.

Figure 28-11 Cisco vManage Authentication API Setup for Postman

When the Postman environment is all set up and you click the Send button, the credentials are passed to vManage using the Authentication API (see Figure 28-12). The response you receive delivers something called a Java session ID, which is displayed as JSESSIONID. This is similar to the Cisco DNA Center token you worked with earlier in this chapter. This session ID is passed to vManage for all future API calls for this user. The HTTP status code 200 OK indicates a successful POST to vManage with the proper credentials.

A screenshot shows the POST Authentication web page open in the Postman My Workspace. The collection pane is open to the left of the screen. The name and value section present within the Cookie tab in the main screen is enclosed within a square. The Status 200 OK is selected above the Cookies list.

Figure 28-12 Successful HTTP POST to Cisco vManage Authentication API

Now let’s look at another API call that collects an inventory of fabric devices within Cisco vManage. Using the HTTP GET operation, this API collects the requested information and displays it in Postman. In Figure 28-13 you can see a lot from Cisco vManage’s response. You can see the URL for this API in the URL bar, and you can also see the HTTP GET request. You can also see that the response is in JSON format, which makes the data easy to read and consume.

A screenshot shows the Postman My Workspace online page. The URL text field is highlighted. The Pretty, Raw, Preview, and son tabs are present within the Body tab. the JSON tab is highlighted. The status 200 OK present above the JSON script is also highlighted.

Figure 28-13 Successful HTTP GET to the Cisco vManage Fabric Device API

If you scroll down in the response, you can see a list of devices under the “data” key received from the API call. This list contains a series of information about each fabric device within Cisco vManage. Some of the information you can see in Figure 28-14 is as follows:

  • Device ID

  • System IP

  • Host name

  • Reachability

  • Status

  • Device type

  • Site ID

A screenshot of the Postman My Workspace shows the HTTP GET. The Collections pane is open to the left of the screen. The JSON script is present on the main screen.

Figure 28-14 Data Received with a Successful HTTP GET to the Cisco vManage Fabric Device API

As you can see, a single API call has the power to gather a significant amount of information. How the data is used is up to the person making the API calls and collecting the data. All the tools, processes, and APIs can be leveraged to provide tremendous value to the business—from visibility into the environment to building relevant use cases to be consumed by the business or its customers.

Data Models and Supporting Protocols

This section provides a high-level overview of some of the most common data models and tools and how they are leveraged in a programmatic approach:

  • Yet Another Next Generation (YANG) modeling language

  • Network Configuration Protocol (NETCONF)

  • RESTCONF

YANG Data Models

SNMP is widely used for fault handling and monitoring. However, it is not often used for configuration changes. CLI scripting is used more often than other methods. YANG data models are an alternative to SNMP MIBs and are becoming the standard for data definition languages. YANG, which is defined in RFC 6020, uses data models. Data models are used to describe whatever can be configured on a device, everything that can be monitored on a device, and all the administrative actions that can be executed on a device, such as resetting counters or rebooting the device. This includes all the notifications that the device is capable of generating. All these variables can be represented within a YANG model. Data models are very powerful in that they create a uniform way to describe data, which can be beneficial across vendors’ platforms. Data models allow network operators to configure, monitor, and interact with network devices holistically across the entire enterprise environment.

YANG models use a tree structure. Within that structure, the models are similar in format to XML and are constructed in modules. These modules are hierarchical in nature and contain all the different data and types that make up a YANG device model. YANG models make a clear distinction between configuration data and state information. The tree structure represents how to reach a specific element of the model, and the elements can be either configurable or not configurable.

Every element has a defined type. For example, an interface can be configured to be on or off. However, the operational interface state cannot be changed; for example, if the options are only up or down, it is either up or down, and nothing else is possible. Example 28-5 illustrates a simple YANG module taken from RFC 6020.

Example 28-5 YANG Model Example

container food {
  choice snack {
      case sports-arena {
          leaf pretzel {
              type empty;
          }
          leaf popcorn {
              type empty;
          }
      }
      case late-night {
          leaf chocolate {
              type enumeration {
                  enum dark;
                  enum milk;
                  enum first-available;
              }
          }
      }
  }
}

The output in Example 28-5 can be read as follows: There is food. Of that food, there is a choice of snacks. The snack choices are pretzels and popcorn. If it is late at night, the snack choices are two different types of chocolate. A choice must be made to have milk chocolate or dark chocolate, and if the consumer is in a hurry and does not want to wait, the consumer can have the first available chocolate, whether it is milk chocolate or dark chocolate. Example 28-6 shows a more network-oriented example that uses the same structure.

Example 28-6 Network-Oriented YANG Model

list interface {
     key "name";
     leaf name {
         type string;
     }
     leaf speed {
         type enumeration {
             enum 10m;
             enum 100m;
             enum auto;
         }
     }
     leaf observed-speed {
         type uint32;
         config false;
     }
}

The YANG model in Example 28-6 can be read as follows: There is a list of interfaces. Of the available interfaces, there is a specific interface that has three configurable speeds. Those speeds are 10 Mbps, 100 Mbps, and auto, as listed in the leaf named speed. The leaf named observed-speed cannot be configured due to the config false command. This is because as the leaf is named, the speeds in this leaf are what was auto-detected (observed); hence, it is not a configurable leaf. This is because it represents the auto-detected value on the interface, not a configurable value.

NETCONF

NETCONF, defined in RFC 4741 and RFC 6241, is an IETF standard protocol that uses the YANG data models to communicate with the various devices on the network. NETCONF runs over SSH, TLS, and (although not common), Simple Object Access Protocol (SOAP). Some of the key differences between SNMP and NETCONF are listed in Table 28-6. One of the most important differences is that SNMP can’t distinguish between configuration data and operational data, but NETCONF can. Another key differentiator is that NETCONF uses paths to describe resources, whereas SNMP uses object identifiers (OIDs). A NETCONF path can be similar to interfaces/interface/eth0, which is much more descriptive than what you would expect from SNMP. The following is a list of some of the common use cases for NETCONF:

  • Collecting the status of specific fields

  • Changing the configuration of specific fields

  • Taking administrative actions

  • Sending event notifications

  • Backing up and restoring configurations

  • Testing configurations before finalizing the transaction

Table 28-6 Differences Between SNMP and NETCONF

Feature

SNMP

NETCONF

Resources

OIDs

Paths

Data models

Defined in MIBs

YANG core models

Data modeling language

SMI

YANG

Management operations

SNMP

NETCONF

Encoding

BER

XML, JSON

Transport stack

UDP

SSH/TCP

Transactions are all or nothing. There is no order of operations or sequencing within a transaction. This means there is no part of the configuration that is done first; the configuration is deployed all at the same time. Transactions are processed in the same order every time on every device. Transactions, when deployed, run in a parallel state and do not have any impact on each other. Parallel transactions touching different areas of the configuration on a device do not overwrite or interfere with each other. They also do not impact each other if the same transaction is run against multiple devices.

Example 28-7 provides an example of a NETCONF element from RFC 4741. This NETCONF output can be read as follows: There is an XML list of users named users. In that list, there are individual users named Dave, Rafael, and Dirk.

Example 28-7 NETCONF Element Example

<rpc-reply message-id="101"
        xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
     <data>
       <top xmlns="http://example.com/schema/1.2/config">
         <users>
           <user>
             <name>Dave</name>
           </user>
           <user>
             <name>Rafael</name>
           </user>
           <user>
             <name>Dirk</name>
           </user>
         </users>
       </top>
     </data>
   </rpc-reply>

An alternative way of looking at this type of NETCONF output is to simply look at it as though it were a shopping list. Example 28-8 provides an example of the shopping list concept. It can be read as follows: There is a group called beverages. Of these beverages, there are soft drinks and tea. The available soft drinks are cola and root beer. Of the available tea, there is sweetened or unsweetened.

Example 28-8 Shopping List Example

Beverages
    Soft Drinks
        Cola
        Root Beer
    Tea
        Sweetened
        Unsweetened

Figure 28-15 illustrates how NETCONF uses YANG data models to interact with network devices and then talk back to management applications. The dotted lines show the devices talking back directly to the management applications, and the solid lines illustrate the NETCONF protocol talking between the management applications and the devices.

A diagram represents the procedure of YANG models used by NETCONF to interact with the Management Applications.

Figure 28-15 NETCONF/YANG Interfacing with Management Applications

NETCONF exchanges information called capabilities when the TCP connection has been made. Capabilities tell the client what the device it’s connected to can do. Furthermore, other information can be gathered by using the common NETCONF operations shown in Table 28-7.

Table 28-7 NETCONF Operations

NETCONF Operation

Description

<get>

Requests running configuration and state information of the device

<get-config>

Requests some or all of the configuration from a datastore

<edit-config>

Edits a configuration datastore by using CRUD operations

<copy-config>

Copies the configuration to another datastore

<delete-config>

Deletes the configuration

Information and configurations are stored in datastores. Datastores can be manipulated by using the NETCONF operations listing in Table 28-7. NETCONF uses Remote Procedure Call (RPC) messages in XML format to send the information between hosts.

Now that we’ve looked at the basics of NETCONF and XML, let’s examine some actual examples of a NETCONF RPC message. Example 28-9 shows an example of an OSPF NETCONF RPC message that provides the OSPF routing configuration of an IOS XE device.

Example 28-9 NETCONF OSPF Configuration Example

<rpc-reply message-id="urn:uuid:0e2c04cf-9119-4e6a-8c05-238ee7f25208"
xmlns="urn:ietf:params:xml:ns:netconf:base:1.0" xmlns:nc="urn:ietf:params:
xml:ns:netconf:base:1.0">
  <data>
    <native xmlns="http://cisco.com/ns/yang/ned/ios">
      <router>
        <ospf>
          <id>100</id>
          <redistribute>
            <connected>
              <redist-options>
                <subnets/>
              </redist-options>
            </connected>
          </redistribute>
          <network>
            <ip>10.10.0.0</ip>
            <mask>0.0.255.255</mask>
            <area>0</area>
          </network>
          <network>
            <ip>20.20.0.0</ip>
            <mask>0.0.255.255</mask>
            <area>0</area>
          </network>
          <network>
            <ip>100.100.0.0</ip>
            <mask>0.0.255.255</mask>
            <area>0</area>
          </network>
        </ospf>
      </router>
    </native>
  </data>
</rpc-reply>

The same OSPF router configuration that would be seen in the command-line interface of a Cisco router can be seen using NETCONF. The data is just structured in XML format rather than what users are accustomed to seeing in the CLI. It is easy to read the output in these examples because of how legible XML is. Example 28-10 saves the configuration of a Cisco network device by leveraging NETCONF.

Example 28-10 NETCONF Save Config Example

<?xml version="1.0" encoding="utf-8"?>
<rpc xmlns="urn:ietf:params:xml:ns:netconf:base:1.0" message-id="">
  <cisco-ia:save-config xmlns:cisco-ia="http://cisco.com/yang/cisco-ia"/>
</rpc>
RESTCONF

RESTCONF, defined in RFC 8040, is used to programmatically interface with data defined in YANG models while also using the datastore concepts defined in NETCONF. There is a common misconception that RESTCONF is meant to replace NETCONF, but this is not the case. Both are very common methods used for programmability and data manipulation. If fact, RESTCONF uses the same YANG models as NETCONF and Cisco IOS XE. The goal of RESTCONF is to provide a RESTful API experience while still leveraging the device abstraction capabilities provided by NETCONF. RESTCONF supports the following HTTP methods and CRUD operations:

  • GET

  • POST

  • PUT

  • DELETE

  • OPTIONS

The RESTCONF requests and responses can use either JSON or XML structured data formats. Example 28-11 shows a brief example of a RESTCONF GET request on a Cisco router to retrieve the logging severity level that is configured. This example uses JSON instead of XML. Notice the HTTP status 200, which indicates that the request was successful.

Example 28-11 RESTCONF GET Logging Severity Example

RESTCONF GET
------------------------

URL: https://10.85.116.59:443/restconf/data/Cisco-IOS-XE-native:native/logging/
monitor/severity

Headers: {'Accept-Encoding': 'gzip, deflate',  'Accept': 'application/yang-data+json, application/
yang-data.errors+json'}

 Body:

RESTCONF RESPONSE

----------------------------

200

{

  "Cisco-IOS-XE-native:severity": "critical"

}

Cisco DevNet

The examples and tools discussed in this chapter are all available for use and practice at Cisco DevNet (http://developer.cisco.com). Network operators who are looking to enhance or increase their skills with APIs, coding, Python, or even controller concepts can find a wealth of help at DevNet. At DevNet it is easy to find learning labs and content to help solidify current knowledge in network programmability. Whether you’re just getting started or are a seasoned programming professional, DevNet is the place to be! This section provides a high-level overview of DevNet, including the different sections of DevNet and some of the labs and content that are available. Figure 28-16 shows the DevNet main page.

The DevNet main page is shown.

Figure 28-16 DevNet Main Page

Across the top of the main page are a few menu options:

  • Discover

  • Technologies

  • Community

  • Support

  • Events

Discover

The Discover page is where you can navigate the different offerings that DevNet has available. Under this tab are subsections for guided learning tracks, which guide you through various technologies and the associated API labs. Some of the labs you interact with are Programming the Cisco Digital Network Architecture (DNA), ACI Programmability, Getting Started with Cisco WebEx Teams APIs, and Introduction to DevNet. When you choose a learning lab and start a module, the website tracks all your progress so you can go away and come back and continue where you left off. This is helpful for continuing your education over the course of multiple days or weeks.

Technologies

The Technologies page allows you to pick relevant content based on the technology you want to study and dive directly into the associated labs and training for that technology. Figure 28-17 illustrates some of the networking content that is currently available.

The DevNet Technologies web page is shown.

Figure 28-17 DevNet Technologies Page

Note

Available labs may differ from what is shown in this chapter. Please visit http://developer.cisco.com to see the latest content available and to interact with the latest learning labs and sandbox environments.

Community

Perhaps one of the most important section of DevNet is the Community page. This is where users have access to many different people at various stages of learning. DevNet ambassadors and evangelists are available to help at various stages of your learning journey. The Community page puts the latest events and news at your fingertips. This is also the place to read blogs, sign up for developer forums, and follow DevNet on all major social media platforms. This is a safe zone for asking questions, simple or complex. The DevNet Community page is the place to start for all things Cisco and network programmability. Figure 28-18 shows some of the available options for users on the Community page.

The DevNet Community web page is shown.

Figure 28-18 DevNet Community Page

Support

The Support section of DevNet is where users can post questions and get answers from some of the best in the industry. Technology-focused professionals are available to answer questions both from technical and theoretical perspectives. You can ask questions about specific labs or the overarching technology (for example, Python or YANG models). You can also open a case with the DevNet Support team, and your questions will be tracked and answered within a minimal amount of time. This is a great place to ask one-on-one questions of the Support team as well as tap into the expertise of the support engineers. Figure 28-19 shows the DevNet Support page as well as where to open a support case.

The DevNet Support web page is shown.

Figure 28-19 DevNet Support Page

Events

The DevNet Events page provides a list of all events that have happened in the past and that will be happening in the future. This is where a user can find the upcoming DevNet Express events as well as conference where DevNet will be presenting. Bookmark this page if you plan on attending any live events.

GitHub

One of the most efficient and commonly adopted ways of using version control is by using GitHub. GitHub is a hosted web-based repository for code. It has capabilities for bug tracking and task management as well. Using GitHub is one of the easiest ways to track changes in your files, collaborate with other developers, and share code with the online community. It is a great place to look for code to get started on programmability. Often times, other engineers or developers are trying to accomplish similar tasks and have already created and tested the code necessary to do so. One of the most powerful features of using GitHub is the ability to rate and provide feedback on other developers’ code. Peer review is encouraged in the coding community. Figure 28-20 shows the main GitHub web page that appears after you log in.

The GitHub main web page is shown.

Figure 28-20 GitHub Main Web Page

GitHub provides a guide that steps through how to create a repository, start a branch, add comments, and open a pull request. You can also just start a GitHub project when you are more familiar with the GitHub tool and its associated processes.

Projects are repositories that contain code files. GitHub provides a single pane to create, edit, and share code files. Figure 28-21 shows a repository called ENCORE that contains three files:

  • ENCORE.txt

  • JSON_Example.txt

  • README.md

The GitHub ENCORE Repository online page is shown.

Figure 28-21 GitHub ENCORE Repository

GitHub also gives a great summary of commit logs, so when you save a change in one of your files or create a new file, GitHub shows details about it on the main repository page (refer to Figure 28-21). If you drill down into one of the files in the repository, you can see how easy it is to edit and save code. If you drill down into JSON_Example.txt, for example, GitHub shows its contents and how to edit the file in the repository. If you click the filename JSON_Example.txt, you can see that the file has seven lines of code and it is 77 bytes in size. Figure 28-22 shows the contents of the JSON_Example.txt file and the options available with the file.

The JSON_Example dot txt Contents is shown in a screenshot.

Figure 28-22 JSON_Example.txt Contents

The pencil allows you to go into editing mode and alter the file contents. This editor is very similar to any text editor. You can simply type into the editor or copy and paste code from other files directly into it. The example in Figure 28-23 shows the addition of another user, named Zuul. If the code were to be committed, the changes in the file would be saved with the new user added to the file. Now that the file is available in the repository, other GitHub users and developers can contribute to this code or add and delete lines of code based on the code that was originally created. For example, if a user has some code to add a new user via JSON syntax, someone could use that code and simply modify the usernames or add to the code to enhance it. This is the true power of sharing code.

The JSON_Example dot txt Contents is shown.

Figure 28-23 Editing the JSON_Example.txt Contents

Basic Python Components and Scripts

Python has by a longshot become one of the most common programming languages in terms of network programmability. Learning to use programming languages can be daunting. Python is one of the easier languages to get started with and interpret. Although this section does not cover how to create or write complex programs or scripts in Python, it does teach some of the fundamental skills necessary to be able to interpret Python scripts. When you understand the basics of interpreting what a Python script is designed to do, it will be easier to understand and leverage other scripts that are available.

GitHub has some amazing Python scripts available for download that come with very detailed instructions and documentation. Everything covered in this section is taken from publicly available GitHub scripts. This section leverages the new knowledge you have gained in this chapter about APIs, HTTP operations, DevNet, and GitHub. Example 28-12 shows a Python script that sets up the environment to log in to the Cisco DNA Center sandbox. This script uses the same credentials used with the Token API earlier in this chapter.

Note

The scripts covered in this section are available at https://github.com/.

Example 28-12 Env_Lab.py

"""Set the Environment Information Needed to Access Your Lab!
The provided sample code in this repository will reference this file to get the
information needed to connect to your lab backend.  You provide this info here
once and the scripts in this repository will access it as needed by the lab.


Copyright (c) 2018 Cisco and/or its affiliates.

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
"""


# User Input

# Please select the lab environment that you will be using today
#     sandbox - Cisco DevNet Always-On / Reserved Sandboxes
#     express - Cisco DevNet Express Lab Backend
#     custom  - Your Own "Custom" Lab Backend
ENVIRONMENT_IN_USE = "sandbox"

# Set the 'Environment Variables' based on the lab environment in use
if ENVIRONMENT_IN_USE == "sandbox":
    dnac = {
        "host": "sandboxdnac.cisco.com",
        "port": 443,
        "username": "devnetuser",
        "password": "Cisco123!"
}

The Env_Lab.py python script starts with three quotation marks. These three quotation marks begin and end a multiple-line string. A string is simply one or more alphanumeric characters. A string can comprise many numbers or letters, depending on the Python version in use. In the case of this script, the creator used a multiple-line string to put additional overall comments into the script. This is not mandatory, but you can see that comments are helpful. The # character indicates a comment in the Python script file. Such comments usually describe the intent of an action within the code. Comments often appear right above the action they describe. Some scripts have a comment for each action, and some are not documented very well, if at all. The comments in this Env_Lab.py script indicate that there are three available options for selecting the lab environment to use:

  • Sandbox: The line in this Python script that says ENVIRONMENT IN USE= “sandbox” corresponds to the selection of the sandbox type of lab environments available through DevNet. In this instance, “sandbox” refers to the always-on and reserved sandboxes that can be accessed through http://developer.cisco.com.

  • Express: This is the back end that is used for the DevNet Express Events that are held globally at various locations and Cisco office locations, as mentioned earlier in this chapter.

  • Custom: This is used in the event that there is already a Cisco DNA Center installed either in a lab or another facility, and it needs to be accessed using this script.

This chapter uses the sandbox lab environment for all examples and explanations.

As you can see in the Python script in Example 28-12, a few variables are used to target the DevNet Cisco DNA Center sandbox specifically. Table 28-8 describes these variables.

Table 28-8 Python Variables for Cisco DNA Center Sandbox in Env_Lab.py

Variable

Value

Description

host

sandboxdnac.cisco.com

Cisco DNA Center sandbox URL

port

443

TCP port to access URL securely (HTTPS)

username

devnetuser

Username to log in to Cisco DNA Center sandbox (via API or GUI)

password

Cisco123!

Password to log in to Cisco DNA Center sandbox (via API or GUI)

The variables shown in Table 28-8 should look familiar as they are in the JSON data format that was discussed earlier in this chapter. Remember that JSON uses key/value pairs and is extremely easy to read and interpret. In Example 28-13, you can see the key/value pair “username”: “devnetuser”. The structure used to hold all the key/value pairs in this script is called a dictionary. In this particular Python script, the dictionary is named dnac. The dictionary named dnac contains multiple key/value pairs, and it starts and ends with curly braces ({}).

Example 28-13 Dictionary Used in Env_Lab.py

dnac = {
    "host": "sandboxdnac.cisco.com",
    "port": 443,
    "username": "devnetuser",
    "password": "Cisco123!"
}

Dictionaries can be written in multiple different ways. Whereas Example 28-13 shows a multiple-line dictionary that is easily readable, Example 28-14 shows the same dictionary written as a single line.

Example 28-14 Single-Line Example of the Dictionary Used in Env_Lab.py

    dnac = {"host": "sandboxdnac.cisco.com", "port": 443, "username": "devnetuser",
"password": "Cisco123!"}

Notice that the line ENVIRONMENT_IN_USE = “sandbox” is used in this script. Following that line in the script is a line that states if ENVIRONMENT_IN_USE == “sandbox”: This is called a condition. A logical if question is asked, and depending on the answer, an action happens. In this example, the developer called out to use the sandbox option with the line of code ENVIRONMENT_IN_USE = “sandbox” and then used a condition to say that if the environment in use is sandbox, call a dictionary named dnac to provide the sandbox details that are listed in key/value pairs. Example 28-15 shows the two relevant lines of code to illustrate this.

Example 28-15 Condition Example Used in Env_Lab.py

ENVIRONMENT_IN_USE = "sandbox"

# Set the 'Environment Variables' based on the lab environment in use
if ENVIRONMENT_IN_USE == "sandbox":

Now let’s look at a script that showcases much of the API information that was covered in this chapter and also builds on all the basic Python information that has just been provided. Example 28-16 shows a Python script called get_dnac_devices.py.

Example 28-16 The Full get_dnac_devices.py Script

#! /usr/bin/env python3

from env_lab import dnac
import json
import requests
import urllib3
from requests.auth import HTTPBasicAuth
from prettytable import PrettyTable

dnac_devices = PrettyTable(['Hostname','Platform Id','Software Type','Software
Version','Up Time' ])
dnac_devices.padding_width = 1

# Silence the insecure warning due to SSL Certificate
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)

headers = {
              'content-type': "application/json",
              'x-auth-token': ""
          }


def dnac_login(host, username, password):
    url = "https://{}/api/system/v1/auth/token".format(host)
    response = requests.request("POST", url, auth=HTTPBasicAuth(username, password),
                                headers=headers, verify=False)
    return response.json()["Token"]


def network_device_list(dnac, token):
    url = "https://{}/api/v1/network-device".format(dnac['host'])
    headers["x-auth-token"] = token
    response = requests.get(url, headers=headers, verify=False)
    data = response.json()
    for item in data['response']:
    dnac_devices.add_row([item["hostname"],item["platformId"],item["softwareType"],
    item["soft.   wareVersion"],item["upTime"]])


login = dnac_login(dnac["host"], dnac["username"], dnac["password"])
network_device_list(dnac, login)

print(dnac_devices)

It might seem like there is a lot going on in the get_dnac_device.py script. However, many of the details have already been explained in the chapter. This section ties together all the components discussed previously and expands on how they work together by breaking the script into five sections, with explanations.

The first section of code tells the Python interpreter what modules this particular script will use. Think of a module as a collection of actions and instructions. To better explain the contents in this script, comments are inserted throughout the script to help document each section. Example 28-17 shows the first section of the get_dnac_devices.py with comments that explain what’s going on.

Example 28-17 Explanation of the First Section of get_dnac_devices.py

# Specifies which version of Python will be used                                     
#! /usr/bin/env python3

# Calls "dnac" dictionary from the env_lab.py script covered earlier                 
from env_lab import dnac

# Imports JSON module so Python can understand the data format that contains key/    
value pairs
import json

# Imports requests module which handles HTTP headers and form data                   
import requests

# Imports urllib3 module which is an HTTP client                                     
import urllib3

# Imports HTTPBasicAuth method from the requests.auth module for authentication to
Cisco DNA Center
from requests.auth import HTTPBasicAuth

# Imports prettytable components from PrettyTable module to structure return data
from Cisco DNA Center in table format
from prettytable import PrettyTabl

Modules help Python understand what it is capable of. For example, if a developer tried to do an HTTP GET request without having the Requests modules imported, it would be difficult for Python to understand how to interpret the HTTP call. Although there are other ways of doing HTTP calls from Python, the Requests modules greatly simplify this process.

Example 28-18 shows the second section of the get_dnac_devices.py script along with explanatory comments.

Example 28-18 Explanation of the Second Section of get_dnac_devices.py

# Puts return data from Cisco DNA Center Network Device API call into easily read-
able table with column names Hostname, Platform Id, Software Type, Software Version
and Up Time.
dnac_devices = PrettyTable(['Hostname','Platform Id','Software Type','Software
Version','Up Time' ])
dnac_devices.padding_width = 1

# Silences the insecure warning due to SSL Certificate                               
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)

# Sends specific HTTP headers to Cisco DNA Center when issuing HTTP GET to the Net-
work Devices API

headers = {
              'content-type': "application/json",
              'x-auth-token': ""
}

Functions are blocks of code that are built to perform specific actions. Functions are very structured in nature and can often be reused later on within a Python script. Some functions are built into Python and do not have to be created. A great example of this is the print function, which can be used to print data to a terminal screen. You can see the print function at the end of the get_dnac_devices.py script. Recalling from earlier in this chapter that in order to execute any API calls to Cisco DNA Center, you must be authenticated, using the Token API. Example 28-19 shows the use of the Token API within a Python script. (Recall that you saw this API used with Postman earlier in the chapter.)

Example 28-19 Explanation of the Third Section of get_dnac_devices.py

# This function does an HTTP POST of the username devnetuser and the password of
Cisco123! to the Token API located at https://sandboxdnac.cisco.com/api/system/v1/
auth/token and uses the values built in the JSON key-value pairs from the Env_Lab.
py. The JSON response from the API called is stored as the Token that will be used
for future API calls for this authenticated user.

def dnac_login(host, username, password):
    url = "https://{}/api/system/v1/auth/token".format(host)
    response = requests.request("POST", url, auth=HTTPBasicAuth(username, password),
                                headers=headers, verify=False)
    return response.json()["token"]

Note

The API URL in this example is exactly the same one used earlier in this chapter.

This section of the script shown in Example 28-20 ties the Token API to the Network Device API call to retrieve the information from Cisco DNA Center. The line that says header [“x-auth-token”] = token is mapping the JSON response from the previous example, which is the token, into the header called x-auth-token. In addition, the URL for the API has changed to network_device, and the response is sending a requests.get to that URL. This is exactly the same example used with Postman earlier in this chapter.

Example 28-20 Explanation of the Fourth Section of get_dnac_devices.py

def network_device_list(dnac, token):
    url = "https://{}/api/v1/network-device".format(dnac['host'])
    headers["x-auth-token"] = token
    response = requests.get(url, headers=headers, verify=False)
    data = response.json()
    for item in data['response']:
        dnac_devices.add_row([item["hostname"],item["platformId"],item["softwareType
"],item["softwareVersion"],item["upTime"]])

The final section of get_dnac_devices.py shows code that ties the dnac dictionary that is in the Env_Lab.py script to the dnac_login function covered earlier. In addition, the print function takes the response received from the response.get that was sent to the Network Device API and puts it into the table format that was specified earlier in the script with the name dnac_devices. Example 28-21 shows the final lines of code in the script.

Example 28-21 Explanation of the Fifth Section of get_dnac_devices.py

login = dnac_login(dnac["host"], dnac["username"], dnac["password"])
network_device_list(dnac, login)

print(dnac_devices)

The Python script examples in this chapter make it easy to see the power and easy-to-use nature of Python. You practice with the examples in this chapter to increase your experience with Python and API structures. The tools mentioned in this chapter, including Postman and Python, are readily available on the Internet for free. These tools, examples, and much more can be studied in depth at http://developer.cisco.com.

The tools covered in this chapter are available online and are very useful in terms of building skill and expertise. Go to DevNet to practice with any of the technologies covered in this chapter. It is often said of programmability that you can start small, but you should just start! A great way to practice is by using a sandbox environment and just building code and running it to see what can be accomplished. You are only limited by your imagination and coding skills! Remember to have fun and keep in mind that programmability is a journey, not a destination. Separating your learning into small, manageable chunks will make it easier to get better with practice and time.

Exam Preparation Tasks

As mentioned in the section “How to Use This Book” in the Introduction, you have a couple of choices for exam preparation: the exercises here, Chapter 30, “Final Preparation,” and the exam simulation questions in the Pearson Test Prep Software Online.

Review All Key Topics

Review the most important topics in the chapter, noted with the key topics icon in the outer margin of the page. Table 28-9 lists these key topics and the page number on which each is found.

Table 28-9 Key Topics for Chapter 28

Key Topic Element

Description

Page

Table 28-3

HTTP Functions and Use Cases

820

Table 28-4

CRUD Functions and Use Cases

820

Table 28-5

HTTP Status Codes

826

List

Steps to authenticate to Cisco DNA Center using a POST operation and basic authentication

826

List

Steps to leverage the Network Device API to retrieve a device inventory from Cisco DNA Center

828

Paragraph

Using the offset and limit filters with the Network Device API when gathering device inventory

830

Complete Tables and Lists from Memory

Print a copy of Appendix B, “Memory Tables” (found on the companion website), or at least the section for this chapter, and complete the tables and lists from memory. Appendix C, “Memory Tables Answer Key,” also on the companion website, includes completed tables and lists you can use to check your work.

Define Key Terms

Define the following key terms from this chapter and check your answers in the Glossary:

application programming interface (API)

command-line interface (CLI)

DevNet

Extensible Markup Language (XML)

GitHub

Java-Script Object (JSON)

NETCONF

Python

RESTCONF

Yang Model

References in This Chapter

RFC 4741, NETCONF Configuration Protocol, by R. Enns. https://tools.ietf.org/html/rfc4741, December 2006.

RFC 6020, YANG—A Data Modeling Language for the Network Configuration Protocol (NETCONF), by M. Bjorklund. https://tools.ietf.org/html/rfc6020, October 2010.

RFC 6241, Network Configuration Protocol (NETCONF), by R. Enns, M. Bjorklund, J. Schoenwaelder, A. Bierman. https://tools.ietf.org/html/rfc6241, June 2011.

RFC 8040, RESTCONF, by A. Bierman, M. Bjorklund, K. Watsen. https://tools.ietf.org/html/rfc8040, January 2017.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset