npm package: @itentialopensource/iag-device-onboarding
Description: Artifact to onboard a device onto IAG internal db
Author: Itential Artifacts
Latest version: 1.0.6-2023.1.0

# IAG Device Onboarding

## Table of Contents

- [IAG Device Onboarding](#iag-device-onboarding)
  - [Table of Contents](#table-of-contents)
  - [Overview](#overview)
  - [Supported IAP Versions](#supported-iap-versions)
  - [Getting Started](#getting-started)
    - [Prerequisites](#prerequisites)
    - [Capabilities](#capabilities)
    - [How to Install](#how-to-install)
    - [Testing](#testing)
  - [Using this Pre-Built](#using-this-pre-built)
    - [Input Schema](#input-schema)
    - [Output Schema](#output-schema)
  - [Additional Information](#additional-information)

## Overview

The **IAG Device Onboarding** pre-built provides the ability to onboard a list of devices onto an IAG instance through the IAG adapter.

_Estimated Run Time_: < 1 minute for single device


## Supported IAP Versions

Itential pre-builts are built and tested on particular versions of IAP. In addition, pre-builts that work with devices are often dependent on certain orchestration systems (e.g. NSO and IAG). As such, these pre-builts will have dependencies on these other systems. This version of the IAG Device Onboarding pre-built has been tested with:

- IAP 2023.1.x

## Getting Started

These instructions will help you get a copy of the pre-built in your local machine for testing in your environment. Reading this section is also helpful for deployments as it provides you with pertinent information on prerequisites and capabilities.

### Prerequisites

Users must satisfy the following prerequisites to install and run this pre-built:

- Itential Automation Platform
  - `^2023.1.x`
- Itential Automation Gateway
  - `^3.227.0+2023.1.15`
- An instantiated IAP IAG adapter

### Capabilities

- Ability to onboard a list of devices.
- Ability to onboard a list of device types (Currently only supports HTTP Request and Ansible device types).
- Ability to onboard a single device through operations manager.

### How to Install

To install this pre-built:

- Verify that you are running the documented [prerequisites](#prerequisites) in order to install the pre-built.

- Follow the instructions on the Itential Documentation site for [importing a pre-built](https://docs.itential.com/docs/importing-a-prebuilt-1).

### Testing

While Itential tests this pre-built and its capabilities, it is often the case the customer environments offer their own unique circumstances. Therefore, it is our recommendation that you deploy this pre-built into a development/testing environment in which you can test the pre-built.

## Using this Pre-Built

This pre-built can be run as a standalone automation or in a [childJob task](https://docs.itential.com/docs/childjob-1).

**Note:** The entry point workflow to this pre-built is called `IAGDO: Onboard Devices`. Use this worklow name if running the pre-built in a childJob task.

Running this pre-built depends on providing correct input so that the onboarding operations against the intended devices run as expected. The input to and possible outputs from this pre-built are described here.

**Note:** This pre-built can also be ran as an automation through Operations Manager. The Operations Manager automation to run this pre-built is called `IAGDO: Onboard With Form`. When onboarding an HTTP device through this form a user must pass properties for `params`, `data`, `headers`, `cookies`, `auth`, `timeout`, and `proxies` as JSON object to correctly pass these additional fields.

<img  src="./images/IAGDO_Onboard_With_Form.png"  alt="IAGDO Onboard With Form Image"  width="800px">

<img  src="./images/IAGDO_Onboard_With_Form2.png"  alt="IAGDO Onboard With Form Image"  width="800px">


### Input Schema

Ansible Device Onboarding:
```json
{
    "device": [
        {
            "deviceName": "Ansible_Test_Device",
            "inventoryType": "ansible",
            "iagAdapterInstance": "IAG-2021.2",
            "onboarding": {
                "ipaddress": "1.1.1.1",
                "port": "22",
                "user": "user",
                "password": "password",
                "device-type": "network_cli",
                "ostype": "ios",
                "become": "true",
                "become_method": "enable",
                "become_user": "user",
                "become_pass": "password"
            }
        }
    ],
    "options": {
        "verbose": false
    }
}
```

The following table details the property keys for an `Ansible Device`.

| key                             | type    | required | description                                              |
|---------------------------------|---------|----------|----------------------------------------------------------|
| device                          | array   | yes      | list of devices                                          |
| device.deviceName               | string  | yes      | device name                                              |
| device.inventoryType            | enum    | yes      | inventory type [anisble or http_requests]                |
| device.iagAdapterInstance       | string  | yes      | IAG adapter devices instance to onboard on               |
| device.onboarding               | object  | yes      | onboarding parameters                                    |
| device.onboarding.device-type   | string  | yes      | NSO instance                                             |
| device.onboarding.ipaddress     | string  | yes      | ip address                                               |
| device.onboarding.port          | string  | yes      | port                                                     |
| device.onboarding.ostype        | string  | no       | allows user to manually view and confirm job details     |
| device.onboarding.user          | string  | no       | user to become through privilege escalation              |
| device.onboarding.sshKey        | string  | no       | Private key file used by ssh                             |
| device.onboarding.password      | string  | no       | password used to authenticate to host                    |
| device.onboarding.become        | string  | no       | allow to force privilege escalation ("true" or "false")  |
| device.onboarding.become        | string  | no       | allows to force privilege escalation ("true" or "false") |
| device.onboarding.become_method | string  | no       | allows to set privilege escalation method                |
| device.onboarding.become_pass   | string  | no       | privilege escalation password                            |
| options                         | object  | yes      | additional options                                       |
| options.verbose                 | boolean | yes      | verbose                                                  |
| options                         | object  | yes      | additional options                                       |
| options.verbose                 | boolean | yes      | verbose                                                  |

The following table details the IAP vs Ansible Inventory type mapping.
For additional documentation related to Ansible inventory, please see the official <a href="https://docs.ansible.com/ansible/latest/inventory_guide/intro_inventory.html#connecting-to-hosts-behavioral-inventory-parameters">Ansible Inventory Guide</a>, and for additional documentation for IAP Ansible createDevice mapping, please see the offcial <a href="https://apidocs.itential.com/api/adapter-automation_gateway/createDevice/">createDevice</a> documentation.

| IAP Variable    | Anisble Variable             |
|-----------------|------------------------------|
| device-type     | ansible_connection           |
| ipaddress       | ansible_user                 |
| port            | ansible_port                 |
| ostype          | ansible_network_os           |
| user            | ansible_user                 |
| sshKey          | ansible_ssh_private_key_file |
| password        | ansible_password             |
| become          | ansible_become               |
| become_method   | ansible_become_method        |
| become_pass     | ansible_become_pass          |

HTTP Request Device Onboarding:
```json
{
    "device": [
        {
            "deviceName": "Http_Test_Device",
            "inventoryType": "http_requests",
            "iagAdapterInstance": "IAG-2021.2",
            "onboarding": {
                "base_url": "1.1.1.1:1/mgmt",
                "protocol": "https",
                "endpoint": "/tm/ltm/pool",
                "method": "",
                "params": {},
                "data": {},
                "headers": {},
                "cookies": {},
                "auth": {
                    "username": "user",
                    "password": "password"
                },
                "timeout": {},
                "allowRedirects": true,
                "proxies": {},
                "verify": false
            }
        }
    ],
    "options": {
        "verbose": false
    }
}
```

The following table details the property keys for a `HTTPRequests Device`.

| key                              | type    | required | description                                                                                                                                                                      |
|----------------------------------|---------|----------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| device                           | array   | yes      | list of devices                                                                                                                                                                  |
| device.deviceName                | string  | yes      | device name                                                                                                                                                                      |
| device.inventoryType             | string  | yes      | inventory type [anisble or http_requests]                                                                                                                                        |
| device.iagAdapterInstance        | string  | yes      | IAG adapter devices instance to onboard on                                                                                                                                       |
| device.onboarding                | object  | yes      | onboarding parameters                                                                                                                                                            |
| device.onboarding.base_url       | string  | yes      | The name of a base url to execute against                                                                                                                                        |
| device.onboarding.protocol       | string  | yes      | The name of the protocol used to communicate                                                                                                                                     |
| device.onboarding.endpoint       | string  | no       | The endpoint to append to the url built from your inventory/host                                                                                                                 |
| device.onboarding.method         | enum    | no       | Request method - one of GET, OPTIONS, HEAD, POST, PUT, PATCH, DELETE                                                                                                             |
| device.onboarding.params         | object  | no       | Keys/values to convert into the request's query string                                                                                                                           |
| device.onboarding.data           | object  | no       | Keys/values to send as the request's body                                                                                                                                        |
| device.onboarding.headers        | object  | no       | Keys/values to send as the request's HTTP headers                                                                                                                                |
| device.onboarding.cookies        | object  | no       | Keys/values to send as the request's cookies                                                                                                                                     |
| device.onboarding.auth           | object  | no       | Keys/values to send as the username and password for Basic Authentication                                                                                                        |
| device.onboarding.timeout        | string  | no       | The connect and read timeouts for the request. See <a href="https://docs.python-requests.org/en/latest/user/advanced/#timeouts">Request HTTP</a> documentation for more detatils |
| device.onboarding.allowRedirects | boolean | no       | A flag which enables or disables HTTP redirection                                                                                                                                |
| device.onboarding.proxies        | object  | no       | The keys/values which describe proxies to use for the request                                                                                                                    |
| device.onboarding.verify         | boolean | no       | A flag which enables or disables TLS certificate verification                                                                                                                    |
| options                          | object  | yes      | additional options                                                                                                                                                               |
| options.verbose                  | boolean | yes      | verbose                                                                                                                                                                          |

### Output Schema

The `ReturnStatus` job variable returned from the run pre-built reports the success or failure of the onboarding process for the list of devices provided to the pre-built. Below are example outputs of scenarios were a device does not exist on the IAG instance, a device does exist on an IAG instance, an invalid inventory type, and a failure with the Get Device Details child job.

Device Does Not Already Exist on IAG:

```json
{
  "ReturnStatus": {
    "details": [
      {
        "response": {
          "get_device": {
            "icode": "AD.500",
            "IAPerror": {
              "origin": "IAG-2021.2-connectorRest-handleEndResponse",
              "displayString": "Error 404 received on request",
              "recommendation": "Verify the request is accurate via debug logs and postman",
              "code": 404,
              "raw_response": {
                "status": "success",
                "code": 404,
                "headers": {
                  "server": "gunicorn/20.0.4",
                  "date": "Thu, 22 Dec 2022 15:29:28 GMT",
                  "connection": "close",
                  "content-type": "application/json;",
                  "content-length": "52",
                  "last-modified": "2022-12-22 10:29:28.511166",
                  "cache-control": "no-store, no-cache, must-revalidate, post-check=0, pre-check=0, max-age=0",
                  "pragma": "no-cache",
                  "expires": "-1",
                  "x-frame-options": "DENY",
                  "x-xss-protection": "1",
                  "x-content-type-options": "nosniff"
                },
                "response": "{\"code\": 404, \"status\": 404, \"message\": \"Not Found\"}",
                "redirects": 0,
                "tripTime": "38ms",
                "reqHdr": {
                  "Content-Type": "application/json",
                  "Accept": "application/json"
                }
              }
            },
            "metrics": {
              "code": 404,
              "timeouts": 0,
              "redirects": 0,
              "retries": 0,
              "tripTime": 38,
              "isThrottling": false,
              "capabilityTime": "172ms"
            },
            "response": {
              "code": 404,
              "status": 404,
              "message": "Not Found"
            }
          },
          "addDevice": {
            "name": "Ansible_Test_Device",
            "device-type": "network_cli",
            "ipaddress": "172.20.102.131",
            "port": "22",
            "ostype": "cisco-nx",
            "become": "true",
            "become_method": "enable",
          }
        },
        "device": "Ansible_Test_Device",
        "message": "Successfully onboarded device to IAG",
        "status": "SUCCESS",
        "errors": []
      }
    ],
    "errors": [],
    "number_failure": 0,
    "number_successfully_onboarded_devices": 1,
    "number_already_onboarded_devices": 0,
    "status": "SUCCESS",
    "number_success": 1,
    "message": "0 devices found already onboarded to IAG, 1 devices successfully onboarded to IAG, 0 devices failed to onboard to IAG"
  }
}
```

Device Already Found on IAG:

```json
{
  "ReturnStatus": {
    "details": [
      {
        "response": {
          "get_device": {
            "name": "Ansible_Test_Device",
            "inventory_type": "ansible",
            "device-type": "network_cli",
            "ipaddress": "1.1.1.1",
            "port": "22",
            "ostype": "cisco-nx",
            "become": "true",
            "become_method": "enable"
          }
        },
        "device": "Ansible_Test_Device",
        "inventory_type": "ansible",
        "message": "Device already exists on IAG",
        "status": "SUCCESS",
        "errors": []
      }
    ],
    "errors": [],
    "number_failure": 0,
    "number_successfully_onboarded_devices": 0,
    "number_already_onboarded_devices": 1,
    "status": "SUCCESS",
    "number_success": 1,
    "message": "1 devices found already onboarded to IAG, 0 devices successfully onboarded to IAG, 0 devices failed to onboard to IAG"
  }
}
```

Given Invalid Inventory Type:

```json
{
  "ReturnStatus": {
    "details": [
      {
        "response": {
          "get_device": "Invalid inventory type"
        },
        "device": "Ansible_Test_Device",
        "inventory_type": "anible",
        "message": "Invalid inventory type",
        "status": "FAILED",
        "errors": [
          {
            "message": "Invalid inventory type",
            "error_details": {}
          }
        ]
      }
    ],
    "errors": [],
    "number_failure": 1,
    "number_successfully_onboarded_devices": 0,
    "number_already_onboarded_devices": 0,
    "status": "FAILED",
    "number_success": 0,
    "message": "0 devices found already onboarded to IAG, 0 devices successfully onboarded to IAG, 1 devices failed to onboard to IAG"
  }
}
```

Get Device Details Error or Any Other Adapter Error:

```json
{
  "ReturnStatus": {
    "details": [
      {
        "response": {
          "get_device": "Cannot forward message to corral:IAG-2021.2"
        },
        "device": "Ansible_Test_Device",
        "inventory_type": "ansible",
        "message": "Cannot forward message to corral:IAG-2021.2",
        "status": "FAILED",
        "errors": [
          {
            "message": "Cannot forward message to corral:IAG-2021.2",
            "error_details": {}
          }
        ]
      }
    ],
    "errors": [],
    "number_failure": 1,
    "number_successfully_onboarded_devices": 0,
    "number_already_onboarded_devices": 0,
    "status": "FAILED",
    "number_success": 0,
    "message": "0 devices found already onboarded to IAG, 0 devices successfully onboarded to IAG, 1 devices failed to onboard to IAG"
  }
}
```

The following table details the property keys of the `ReturnStatus` output object:


| key                                                | type    | description                                                         |
|----------------------------------------------------|---------|---------------------------------------------------------------------|
| ReturnStatus.status                                | enum    | status of onboarding list of devices [SUCCESS, FAILED]              |
| ReturnStatus.errors                                | array   | list of errors encountered returned from running pre-built          |
| ReturnStatus.number_failure                        | integer | number of devices that failed to onboard                            |
| ReturnStatus.number_successfully_onboarded_devices | integer | number of successfully onboarded devices                            |
| ReturnStatus.number_already_onboarded_devices      | integer | number of already onboarded devices                                 |
| ReturnStatus.number_success                        | integer | number devices found already on IAG or successfully onboarded to IAG |
| ReturnStatus.message                               | string  | description of onboarding list of devices result                    |
| ReturnStatus.details[x].response.get_device        | object  | IAGGDD: Get Device Details Details childJob response                |
| ReturnStatus.details[x].response.add_Device        | object  | IAGDO: Onboard Device childJob response                             |
| ReturnStatus.details[x].device                     | string  | device name                                                         |
| ReturnStatus.details[x].message                    | string  | description of single device result                                 |
| ReturnStatus.details[x].status                     | string  | status of single device result [SUCCESS, FAILED]                    |
| ReturnStatus.details[x].errors                     | array   | list of errors encountered onboaring single device                  |

## Additional Information

Please use your Itential Customer Success account if you need support when using this pre-built.