Skip to content

APIC

This guide shows how to use the CiscoAPIC client to interact with Cisco Application Policy Infrastructure Controller (APIC) APIs.

Tip: The APIC API supports both JSON and XML formats, and so does the client. You can use whichever format best fits your workflow.


Connect to APIC

Connect to APIC (JSON or XML)
from wingpy import CiscoAPIC

apic = CiscoAPIC(
    base_url="https://apic.example.com", # (1)!
    username="admin", # (2)!
    password="password", # (3)!
    verify=False,
)
  1. Environment variable:
    WINGPY_APIC_BASE_URL
    
  2. Environment variable:
    WINGPY_APIC_USERNAME
    
  3. Environment variable:
    WINGPY_APIC_PASSWORD
    

Get All Tenants

The apic.get_all() method retrieves all items from a paginated endpoint, handling pagination for you. This is useful for large datasets.

tenants = apic.get_all("/api/class/fvTenant.json")
for tenant in tenants:
    print(tenant)
tenants_xml = apic.get_all("/api/class/fvTenant.xml")
for tenant_elem in tenants_xml:
    print(tenant_elem.tag, tenant_elem.attrib)

Create a Tenant

Use the post method to create a new tenant. You can use either JSON or XML format for the request body, as the client looks the "extension" of the URL to determine the format.

tenant_data = {
    "fvTenant": {
        "attributes": {"name": "TestTenant"}
    }
}
response = apic.post(
    "/api/mo/uni/tn-TestTenant.json",
    data=tenant_data,
)
print(response.json())
from lxml.etree import Element, SubElement

tenant_elem = Element("fvTenant", name="TestTenant")
response = apic.post(
    "/api/mo/uni/tn-TestTenant.xml",
    data=tenant_elem,
)
print(response.status_code)

Update a Tenant

You can update an existing tenant using the patch method. Again, you can choose between JSON or XML format.

update_data = {
    "fvTenant": {
        "attributes": {"descr": "Updated description"}
    }
}
response = apic.patch(
    "/api/mo/uni/tn-TestTenant.json",
    data=update_data,
)
print(response.status_code)
from lxml.etree import Element

update_elem = Element("fvTenant", descr="Updated description")
response = apic.patch(
    "/api/mo/uni/tn-TestTenant.xml",
    data=update_elem,
)
print(response.status_code)

Delete a Tenant

response = apic.delete(
    "/api/mo/uni/tn-TestTenant.json"
)
print(response.status_code)
response = apic.delete(
    "/api/mo/uni/tn-TestTenant.xml"
)
print(response.status_code)

Get a Single Tenant

You can retrieve a single tenant by specifying its distinguished name (DN) in the path. Both JSON and XML formats are supported.

rsp = apic.get("/api/mo/uni/tn-TestTenant.json")
data = rsp.json()
print(data["imdata"][0]["fvTenant"]["attributes"])
rsp = apic.get("/api/mo/uni/tn-TestTenant.xml")
from lxml.etree import fromstring
xml_data = fromstring(rsp.content)
print(xml_data[0].attrib)

Get All EPGs for a Tenant (with Pagination)

You can use query parameters to fetch all EPGs (Endpoint Groups) for a tenant, and the client will handle pagination for you.

app_path = "/api/mo/uni/tn-TestTenant/ap-App.json"
params = {
    "query-target": "children",
    "rsp-subtree": "children",
    "rsp-subtree-class": "fvAEPg",
}
epgs = apic.get_all(app_path, params=params, page_size=4)
print(len(epgs))
app_path = "/api/mo/uni/tn-TestTenant/ap-App.xml"
params = {
    "query-target": "children",
    "rsp-subtree": "children",
    "rsp-subtree-class": "fvAEPg",
}
epgs_xml = apic.get_all(app_path, params=params, page_size=4)
print(len(epgs_xml))