Cisco ISE and API for Guest access

Cisco ISE and API for Guest access

I wrote a lengthy post in May about using the API on Cisco ISE (and deleted).
The article was mainly supposed to demonstrate how to enable the API and basic use.
But I’m not a programmer, at best I can be very creative with bash scripts and curl, and my limited knowledge prevented me from finishing the article because I didn’t know how to handle the errors I got.
In the meantime, I’ve started playing around with python. I’m still not a programmer, but my scripting is more fun now. 🙂

Scenario:

Cisco WLC authenticates (“mac filtering”) with Cisco Identity Services Engine (ISE) so guest users use the Cisco ISE guest portal to log on to the wireless network.
There are plenty of ways to manage the guest users; self registration, sponsor portals and more, but since we already had a system in place to “manage” in-house guests, we wanted the system to automatically create guest users when were registered in the reception.

The ISE is at version 2.2, and this was important to me, because prior to 2.2 the API did not support JSON for Guest REST API, only xml.

Guest and sponsor portals were already configured, and we were already able to create guest users using the sponsor portal on the ISE, so I won’t go into details on that in this post.

Enabling the API:

Cisco refers to the API as “ERS”, as in “External RESTful API services” on the ISE, and it’s not on by default.
You have to to got Administration -> System -> Settings -> ERS Settings and enable ERS.

You can enable read/write for the Primary Administration Node and read for secondary nodes.

Accessing and using the API.

When the API/ERS has been enabled, port 9060 should be reachable on the ISE and you should be able to access via https://10.10.10.10:9060/ers/sdk, assuming the IP address of the ISE is 10.10.10.10.
And there you will find most of the API documentation, along with some examples and even sample-scripts.

Chances are though, that when you try to access the API, your admin credentials won’t work.
This is because being a “Super Admin” does not give you access to the API, you have to be an “ERS Admin”, so you might need to create an additional user for this purpose.

For everything related to managing and configuring the ISE, you’ll need these credentials to access the API.

To manage Guest users, you’ll need a user who has access to the sponsor portal that’s used for these guest users.
And when you have a user that’s a part of some sponsor group, you’ll also need to edit that sponsor group settings and allow sponsors to use the API to manage guests. (Not enabled by default.)

So, Work Centers -> Guest Access -> Sponsor Groups.
On the bottom of the list you’ll see where you need to allow API for guest management.

Managing Guest users

  • Open up the https://ise:9060/ers/sdk, go into API documentation and “Guest User”
    • Reference and important info is there.
  • Viewing all guest users: GET request to https://rls-ise01:9060/ers/config/guestuser
    • Using sponsor credentials.
  • Adding a guest user:
    • Before adding, we need to find out the “id” of the relevant sponsor portal.
    • https://ise:9060/ers/config/sponsorportal
      • Using the ERS admin credentials
      • Gives out a list of all portals.
    • I used the json template example for GuestUser and modified a bit.
      • In the API documentation, there’s a resource definition table, and it specified which values are required. In my experience, some items marked as “required: no” are actually required, as the API throws an error if they are missing, so just take the basic template and then play around with it.

 

My issues on the way.

Apart from having no idea what I was doing, here are a few items that I ran into:

  • There’s a bug(CSCux39158) in ISE 2.0 (and 2.1 and 2.2) when creating Guest users with XML code, the code has to be in correct order, but Cisco doesn’t specify the order.
  • Initially I tried doing this with bash scripts and curl. But I ran into multiple issues with different curl versions and SSL cipher support and SSL/TLS versions, and here’s where I initially gave up.
  • Remembering when to use the ERS-Admin credentials and when to use the Sponsor user credentials.
  • Non-descriptive error messages
    • Most of the time, when you do something wrong, ISE gives you a pretty good error message that tells you what you did wrong.
      • But sometimes if I messed the syntax up, ISE gave me a 404 error.
      • And if I try to reference a guest-type that doesn’t exist, I just get some basic error or a 404.
  • Trusting the resource-definitions in the API documentation, I removed everything that was said to be not required, only to adding most of it again.
  • The ISE will either have a self-signed certificate, or a certificate from the local/company CA.
    • So python’s request module will always throw a certificate error. Temporarily you can use “verify=False”, or just specify a CA file that includes the CA certs.

 

Some practical examples:

Remember, I just started to learn python, so don’t judge 🙂
And I’m using python 3.4 and 3.6.

Creating an authorization string to use in the header for authentication (found this somewhere on stackoverflow)

>>>
>>> import base64
>>> user='ersadmin'
>>> password='ersadmincredentials'
>>> creds = str.encode(':'.join((user, password)))
>>> encodedAuth = bytes.decode(base64.b64encode(creds))
>>> print(encodedAuth)
ZXJzYWRtaW46ZXJzYWRtaW5jcmVkZW50aWFscw==
>>>

Important: this is NOT encryption, this string can be easily reverted back to clear text.

 

Listing current guest users:

>> import pprint
>>> import requests
>>> APIauth='ZXJzYWRtaW46ZXJzYWRtaW5jcmVkZW50aWFscw=='
>>> headers = {
... 'accept': "application/json",
... 'authorization': 'Basic ' + APIauth,
... 'cache-control': "no-cache",
... }
>>>
>>> response = requests.get('https://ise-01.mycompany.tld:9060/ers/config/guestuser', headers=headers)
>>> print(bytes.decode(response.content))

(You can then load this into a dictionary or whatever, or you can check an individual guest user and see the status, dates, password etc.)

 

Creating a guest user:

>>>
>>> import requests
>>> import json
>>> APIAuth='ZXJzYWRtaW46ZXJzYWRtaW5jcmVkZW50aWFscw=='
>>> headers = {
... 'accept': "application/json",
... 'authorization': 'Basic ' + APIAuth,
... 'cache-control': "no-cache",
... 'Content-Type': 'application/json',
... 'ERS-Media-Type': 'identity.guestuser.2.0'
... }
>>>
>>> guestUserTemplate = {
... 'GuestUser' : {
... 'guestType' : 'Contractor (default)',
... 'guestInfo' : {
... 'userName' : 'dummyGuest',
... 'password' : 'dummyGuestPass1',
... 'enabled' : 'true'
... },
... 'guestAccessInfo' : {
... 'validDays' : 2,
... 'fromDate' : '09/02/2017 20:00',
... 'toDate' : '09/03/2017 20:00',
... 'location': 'Iceland'
... },
... 'portalId' : 'a6f54470-2240-11d9-55ab-007057bf5fd3'
... }
... }
>>>
>>>
>>> response = requests.post('https://ise-01.mycompany.tld:9060/ers/config/guestuser', data=json.dumps(guestUserTemplate),
headers=headers)

 

 

 

 

 

 

 

 

Leave a Comment