Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pyaoscx V2 Update #4

Merged
merged 3 commits into from
Jun 4, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 9 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,18 +1,24 @@
# pyaoscx

These modules are written for AOS-CX API v1 and v10.04. These scripts are written for devices running AOS-CX firmware version 10.04.
These modules are written for AOS-CX API v1 and v10.04. These scripts are written for devices running AOS-CX firmware
version 10.04 or greater.

For this initial release, it is recommended to use the v1 AOS-CX API. See the Release Notes for more information.
See the [Release Notes](RELEASE-NOTES.md) for more information.

Please note that pyaoscx v2 is **not** backwards compatible for pyaoscx v1 and earlier, so please specify the correct
version when using pyaoscx in requirements.txt files

## Structure
Detailed information about the structure and design can be found in the [Design document](pyaoscx/DESIGN.md).

* REST API call functions are found in the modules in /pyaoscx.
* REST API call functions are combined into other functions that emulate low-level processes. These low-level process functions are also placed in files in /pyaoscx.
* Functions from the /pyaoscx files (API functions and low-level functions) are combined to emulate larger network configuration processes (workflows). These workflow scripts stored in the /workflows folder.


## How to contribute

Please see the accompanying CONTRIBUTING.md file for guidelines on how to contribute to this repository.
Please see the accompanying [CONTRIBUTING.md](CONTRIBUTING.md) file for guidelines on how to contribute to this repository.

## Git Workflow

Expand Down
32 changes: 32 additions & 0 deletions RELEASE-NOTES.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,35 @@
# 2.0.0

## Notable Changes
**WARNING: V2 is NOT backwards compatible with v1 and earlier**
* Huge overhaul of the design - the libraries now use factories in order for the code to be more object oriented.
Please read the [Design document](pyaoscx/DESIGN.md) file for more information.
* Removed previous workflow examples (defunct) and added /workflows/workflow.py as an example for using the new design
* Added directories for supporting files in /rest/v1 and /rest/v10_04
* Most of the previous libraries have been updated, but there are unsupported modules that are pending updates below:
* ARP
* Common_ops
* EVPN
* LLDP
* Loop Protect
* MAC
* NAE
* QoS
* System
* VXLAN
* Additionally, a few libraries have been migrated into other libraries:
* bgp.py is now split between bgp_router.py and bgp_neighbor.py
* config. py is now configuration.py
* dhcp.py is now dhcp_relay.py
* lag.py is now integrated into interface.py
* ospf.py is now split between ospf_area.py, ospf_interface.py, and ospf_router.py


# 1.0.0

## Notable Changes
* Made changes to setup.py to update the PyPi information

# 0.3.0

## Notable Changes
Expand Down
131 changes: 131 additions & 0 deletions pyaoscx/CONTRIBUTING.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
# Contribution Guidelines

If you're reading this, you're probably thinking about contributing to this repository. We really appreciate that--thank you!

This document provides guidelines on contributing to this repository. Please follow these guidelines when creating issues, making commits, and submitting pull requests. The repository maintainers review all pull requests and verify that they conform to these guidelines before approving and merging.

#### Table Of Contents
[How Can I Contribute?](#how-can-i-contribute)
* [Contribution Ideas](#contribution-ideas)
* [What should I know before I get started?](#what-should-i-know-before-i-get-started)

[Licensing](#licensing)
* [Developer's Certificate of Origin](#developers-certificate-of-origin)
* [Sign Your Work](#sign-your-work)

[Coding Conventions](#coding-conventions)

[Additional Notes](#additional-notes)
* [Resources](#resources)

## How Can I Contribute?

### Contribution Ideas

1. Raise issues for bugs, features, and enhancements.
1. Submit updates and improvements to the documentation.
1. Submit articles and guides, which are also part of the documentation.
1. Help out repo maintainers by answering questions in [Airheads Developer Community][airheads-link].
1. Share feedback and let us know about interesting use cases in [Airheads Developer Community][airheads-link].

### What should I know before I get started?

The best way to directly collaborate with the project contributors is through GitHub.

* If you want to raise an issue such as a defect, an enhancement request, feature request, or a general issue, please open a GitHub issue.
* If you want to contribute to our code by either fixing a problem, enhancing some code, or creating a new feature, please open a GitHub pull request against the development branch.
> **Note:** All pull requests require an associated issue number, must be made against the **development** branch, and require acknowledgement of the DCO. See the [Licensing](#licensing) section below.

Before you start to code, we recommend discussing your plans through a GitHub issue, especially for more ambitious contributions. This gives other contributors a chance to point you in the right direction, give you feedback on your design, and help you find out if someone else is working on the same thing.

It is your responsibility to test and verify, prior to submitting a pull request, that your updated code doesn't introduce any bugs. Please write a clear commit message for each commit. Brief messages are fine for small changes, but bigger changes warrant a little more detail (at least a few sentences).
Note that all patches from all contributors get reviewed.
After a pull request is made, other contributors will offer feedback. If the patch passes review, a maintainer will accept it with a comment.
When a pull request fails review, the author is expected to update the pull request to address the issue until it passes review and the pull request merges successfully.

At least one review from a maintainer is required for all patches.

### Contribution Guidelines
This repo is maintained on a best-effort basis. The burden is on the submitter and not the repo maintainers to ensure the following criteria are met when code is submitted.
1. All code submissions must adhere to the structure of the repo:
* Lower-level functions and API calls must be saved in the /pyaoscx folder.
* High-level process-focused functions must be saved in the /workflows folder.
* Do not create new separate folders for submitted projects.
* Do not make copies of existing files to be saved in different folders.
* The objective is that all submissions build on the repo as a whole, rather than creating multiple sub-projects housed in the repo.
2. All Python code should conform to PEP-8 standards. The maintainers use Pycharm IDE to perform this check. That does not require submitters to use Pycharm, but regardless of the code editor used, the PEP-8 check must be successful.
3. All functions should have explanatory docstrings using the reStructuredText format.
4. All workflows should have a comment at the top explaining the configuration steps the workflow performs, and any preconditions that need to be met before running the script.
5. All git commits should have clear, concise messages which explain the changes made in the commit. All Pull Requests (PRs) should contain a title and comments that explain the impact of the PR.
6. All code submitted for merge consideration must be tested by the submitter.

## Licensing

All contributions must include acceptance of the DCO:

### Developer’s Certificate of Origin

> Developer Certificate of Origin Version 1.1
>
> Copyright (C) 2004, 2006 The Linux Foundation and its contributors. 660
> York Street, Suite 102, San Francisco, CA 94110 USA
>
> Everyone is permitted to copy and distribute verbatim copies of this
> license document, but changing it is not allowed.
>
> Developer's Certificate of Origin 1.1
>
> By making a contribution to this project, I certify that:
>
> \(a) The contribution was created in whole or in part by me and I have
> the right to submit it under the open source license indicated in the
> file; or
>
> \(b) The contribution is based upon previous work that, to the best of my
> knowledge, is covered under an appropriate open source license and I
> have the right under that license to submit that work with
> modifications, whether created in whole or in part by me, under the same
> open source license (unless I am permitted to submit under a different
> license), as indicated in the file; or
>
> \(c) The contribution was provided directly to me by some other person
> who certified (a), (b) or (c) and I have not modified it.
>
> \(d) I understand and agree that this project and the contribution are
> public and that a record of the contribution (including all personal
> information I submit with it, including my sign-off) is maintained
> indefinitely and may be redistributed consistent with this project or
> the open source license(s) involved.

### Sign Your Work

To accept the DCO, simply add this line to each commit message with your
name and email address (`git commit -s` will do this for you):

Signed-off-by: Jane Example <[email protected]>

For legal reasons, no anonymous or pseudonymous contributions are
accepted.

## Coding Conventions

1. Python code should conform to PEP-8. PyCharm editor has a built-in PEP-8 checker.
1. Since this is a collaborative project, document your code with comments that will help other contributors understand the code you write.
1. When in doubt, follow conventions you see used in the source already.

## Additional Notes

> **Note:** Please don't file an issue to ask a question. Please reach out to us via email or disucssion forums.

### Resources

| Resource | Description |
| --- | --- |
| [Airheads Developer Community][airheads-link] | Aruba Airheads forum to discuss all things network automation. |
| [Aruba Bots Automate Videos][aruba-bots-playlist-link]| YouTube playlist containing instructional videos for Ansible and Python automation repositories. |
| [[email protected]][email-link] | Distribution list email to contact the switching automation technical marketing engineering team. |


[airheads-link]: https://community.arubanetworks.com/community-home?CommunityKey=ea467413-8db4-4c49-b5f8-1a12f193e959
[aruba-bots-playlist-link]: https://www.youtube.com/watch?v=_QxwUiXkJpA&list=PLsYGHuNuBZcY02FUh95ZpOB5VFkPurVaX
[email-link]: mailto:[email protected]
180 changes: 180 additions & 0 deletions pyaoscx/DESIGN.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,180 @@
# pyaoscx

## Overview

The pyaoscx (a.k.a. AOS-CX Python SDK) is a framework created to ease the access to
the Aruba switches running AOS-CX, using the REST API interface. The framework is
not intended to be a Network Management System (NMS). Instead, it is meant to
provide functions and classes to perform basic operations on the devices,
including the following:

1. Handling the session and remote connection.
1. Handling the allowed operations depending on their capabilities.
1. Handling the responses depending on the API version.
1. Basic data validation.
1. Raising meaningful errors.

And, also, if needed:

1. Caching data.
1. Handling notifications.

## Design drivers

pyaoscx uses the object-oriented approach. Instead of having separate modules to
perform specific operations, it connect several features together to represent
the operational state of the switch. Such pattern allows the client to keep track
of the switch configuration in its internal data structures.


Every single feature must be represented in a class. Such a class may or may not
be contained in another class or a collection. For example, the `Interface`
represents a specific Interface, and it may contain references to other `VLANs`, `VRFs`,
and depending on the use case, the `VSF` or `VSX` configuration. Also, an
`Interface` may be represented as a `LAG`, meaning that it may contain
references to more than a single physical port.

### pyaoscx Modules
Each pyaoscx module is defined as a Python Class, in which it contains method
definitions to generate and manage a module through REST API call or multiple
REST API calls. All module creation is managed through a flag attribute materialized.
This attribute will be True if the module exists within the Switch Device, False otherwise.
This will be updated whenever a POST or GET called is done.

Each pyaoscx Module has a list of important attributes besides materialized:
* session: use to make the HTTP requests, among other things.
* config_attrs: list of attributes writable to each specific object
* original_attributes: dictionary with object information and attributes right
after performing a GET request.
* modified: Flag to verify if object was modified, in case it was not the PUT
request is not made.

### Materialized objects

The attributes for a local object in the SDK may not match the current configuration on the switch.
Creating a local object in the SDK does not mean the object was created in the device.
The internal attributes can be filled with _artificial_ data, which cannot be
considered _materialized_ unless the object was retrieved from the device with
a __get__ operation, or the object was created with a __create__ operation.

### Operations

REST API allows a well-known list of HTTP verbs. They must be mapped to class-
specific operations to keep the same behavior along this SDK.

#### Get

This method maps to the HTTP GET verb. It allows to retrieve the data from the
device, converting the JSON response into the corresponding internal attributes
of the object. Object attributes must match 1:1 with the device information.

#### Create

This method maps to the HTTP POST verb. It retrieves a list of attributes from
the object known as writable attributes, creating a body for the
POST request.

#### Update

This method maps to the HTTP PUT verb. Just as the CREATE, retrieves a list of
attributes from the object known as writable attributes. The difference
is the UPDATE methods makes a PUT Request. It's important to know that this method
is executed only if the object is materialized.

##### NOTIFICATIONS

#### Set

Given that the REST API does not provide support to the HTTP PATCH verb yet, all
the operations to change the device configuration must use the HTTP PUT verb.
It means that the the original attributes must be retrieved first, then change
the values required, and finally perform the change. This operation cannot be
performed on an unmaterialized object.


### Session management

In order to perform any operation in the device, a connection must be
established. The session is an object representing it. It keeps the credential
information, such as `username` and `password`, and, once established, it also
keeps the session cookie. There is an assumption that all the operations
performed should be done with the same REST API version. Therefore, the session
also contains the version the client wants to use.

The session state must be validated every time an operation must be performed.
Therefore, using a Python decorator is the suggested approach.

However, in order to prevent using a _global accessible object_ representing
the session, and passing it as a parameter in every call, the SDK objects may
receive the session object as _mandatory parameter_ in the constructor.

### Factory Pattern

The REST API request and responses vary depending on the version. It means that
the internal structure of the payload changes, and the SDK must take care of it.
A Factory class is used to create new objects -- both python objects and modules
inside a switch AOS-CX Device.

If a module is created using the pyaoscx Factory, it's going to be set with the given
state in each creation method.

## Main classes

### Session

The session class keeps the connection parameters. When a connection is established,
it also records the session cookie and the last time the connection was used, which
can help to identify whether the session is still valid because of the idle time.
The following fields will be required to store the main session information:

* Username
* Password
* Cookie
* API version
* Last operation timestamp

### API

Represents the API version used. Keeps all the important information
for the version and the methods related to it:

* release date
* version number
* default selector
* default depth


### Device

This class identifies the switch. It keeps all the basic internal parameters
which defines the device identity, like serial number and name, but, most importantly,
the device's capacities and capabilities. The latter parameters allow to decide
what kind of operations can be performed on a switch, given some features are
available on a certain family of devices.

* Name
* Serial
* Capacities
* Capabilities

### Configuration

This class represents a Device's configuration and all of its attributes. It's used to
configure the device, get full config structure, backup configuration, among other things.


### Error handling

Leveraging the Python infrastructure, the exceptions are the best
mechanism to handle the errors. An exception may report internal details
about the issue found, by returning error codes and descriptive error strings.

The following hierarchical organization will help classify the possible errors,
and, furthermore, let the SDK client know what exactly happened when calling
a function.

#### Exceptions

1. GenericOperationError
2. ResponseError
3. VerificationError
Loading