Authentication

Access to the Crosswork Planning REST API requires authentication and authorization with a valid account. Only these accounts can submit requests to API operations. All API communication occurs over a secure HTTPS connection.

The Crosswork Planning API allows multiple users, each with user-specific authorization and privileges based on their role. Users receive role-based access tied to their function, and REST endpoints are restricted accordingly. The admin user retains full access without restrictions.

Crosswork Planning manages individual users and provides a single API gateway for all API requests. Users authenticate through the Crosswork authentication API to access all available API requests.

Authentication and Token Management for Crosswork Planning REST API

This section explains how to obtain a Ticket Granting Ticket (TGT) and a JSON Web Token (JWT) required for making secure API calls.

The Crosswork Planning API supports standard REST methods, including POST and GET. All requests and responses use JSON-formatted payloads where applicable.

To perform API operations on the Crosswork Planning platform, you first must authenticate and obtain a JSON Web Token (JWT). The authentication process consists of two steps:

  1. Obtain a Ticket Granting Ticket (TGT): Use your username and password to request a TGT from the Single Sign-On (SSO) server.
  2. Exchange the TGT for a JWT: Use the TGT to request a JWT, which serves as a Bearer token for subsequent API calls.

Step 1: Obtain a Ticket Granting Ticket

The first step is to request a Ticket Granting Ticket (TGT) by providing your username and password.

POST URL and Request Payload

POST https://<crosswork-host>:30603/crosswork/sso/v1/tickets username=admin&password=abcdef123!

Example

curl -k -s -X POST
https://10.225.120.1:30603/crosswork/sso/v1/tickets
-H 'Content-Type: application/x-www-form-urlencoded'
-H 'Accept: text/plain'
-d 'username=admin&password=abcd123!'

Response

TGT-34-dDGV8oqlqLdDgRFlldWGPOui-XoRa8bcJ80XdQOAFqeAUYHvmMTFwm6kez35IcRmWQA-cas-6f94874745-pxnlt

Save this TGT to request a JWT in the next step.

Step 2: Obtain a JSON Web Token

With the TGT obtained in Step 1, you can request a JSON Web Token (JWT) to use for API authentication.

POST URL and Request Payload

POST https://<crosswork-host>:30603/crosswork/sso/v2/tickets/jwt tgt=TGT-34-dDGV8oqlqLdDgRFlldWGPOui-XoRa8bcJ80XdQOAFqeAUYHvmMTFwm6kez35IcRmWQA-cas-6f94874745-pxnlt service=https://198.51.100.1:30603/app-dashboard

Example

curl -k -s -X POST
https://10.225.120.1:30603/crosswork/sso/v2/tickets/jwt
-H 'Content-Type: application/x-www-form-urlencoded'
-d 'tgt=TGT-34-dDGV8oqlqLdDgRFlldWGPOui-XoRa8bcJ80XdQOAFqeAUYHvmMTFwm6kez35IcRmWQA-cas-6f94874745-pxnlt&service=https://10.225.120.1:30603/app-dashboard'

Response

eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCIsImtpZCI6IjE0ZWQ0NGQwLTZhYTQtNDg4Yy05ZDI3LWFhNWVkMjE3OTcwMyJ9.....................

Save this jwttoken to use for subsequent API requests.

Step 3: Using the JWT for Authorization

Once you have the JWT, include it in the Authorization header of your API requests.

Authorization: Bearer <JWT>

Example

curl -k -X GET
https://10.225.120.1:30603/your-api-endpoint
-H "Authorization: Bearer <JWT>"`

Replace with the token obtained in Step 2.

Note: JWTs are valid for 8 hours. When the token expires, you need to repeat the authentication steps (Step 1 and Step 2) to obtain a new JWT.

Authentication for Crosswork Planning Design And Python Libraries using OPM Libraries package

Crosswork Planning offers a Design/OPM Libraries package, downloadable from Cisco Software Central, enabling users to write and run scripts with Design and OPM Libraries on a Linux machine by connecting to the designapi service on the Crosswork Planning VM.

The OPM-service server and client communication is secured with TLS and SSL certificates, which provide digital identification for user authentication and verifying communication partners.

The authentication process consists of three steps:

  1. Generate Client Certificates.
  2. Upload Client Certificates/Onboard Clients.
  3. Add Server Certificate to Client's truststore.

Step 1: Install Python 3.10

To use the Libraries package, you must install Python 3.10 or later, ensuring it is a 64-bit version.

Step 2: Unzip the Libraries package

tar -xvzf cp_design_opm_sdk.tgz

Step 3: Update Environment

The environment variables that you need to set to use the Crosswork Planning Design/OPM Libraries package in Python scripts are:

export CARIDEN_HOME=/my/installation/home/cw-planning # Replace by actual folder where the Libraries package is unzipped
export PYTHONPATH=$PYTHONPATH:$CARIDEN_HOME/lib/python
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$CARIDEN_HOME/lib:$CARIDEN_HOME/lib/python

Step 4: Generate Client Certificates

Use the "generate_client_certs" script provided in the cp_design_opm_sdk.tgz to generate the client certificate. An optional password use for encrypting client key can be passed as argument.

Note: The script requires the Python package cryptography version 39.0.2 or later.

user@machine:~/opm-client$ cd $CARIDEN_HOME
user@machine:~/opm-client$ ls 
docs  etc  generate_client_certs  lib
user@machine:~/opm-client$  ./generate_client_certs --password
Password:

The certificates are created in the {CARIDEN_HOME}/etc/certs directory.

user@machine:~/opm-client$ ls -lhrt  $CARIDEN_HOME/etc/certs
total 16K
-rw-rw-r-- 1 akhil akhil 1.9K Jul 31 19:28 designapi_user_key.pem
-rw-rw-r-- 1 akhil akhil 1.4K Jul 31 19:28 designapi_user_cert.pem
-rw-rw-r-- 1 akhil akhil 4.1K Aug  7 06:42 ca_cert.pem
user@machine:~/opm-client$

Step 5: Upload Client Certificates / Onboard Clients

The OPM service REST API handles uploading and downloading certificates. The API requests should include the JSON web token in the Authorization header. For authorization of REST API refer: Authentication and Authorization for Crosswork Planning REST API.

In this step, we onboard a client to opm-service by uploading the client certificate generated in Step 4: Generate Client Certificates

To upload the client certificate, use a POST request to the cp/opm-service/api/v1/certs API.

Example

curl -k -s -X POST https://10.225.120.1:30603/cp/opm-service/api/v1/certs
-H 'Content-Type: multipart/form-data'
-H 'Authorization: Bearer <JWT>'
-F 'cert=@"<CARIDEN_HOME>/cw-planning/etc/certs/designapi_user_cert.pem"'
-F 'title="dev-vm-cert"

Response

{}

Replace with the token that is obtained in Step 2 of Authentication and Authorization for Crosswork Planning REST API.

Replace with the actual folder where the Libraries package is unzipped.

Step 6: Add Server Certificate to Client's truststore

Use GET request to the cp/opm-service/api/v1/certs/server API to get the server's certificate.

Example

curl -k -X GET
https://10.225.120.1:30603/cp/opm-service/api/v1/certs/server
-H "Authorization: Bearer <JWT>"`

Response

-----BEGIN CERTIFICATE-----
MIID2DCCAsCgAwIBAgIUKE8w9p9gTAhgG8mXncKbXd7ip0YwDQYJKoZIhvcNAQEL
................................................................
...
-----END CERTIFICATE-----

Replace with the token that is obtained in Step 2 of Authentication and Authorization for Crosswork Planning REST API

Add the server certificate to client's truststore by append the server certificate to {CARIDEN_HOME}/etc/certs/ca_cert.pem.

Step 6: Using the certificates when writing RPC/OPM Python scripts

Once you have generated the certificates, use the cp/opm-service/api/v1/start API in a POST request to start the designapi service.

Example

curl -k -s -X POST https://10.225.120.1:30603/cp/opm-service/api/v1/start
-H 'Authorization: Bearer <JWT>'

Response

{
  "message": "DesignAPI daemon started successfully",
  "success": true
}

After starting the API service, scripts using the Design RPC/OPM Python libraries can connect to the designapid instance on the Crosswork Planning VM using the VM's IP address, port 30744, and the SSL protocol.

Example

import com.cisco.wae.design
import sys

plan_file = sys.argv[1]
host = sys.argv[2]
port = 30744
protocol = 'ssl'

with open(plan_file, 'rb') as f:
    conn = com.cisco.wae.design.ServiceConnectionManager.newServiceConnection(host, port, protocol)
    plan = conn.getPlanManager().newPlanFromBytes(f.read())
    for nodeKey, node in plan.getNetwork().getNodeManager().getAllNodes().items():
        print((node.getName()))