aci adapter

Features

The module allows to configure resources on aci. It can be used in two fashions:

  1. Using the generated resources: clearly typed resources, but only show a subset of aci capabilities –> aci::RelativeResource sub entities.

  2. Using generic resources: untyped resources, the structure of the resource is the responsibility of the module user –> aci::StandaloneResource.

Api configuration

Aci api is protected by authentication, the adapter needs to receive some authentication info in order to function properly. Mainly the adapter needs to know:

  1. Where the api is (what is the url?) –> aci::Api, base_url attribute

  2. Who should be managing resource on the api (username) –> aci::Api, username, or username_env_var attribute

  3. How can the user authenticate to the api (password) –> aci::Api, password, or password_env_var attribute

:bulb: For username and password, either the raw value or the environment variable should provided. If the environment variable is used, the value the attribute should receive is the name of the environment variable that the agent has access to, and in which the expected value (username or password value) can be found.

Usage example

Here are two equivalent models illustrating the usage of the module, using the generated resources and the generic ones.

  1. Generated resources:

import aci
import aci::pol
import aci::fv

api = aci::Api(
    name="api",
    base_url="https://192.168.26.200",
    username_env_var="ACI_API_USERNAME",
    password_env_var="ACI_API_PASSWORD",
    verify=false,
    retry_max_attempts=5,
    retry_interval=3,
)

tenant = aci::fv::Tenant(
    parent=aci::pol::Uni(parent=aci::Root(api=api, managed=false), managed=false),
    name="test",
    managed=false,
)

vrf = aci::fv::Ctx(
    parent=tenant,
    name="test",
    purged=false,
)

app = aci::fv::Ap(
    parent=tenant,
    name="test",
    purged=false,
)

bd = aci::fv::BD(
    parent=tenant,
    name="test",
    purged=false,
)

rs_ctx = aci::fv::RsCtx(
    parent=bd,
    tnFvCtxName=vrf.name,
    requires=[bd, vrf],
)

epg = aci::fv::AEPg(
    parent=app,
    name="test",
    descr="10",
    fvRsBd=aci::fv::RsBd(
        tnFvBDName=bd.name,
        requires=[epg, bd],
    ),
    fvRsPathAtt=aci::fv::RsPathAtt(
        tDn="topology/pod-1/paths-101/pathep-[eth1/5]",
        encap="vlan-11",
        requires=epg,
    ),
    requires=app,
)
  1. Generic resources

import aci

api = aci::Api(
    name="api",
    base_url="https://192.168.26.200",
    username_env_var="ACI_API_USERNAME",
    password_env_var="ACI_API_PASSWORD",
    verify=false,
    retry_max_attempts=5,
    retry_interval=3,
)

tenant = aci::StandaloneResource(
    api=api,
    mo_class_name="fvTenant",
    rn_format="tn-%(name)s",
    parent_dn="uni",
    attributes={
        "name": "test",
    },
    managed=false,
)

vrf = aci::StandaloneResource(
    api=api,
    mo_class_name="fvCtx",
    rn_format="ctx-%(name)s",
    parent_dn=tenant.dn,
    attributes={
        "name": "test",
    },
    requires=tenant,
    purged=false,
)

app = aci::StandaloneResource(
    api=api,
    mo_class_name="fvAp",
    rn_format="ap-%(name)s",
    parent_dn=tenant.dn,
    attributes={
        "name": "test",
    },
    requires=tenant,
    purged=false,
)

bd = aci::StandaloneResource(
    api=api,
    mo_class_name="fvBD",
    rn_format="BD-%(name)s",
    parent_dn=tenant.dn,
    attributes={
        "name": "test",
    },
    requires=tenant,
    purged=false,
)

rs_ctx = aci::StandaloneResource(
    api=api,
    mo_class_name="fvRsCtx",
    rn_format="rsctx",
    parent_dn=bd.dn,
    attributes={
        "tnFvCtxName": vrf.attributes["name"],
    },
    requires=[bd, vrf],
)

epg = aci::StandaloneResource(
    api=api,
    parent_dn=app.dn,
    rn_format="epg-%(name)s",
    mo_class_name="fvAEPg",
    attributes={
        "name": "test",
        "descr": "10",
    },
    requires=app,
)

rs_bd = aci::StandaloneResource(
    api=api,
    parent_dn=epg.dn,
    rn_format="rsbd",
    mo_class_name="fvRsBd",
    attributes={
        "tnFvBDName": bd.attributes["name"],
    },
    requires=[epg, bd],
)

static_port = aci::StandaloneResource(
    api=api,
    parent_dn=epg.dn,
    rn_format="rspathAtt-[%(tDn)s]",
    mo_class_name="fvRsPathAtt",
    attributes={
        "tDn": "topology/pod-1/paths-101/pathep-[eth1/5]",
        "encap": "vlan-11",
    },
    requires=[epg],
)