.. Reminder for header structure:
  Parts (H1)          : #################### with overline
  Chapters (H2)       : ******************** with overline
  Sections (H3)       : ====================
  Subsections (H4)    : --------------------
  Subsubsections (H5) : ^^^^^^^^^^^^^^^^^^^^
  Paragraphs (H6)     : """""""""""""""""""""

.. meta::
 :description: WAPT documentation version 2.7 Using the WAPT server APIs
 :keywords: API, Application Protocol Interface, WAPT, documentation

.. role:: green
   :class: green-text
.. role:: orange
   :class: orange-text
.. role:: red
   :class: red-text

.. _using__wapt_api:

##########################
Using the WAPT Server APIs
##########################


************
API Overview
************

.. note::

  This documentation does not describe all available :abbr:`APIs (Application Programming Interfaces)`. It focuses on the most useful ones.

Currently, it is only possible to use Python code to interact with the an :term:`API`.

Most of the available APIs can be found in the :file:`server.py` file located at :file:`/opt/wapt/waptserver/server.py` on Debian.

Additional APIs are available in other files such as :file:`enterprise.py`, :file:`repositories.py`, :file:`wads.py`, etc.

.. warning::

  Since version 2.5, most API URLs are protected with SSL client certificates. Therefore, it is no longer possible to use HTML requests like: `https://admin:MYPASSWORD@srvwapt.mydomain.lan/api/v1/hosts`.

**************
Using the APIs
**************

Requirement:
============
  
1- **Create a WAPT user and assign the ACL "launch requests"** (It is recommended to create a new user for requests because the password is included in the request).

  In the waptconsole : Go to :guilabel:`Server` > :guilabel:`Manage Wapt users and rights`.

  :guilabel:`New account` > :kbd:`F2` name like reporting. (1) & (2)

  :guilabel:`Change User password`. (3)

  Click on "Run Reports" ACL and click on "Allow". (4) & (5)
  
    .. figure:: wapt-resources/Create_reporting_user.png
      :scale: 75%
      :align: center
      :alt: Create reporting user

      Create reporting user.

2- Depending on the request, **it may be necessary to add ACLs on the reporting user**. This can be see in the request file You can see this in the request in the api source file.

  .. code-block::

    For Example: On server.py file, you can read this at the begin of the API's resquest groups.

      Example:
      @app.route('/api/v3/groups')
      @app.route('/api/v1/groups')
      @requires_auth(['admin','view']) Requires either the "admin" or "view" ACL (Access Control List) permissions. Having either one or both of these permissions is sufficient to access this endpoint.


Operating procedure:
====================


There are two primary method to do an api request, the **Command-Line Method** and the **Script-Based Method**.

**Any Wapt agent can launch an API**.

|

Command-Line Method
-------------------

The Command-Line Method involves executing API requests directly from the command line interface (CLI) using tools like cmd on Windows or bash on Unix-based systems.
This method is quick and efficient for simple or one-off requests.


Example: On a CLI or bash

.. code-block::

  wapt-get server-request "/api/v1/hosts" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

|

Script-Based Method
-------------------

The Script-Based Method requires creating a Python script (.py file) to define and execute the API request.
This method is more flexible and powerful, allowing for complex logic, error handling, and data processing.

.. tab-set::

  .. tab-item:: Windows

    1. Connect to a WAPT Windows agent.
    2. Create a directory named :file:`waptdev` at the root of your disk, like, `c:\\waptdev\\API_request`.
    3. Create a :file:`.py` file in this directory to edit the request, like, `api-1.py`.
    4. Copy the *python script* below and *personalize* the password for your user "reporting" and the desired API.
    5. Run the file with the following command: `&"C:\\Program Files (x86)\\wapt\\wapt-get.exe" c:\\waptdev\\API_request\\api-1.py`.
    6. The output can be displayed in CSV format: `cat api-1.csv`.

  .. tab-item:: Debian and Derivatives

    1. Connect to a WAPT Linux agent.
    2. Create a directory named :file:`waptdev` at the root of your disk, like, `/wapdev/`.
    3. Create a :file:`.py` file in this directory to edit the request, like, `api-1.py`.
    4. Copy the *python script* below and *personalize* the password for your user "reporting" and the desired API.
    5. Run the file with the following command: `/opt/wapt/wapt-get.bin /wapdev/api-1.py`.
    6. The output can be displayed in CSV format: `cat api-1.csv`.

  .. tab-item:: Red Hat and Derivatives

    1. Connect to a WAPT Linux agent.
    2. Create a directory named :file:`waptdev` at the root of your disk, like, `/wapdev/`.
    3. Create a :file:`.py` file in this directory to edit the request, like, `api-1.py`.
    4. Copy the *python script* below and *personalize* the password for your user "reporting" and the desired API.
    5. Run the file with the following command: `/opt/wapt/wapt-get.bin /wapdev/api-1.py`.
    6. The output can be displayed in CSV format: `cat api-1.csv`.


.. white_toggle::
  :titleen: The Python script
  :titlefr: Le Script Python

  .. code-block:: python

      import json
      import waptlicences
      import csv
      import sys
      sys.path.append('/opt/wapt')

      from common import Wapt
      WAPT = Wapt()
      ini_wapt_path = WAPT.config_filename

      user = "reporting"
      password = "[Enter the password for user reporting]"

      def run_report():
          auth_context = waptlicences.waptserver_login(ini_wapt_path, user=user, password=password)
          try:
              res = waptlicences.waptserver_request(ini_wapt_path, action='[enter the desired api like /api/v1/hosts]', auth_context=auth_context)
              if res['http_status'] == 200:
                  data = json.loads(res['content'])['result']

                  # Debugging: Print the raw data received from the API
                  print("Raw data from API:", json.dumps(data, indent=2))

                  # Check if data is not empty
                  if not data:
                      print("No data received from the API.")
                      return []

                  # Check if the first element of data is a list
                  if isinstance(data[0], list):
                      for row in data:
                          # Assuming row is a list of strings
                          for i, value in enumerate(row):
                              if isinstance(value, list):
                                  row[i] = '|'.join(value)

                      with open('test.csv', 'w', newline='', encoding='utf-8') as csvfile:
                          fieldnames = data[0]
                          writer = csv.writer(csvfile, delimiter=';')
                          writer.writerow(fieldnames)
                          writer.writerows(data[1:])  # Write the rest of the data
                  else:
                      print("Unexpected data format. First element is not a list.")
                      return []

                  return data
              else:
                  raise Exception('Request failed with status %s : %s' % (res['http_status'], res['content']))
          finally:
              waptlicences.waptserver_logout(ini_wapt_path)

      # Call the function and print the returned data
      data = run_report()
      print(repr(data))


Certificate, Signature and File Management
------------------------------------------

WAPT provides several commands for managing digital certificates, signing data, and verifying its integrity and authenticity. These features allow users to inspect the certificates used by WAPT, generate and verify digital signatures in JSON format, and check file integrity using cryptographic hashes. They also provide access to WAPT configuration files and enable the retrieval of remote resources.

The available commands are listed below:

.. list-table::
   :header-rows: 1
   :widths: 25 75

   * - Command
     - Description
   * - ``show-cert``
     - Display information about certificates.
   * - ``sign-json``
     - Action to sign a JSON file.
   * - ``check-json``
     - Verify the signature and integrity of JSON data.
   * - ``check-file-hash``
     - Verify the cryptographic hash of a file.
   * - ``.ini``
     - Display and access the configuration file used by WAPT.


*****************************
Some examples of api requests
*****************************

|

API V1
======

/api/v1/hosts
-------------

Get registration data of one or several hosts.

.. code-block::

  wapt-get server-request "/api/v1/hosts" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


List all hosts using the following parameters:

  * *reachable*;

  * *computer_fqdn* ==> computer_name;

  * *connected_ips*;

  * *mac_addresses*.

Example:

.. code-block::

  wapt-get server-request "/api/v1/hosts?columns=reachable,computer_fqdn,connected_ips,mac_addresses&limit=10000" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

/api/v1/groups
--------------

Get all dependencies that are directly assigned to a machine package.

.. code-block::

  wapt-get server-request "api/v1/groups" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


/api/v1/host_data
-----------------

|

**dmi field**

Get :abbr:`DMI (Desktop Management Interface)` info for a host:

.. code-block::

  wapt-get server-request "api/v1/host_data?uuid=[UUID OF THE COMPUTER]&field=[DMI FIELD DESIRED]" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


Example for the dmi field *"os_name"* :

.. code-block::

  wapt-get server-request "api/v1/host_data?uuid=CDAB699D-CA52-98B6-3AC2-749E66B04841&field=os_name" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

**installed_packages**

Option *installed_packages* will list all packages installed on a specific host.

Example: 

.. code-block::

  wapt-get server-request "api/v1/host_data?uuid=CDAB699D-CA52-98B6-3AC2-749E66B04841&field=installed_packages" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


**installed_softwares**

Option *installed_softwares* will list all softwares installed on a specific host.

Example: 

.. code-block::

  wapt-get server-request "api/v1/host_data?uuid=CDAB699D-CA52-98B6-3AC2-749E66B04841&field=installed_softwares" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

**wsusupdates**

Option *wsusupdates* will list all Windows Updates installed on a specific host.

Example: 

.. code-block::

  wapt-get server-request "api/v1/host_data?uuid=CDAB699D-CA52-98B6-3AC2-749E66B04841&field=wsusupdates" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

/api/v1/usage_statistics
------------------------

Get usage statistics from the WAPT Server.

.. code-block::

  wapt-get server-request "api/v1/usage_statistics" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

.. note::

  This API is useful if you have several WAPT Servers and you want to know how many hosts are there.

API V2
======

/api/v2/waptagent_version
-------------------------

Display :program:`waptagent.exe` version.

.. code-block::

  wapt-get server-request "/api/v2/waptagent_version" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

API V3
======

/api/v3/packages
----------------

List packages on the repository, retrieve the :file:`control` files of WAPT packages.

.. code-block::

  wapt-get server-request "/api/v3/packages" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


The following API commands can be used to manage packages in the WAPT Server repository:

* `search-package`: searches for packages available in the WAPT Server repository.
* `download-package`: downloads a package from the WAPT Server repository.
* `show-package`: displays information about a package.
* `edit-package`: downloads a package and opens it for editing.

These commands support filtering using the following options:

* `--this`: filters the results according to the capabilities of the current machine.
* `--locale`: filters packages by language.
* `--maturity`: filters packages by maturity level.
* `--target_os`: filters packages by target operating system.
* `--architecture`: filters packages by architecture.
* Keywords or `{package_uuid}` can be used to search for a specific package.

/api/v3/known_packages
----------------------

List all packages with last *signed_on* information.

.. code-block::

  wapt-get server-request "/api/v3/known_packages" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


/api/v3/trigger_cancel_task
---------------------------

Cancel a running task.

.. code-block::

  wapt-get server-request "/api/v3/trigger_cancel_task" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


/api/v3/get_ad_ou
-----------------

List :abbr:`OU (Organizational Unit)` seen by hosts and displayed in the WAPT Console.

.. code-block::

  wapt-get server-request "/api/v3/get_ad_ou" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


/api/v3/get_ad_sites
--------------------

List Active Directory sites.

.. code-block::

  wapt-get server-request "/api/v3/get_ad_sites" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

/api/v3/hosts_for_package
-------------------------

List hosts with a specific package installed.

.. code-block::

  wapt-get server-request "/api/v3/hosts_for_package?package=[name of your package like tis-paint]" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

/api/v3/ping
------------

Ping shows a general set of informations on a WAPT Server.

Example:

.. code-block::

  wapt-get server-request /api/v3/ping -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password

/api/v3/reporting_exec
----------------------

Below is a python script that executes a query with a specific id from WAPT Console Reporting tab. In this script, user "reporting" should have "Run reports" ACL.
It works on every platform (windows, linux and mac agents).

.. white_toggle::
  :titleen: The Python script
  :titlefr: Le Script Python

  .. code-block:: python

    import os
    import json
    import logging
    import waptlicences
    import requests
    import sys
    sys.path.append('/opt/wapt')
    from common import get_requests_client_cert_session
    from common import Wapt



    WAPT = Wapt()
    ini_wapt_path = WAPT.config_filename
    w = Wapt(config_filename=ini_wapt_path)

    # WAPT Conf
    wapt_url = w.waptserver.server_url

    user = "reporting"
    password = "password"


    def run_report():

        t = waptlicences.waptserver_login(ini_wapt_path,user,password)
        session = get_requests_client_cert_session(wapt_url,
        cert=(t['client_certificate'],t['client_private_key'],t['client_private_key_password']),
        verify=w.waptserver.verify_cert
        )
        if not 'session' in t['session_cookies']:
          session_cookies = [u for u in t['session_cookies'] if u['Domain'] == WAPT.waptserver.server_url.split('://')[-1]][0]
        else:
          session_cookies = t['session_cookies']['session']
          session_cookies['Name'] = 'session'

        session.cookies.set(session_cookies['Name'], session_cookies['Value'], domain=session_cookies['Domain'])
        t= None


        url = f'{wapt_url}/api/v3/reporting_exec?id=19'
        response = session.get(url)
        data = response.json()

        return data['result']



    print(run_report())

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

.. Danger::

   **A few examples of APIs using the post method**.

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


/api/v3/change_password
-----------------------

Change the Admininistrator password [only this account].
The request is a python dictionnary *{}* with keys:

* *user*;

* *old_password*;

* *new_password*.

Example:

.. code-block::

  wapt-get server-request /api/v3/change_password --method=POST --data="{'user':'USER','password':'old_password',''new_password':'new_password'}"

/api/v3/hosts_delete
--------------------

Delete hosts with specific uuid.
Requires admin or unregister_host ACL.

.. code-block:: bash

  wapt-get server-request /api/v3/hosts_delete --method=POST --data="{'uuids': ['f76f1c44-ba82-714b-9241-5ad0ed671cb1', 'f76ffgh4-ba82-714b-9241-5ad0dfdfe1rt6'], 'delete_packages': 'True', 'delete_inventory': 'True'}"  --wapt-server-user=admin --wapt-server-passwd=password


/api/v3/packages_delete
-----------------------

Delete package with a precise version.
The request is a python list *[]*.
A list of packages may be given, separated by commas *,*.

Example:

.. code-block:: bash

  wapt-get server-request /api/v3/packages_delete --method=POST --data="['ht-wapt-debian-gui_2.6.0.16977-2_0fce3ca2b61ebdbdc9b4b065cfe87176_PROD.wapt']" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


/api/v3/trigger_wakeonlan
-------------------------

If hosts are WakeOnLan enabled, this API is useful.

Syntax is :file:`--data-raw`: a dictionnary with key *uuids* and a list of host uuids.

Example:

.. code-block::
  
  wapt-get server-request /api/v3/trigger_wakeonlan --method=POST --data="{'uuids':['C74B68E2-CB63-BC4D-B6DB-74110DD4E535']}" -c /opt/wapt/wapt-get.ini --wapt-server-user=user --wapt-server-passwd=password


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

.. Danger::

   **Example of APIs using the delete method**.

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

/api/v3/delete_unused_driver_files
----------------------------------

Example:

.. code-block:: bash
  
  wapt-get server-request /api/v3/delete_unused_driver_files --wapt-server-user=user --wapt-server-passwd=password --method=DELETE