Manage a Cisco ACI Attachable Access Entity Profile (AAEP) — the access-policy glue (class
infraAttEntityP, DNuni/infra/attentp-{name}) between fabric interfaces and one or more domains — as a typed, secure-by-default building block targetingCiscoDevNet/aci ~> 2.20.
This module manages an ACI Attachable Access Entity Profile together with its domain bindings and its optional default access-generic container as one coherent, secure-by-default unit:
- 🧷 The AAEP (
aci_attachable_access_entity_profile.this) — the fabric access-policy object, addressed by the Distinguished Nameuni/infra/attentp-{name}, that lets a set of fabric interfaces "see" the domains bound to it. - 🔗 Typed domain relations — a
relation_to_domainslist binding the AAEP to one or more physical, VMM, L3, or Fibre Channel domains by DN (classinfraRsDomP), managed directly on the keystone. - 🗂️ An optional "default" access-generic container (
aci_access_generic.this, classinfraGeneric) — a singleton child some fabric configurations expect to exist explicitly; created only when requested. - 🏷️ The ACI metadata tail —
annotation(preserved asorchestrator:terraform),name_alias, anddescription, plusowner_key/owner_tagand theannotations/tagskey-value lists. - 🔑 Scope, not credentials — the AAEP is a fabric access-policy object with no parent DN; authentication and the APIC URL are the caller's provider concern and are never module variables.
💡 Why it matters: the AAEP is the pivot point of the access-policy model — every interface policy group that binds fabric ports to a domain does so through an AAEP. Getting its domain bindings right, and keeping them declarative and typed, is what lets VLAN pools and EPGs actually reach the wire.
If these Terraform modules have been helpful to you or your organization, I'd appreciate your support in any of the following ways:
- ⭐ Star this repository to help others discover this Terraform module.
- 🤝 Connect with me on LinkedIn: linkedin.com/in/microsoftexpert
- ☕ Buy me a coffee: buymeacoffee.com/microsoftexpert
Whether it's a star, a professional connection, or a coffee, every gesture helps keep these modules actively maintained and continually improving. Thank you for being part of the community!
graph LR
apic["Cisco APIC fabric (provider auth, out of band)"]:::ext
aaep["terraform-aci-attachable-access-entity-profile (this module)"]:::this
infra["aci_attachable_access_entity_profile - class infraAttEntityP - DN uni/infra/attentp-{name}"]:::keystone
pd["terraform-aci-physical-domain"]:::sib
vp["terraform-aci-vlan-pool"]:::sib
ipg["interface policy group modules"]:::sib
epg["terraform-aci-application-epg"]:::sib
apic -->|"provider configured by caller"| aaep
aaep -->|"manages"| infra
pd -->|"domain DN via relation_to_domains"| aaep
vp -->|"vlan_pool_dn (bound to the domain)"| pd
aaep -->|"attachable_access_entity_profile_dn"| ipg
ipg -->|"domain reachable via the AAEP"| epg
classDef this fill:#00BCEB,color:#fff,stroke:#00BCEB;
classDef keystone fill:#0D274D,color:#fff,stroke:#0D274D;
classDef sib fill:#f5f5f5,color:#333,stroke:#cccccc;
classDef ext fill:#eeeeff,color:#333,stroke:#9999ff;
The AAEP sits between the access-policy domain objects (physical/VMM/L3/FC domains, themselves bound to
VLAN pools) and the interface policy groups that attach fabric ports to it. It takes no parent DN — it
composes directly under uni/infra — and emits an id (its DN) that interface-policy-group modules
consume as attachable_access_entity_profile_dn.
graph TD
n["attachable_access_entity_profile.name (required, immutable)"]:::in
meta["annotation / name_alias / description / owner_key / owner_tag"]:::in
at["annotations / tags (key/value maps)"]:::in
rel["relation_to_domains (typed list, infraRsDomP)"]:::in
this["aci_attachable_access_entity_profile.this (keystone, infraAttEntityP)"]:::this
ag_in["access_generic (optional object)"]:::in
ag["aci_access_generic.this (for_each, 0-1, infraGeneric)"]:::child
oid["output: id (DN uni/infra/attentp-{name})"]:::out
onm["output: name"]:::out
oag["output: access_generic_dns"]:::out
n --> this
meta --> this
at --> this
rel --> this
this --> oid
this --> onm
ag_in --> ag
this --> ag
ag --> oag
classDef this fill:#00BCEB,color:#fff,stroke:#00BCEB;
classDef child fill:#00BCEB,color:#fff,stroke:#00BCEB;
classDef in fill:#f5f5f5,color:#333,stroke:#cccccc;
classDef out fill:#eeeeff,color:#333,stroke:#9999ff;
Resource inventory
| Resource | Name | Cardinality | Role |
|---|---|---|---|
aci_attachable_access_entity_profile |
this |
1 (keystone) | The AAEP (infraAttEntityP), with its typed domain relations. |
aci_access_generic |
this |
0-1 (for_each) |
The AAEP's singleton "default" access-generic container (infraGeneric), created only when requested. |
| Requirement | Value |
|---|---|
| Terraform | >= 1.3.0 (uses optional() object defaults) |
| Provider | CiscoDevNet/aci ~> 2.20 |
| Provider block | None in this module — the caller configures and authenticates the provider (username/password, X.509 signature, or login domain) out of band. |
| Scope | None — the AAEP is a fabric access-policy object under uni/infra (no parent DN). |
Schema notes that bite (verified against the live provider schema):
- 🔒
attachable_access_entity_profile.nameis immutable. Changing it forces replacement — a brand-new AAEP, and every interface policy group bound to it must be re-pointed. - ℹ️
aci_attachable_access_entity_profileis a migrated (plugin-framework) resource in this provider line.annotations,tags, andrelation_to_domainsare typed nested attributes — all assigned with=, not as HCLblock {}stanzas. ⚠️ Three ways exist to manage the sameinfraRsDomPrelationship — the keystone's typedrelation_to_domains, the standaloneaci_aaep_to_domain, and the standaloneaci_relation_from_attachable_access_entity_profile_to_domain. This module manages that relationship only through the keystone's typed attribute; do not also declare either standalone resource against an AAEP this module manages, or the two will fight over the same child object.- ℹ️
aci_relation_to_domainis not this module's relation. Its DN (uni/tn-{name}/ap-{name}/epg-{name}/rsdomAtt-[{tDn}]) and classfvRsDomAttshow it is the EPG-side domain binding, parented under an application EPG — it belongs to the application-EPG module, not the AAEP. - 🔒
aci_access_generic'snameis fixed to"default". The provider rejects any other value; this module hardcodes it and does not expose it as an input. - ℹ️
annotation(singular) andannotations(plural) are different fields.annotationis the single orchestrator marker (defaults toorchestrator:terraform);annotationsis the separate user-defined tagAnnotation list. This module manages both. - ℹ️
idis the DN (uni/infra/attentp-{name}), computed by APIC at create. It is the value downstream modules consume asattachable_access_entity_profile_dn. ⚠️ validate_relation_dn(provider defaulttrue) means arelation_to_domainsentry pointing at a domain that does not yet exist will fail at apply — create the domain first, or wire it by reference.
Scope the caller's APIC login to the least privilege this module needs:
- Create / delete an AAEP: the
access-adminrole (or a custom role with fabric access-policy write privilege), typically scoped to theallsecurity domain — access policies are fabric-wide constructs. - Referenced domains: read on every physical, VMM, L3, or Fibre Channel domain targeted by
relation_to_domains.
The module never sees a credential — authentication is a provider/caller concern supplied out of band (e.g. ACI_USERNAME / ACI_PASSWORD, or ACI_PRIVATE_KEY / ACI_CERT_NAME for signature-based auth).
- A reachable Cisco APIC (
ACI_URL) whose version is compatible with the~> 2.20provider, with the provider configured and authenticated by the caller. - In production, the provider should be configured with
insecure = falseand proper CA trust — the provider's own default (insecure = true, skip TLS verification) is not a safe steady state. - Any domain referenced by
relation_to_domainsmust exist (or be created in the same configuration) so the provider's DN validation passes. - No parent object is required — the AAEP is created directly under
uni/infra.
terraform-aci-attachable-access-entity-profile/
├── providers.tf # terraform{} + required_providers (aci ~> 2.20); no provider block
├── variables.tf # the AAEP object + the optional access_generic object — typed, secure defaults
├── main.tf # aci_attachable_access_entity_profile.this (keystone) + aci_access_generic.this (0-1)
├── outputs.tf # id (the DN) first, then name and access_generic_dns
├── README.md # this document
├── SCOPE.md # cross-module contract (scope, consumes/emits, roles, prerequisites)
├── LICENSE # MIT
└── .gitignore # canonical library ignore set
# The caller configures the provider (authentication is out of band).
provider "aci" {
# username / password, or private_key + cert_name for signature auth;
# url = "https://apic.example.com"; set insecure = false in production.
}
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
description = "AAEP for compute-cluster leaf ports"
}
}
output "aaep_dn" {
value = module.aaep.id # pass this as attachable_access_entity_profile_dn to interface-policy-group modules
}Consumes
| Input | Type | Typical source |
|---|---|---|
attachable_access_entity_profile |
object({...}) |
caller (name + metadata tail + typed domain relations, by DN) |
access_generic |
object({...}) or null |
caller (optional; the default access-generic container) |
Emits
| Output | Description | Consumed by |
|---|---|---|
id |
AAEP DN (uni/infra/attentp-{name}) — primary reference |
interface-policy-group modules (as attachable_access_entity_profile_dn), downstream access-policy composition |
name |
AAEP name | composition / audit |
access_generic_dns |
Map of access-generic key → DN, when created | audits / downstream reference |
1 · Minimal — an AAEP with secure defaults
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
}
}💡 The minimal call creates only the AAEP.
annotationis preserved asorchestrator:terraform, and no domain relation is created — nothing permissive by default.
2 · Description and GUI alias
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
name_alias = "Compute Hosts AAEP"
description = "Bound to the compute-cluster leaf interface policy groups"
}
}ℹ️
name_aliasis a display alias shown in the APIC GUI;nameremains the immutable identity encoded in the DN.
3 · A custom annotation marker
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
annotation = "orchestrator:terraform:platform-team"
}
}🔒 Keep the
orchestrator:terraformprefix so Terraform-managed objects stay identifiable in APIC. This suite defaultsannotationtoorchestrator:terraform; override it only to extend, not to erase, that marker.
4 · User metadata via the annotations (tagAnnotation) list
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
annotations = {
"cost-center" = "CC-4021"
"environment" = "production"
"owner" = "network-platform"
}
}
}ℹ️
annotationsis given as an ergonomic{ key = value }map and rendered as the ACItagAnnotation{key, value}list. Keys are unique by construction.
5 · Classification tags (tagTag) list
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
tags = {
"tier" = "gold"
"pci" = "in-scope"
}
}
}ℹ️
tagsmaps to the ACItagTaglist — use it for classification/labeling distinct from the free-formannotations.
6 · Ownership and correlation keys
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
owner_key = "cmdb-9931"
owner_tag = "provisioned-by-network-automation"
}
}ℹ️
owner_keyandowner_taglet external systems correlate this object with their own records — neither carries security posture.
7 · A single physical-domain binding
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
relation_to_domains = [
{ target_dn = "uni/phys-compute-physdom" }
]
}
}
⚠️ The referenced domain must exist (or be created in the same apply). With the provider'svalidate_relation_dndefault oftrue, a dangling relation fails at apply — fix the missing domain rather than disabling validation.
8 · Multiple domain bindings (physical + VMM)
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
relation_to_domains = [
{ target_dn = "uni/phys-compute-physdom" },
{ target_dn = "uni/vmmp-VMware/dom-compute-vds" },
]
}
}💡
relation_to_domainsis a plain list — bind as many domains as the fabric design needs from a single AAEP.
9 · Wiring a physical-domain module's DN into the AAEP
module "physical_domain" {
source = "git::https://github.com/microsoftexpert/terraform-aci-physical-domain.git?ref=v1.0.0"
physical_domain = { name = "compute-physdom" }
}
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
relation_to_domains = [
{ target_dn = module.physical_domain.id }
]
}
}💡 Reference a sibling domain module's
idoutput directly rather than hardcoding the domain DN.
10 · Creating the "default" access-generic container
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
}
access_generic = {
description = "Explicit default association container"
}
}ℹ️ Most fabrics never need this explicit object — domain relations are already managed on the keystone. Set
access_genericonly when your configuration specifically expects the "default" container to exist as its own managed object.
11 · A fully-annotated AAEP (all metadata)
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
name_alias = "Compute Hosts AAEP"
description = "Bound to the compute-cluster leaf interface policy groups"
owner_key = "cmdb-9931"
owner_tag = "network-automation"
annotations = { "cost-center" = "CC-4021", "environment" = "production" }
tags = { "tier" = "gold" }
relation_to_domains = [
{ target_dn = "uni/phys-compute-physdom" }
]
}
}12 · Least-privilege operating model (documentation variant)
# Configure the provider with a login scoped to access-policy management only —
# not a fabric-wide admin — for day-2 changes to an existing AAEP.
provider "aci" {
# username = "svc-access-admin" # an access-admin role
# private_key = var.apic_private_key # signature auth avoids login-rate limits
# cert_name = "terraform-cert"
# url = "https://apic.example.com"
# insecure = false
}
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = { name = "aaep-compute-hosts" }
}🔒 Access policies are fabric-scoped; scope automation logins to the
access-adminrole rather than a fabric-wideadminaccount. Prefer signature-based (X.509) auth for automation to avoid APIC login-rate thresholds.
13 · Many AAEPs from one definition (caller-side for_each)
locals {
aaeps = {
"compute" = { name = "aaep-compute-hosts", description = "Compute cluster leaf ports" }
"storage" = { name = "aaep-storage-hosts", description = "Storage cluster leaf ports" }
}
}
module "aaeps" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
for_each = local.aaeps
attachable_access_entity_profile = each.value
}
output "aaep_dns" {
value = { for k, m in module.aaeps : k => m.id }
}💡 Instantiate the module with
for_eachto manage a fleet of AAEPs from a single, auditable map.
14 · Reading outputs for downstream wiring
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = { name = "aaep-compute-hosts" }
}
output "aaep_dn" { value = module.aaep.id } # uni/infra/attentp-aaep-compute-hosts
output "aaep_name" { value = module.aaep.name }15 · 🏗️ End-to-end composition — physical domain → AAEP → interface policy group → EPG
provider "aci" {
# configured + authenticated by the caller; insecure = false in production
}
# 1) A VLAN pool for the compute domain's encapsulation range.
module "vlan_pool" {
source = "git::https://github.com/microsoftexpert/terraform-aci-vlan-pool.git?ref=v1.0.0"
vlan_pool = { name = "compute-vlans", allocation_mode = "static" }
ranges = { "100-199" = { from = "vlan-100", to = "vlan-199" } }
}
# 2) A physical domain bound to that VLAN pool.
module "physical_domain" {
source = "git::https://github.com/microsoftexpert/terraform-aci-physical-domain.git?ref=v1.0.0"
physical_domain = { name = "compute-physdom" }
}
# 3) The keystone AAEP, bound to the physical domain.
module "aaep" {
source = "git::https://github.com/microsoftexpert/terraform-aci-attachable-access-entity-profile.git?ref=v1.0.0"
attachable_access_entity_profile = {
name = "aaep-compute-hosts"
relation_to_domains = [
{ target_dn = module.physical_domain.id }
]
}
}
# 4) A tenant + EPG whose domain association reaches the fabric through the AAEP
# above (via the physical domain and the interface policy groups that bind it).
module "tenant" {
source = "git::https://github.com/microsoftexpert/terraform-aci-tenant.git?ref=v1.0.0"
tenant = { name = "core-prod" }
}
module "application_profile" {
source = "git::https://github.com/microsoftexpert/terraform-aci-application-profile.git?ref=v1.0.0"
tenant_dn = module.tenant.id
application_profile = { name = "payments" }
}
output "aaep_dn" { value = module.aaep.id }🏗️ The AAEP is the pivot between access policy (VLAN pool → domain → AAEP → interface policy group) and the tenant policy model (tenant → application profile → EPG → domain association). Every interface policy group that needs to reach this domain takes
module.aaep.idas itsattachable_access_entity_profile_dn.
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
attachable_access_entity_profile |
object({...}) |
✅ | — | The AAEP: name (required, immutable) plus the metadata tail and typed domain relations. |
access_generic |
object({...}) or null |
➖ | null |
The optional "default" access-generic container. |
Full input schema (from variables.tf)
variable "attachable_access_entity_profile" {
type = object({
name = string # REQUIRED, immutable (force-new), 1-64 chars
annotation = optional(string, "orchestrator:terraform") # ACI annotation marker (kept identifiable)
name_alias = optional(string, null) # GUI display alias
description = optional(string, null) # free-form description
owner_key = optional(string, null) # client correlation key
owner_tag = optional(string, null) # client correlation tag
annotations = optional(map(string), {}) # tagAnnotation {key,value} pairs as a {key = value} map
tags = optional(map(string), {}) # tagTag {key,value} pairs as a {key = value} map
relation_to_domains = optional(list(object({ # typed relation infraRsDomP, by domain DN
target_dn = string
annotation = optional(string, "orchestrator:terraform")
})), [])
})
# validation: name is 1-64 chars, matches ^[a-zA-Z0-9_.:-]+$, and every
# relation_to_domains[*].target_dn is non-empty
}
variable "access_generic" {
type = object({
annotation = optional(string, "orchestrator:terraform")
description = optional(string, null)
name_alias = optional(string, null)
})
default = null # null creates no access-generic container; name is hardcoded to "default" in main.tf
}| Output | Description | Notes |
|---|---|---|
id |
AAEP Distinguished Name (uni/infra/attentp-{name}) |
Primary cross-module reference — pass as attachable_access_entity_profile_dn. |
name |
AAEP name | For composition / audit. |
access_generic_dns |
Map of access-generic key → DN | Empty map unless access_generic is set. |
- One keystone, one optional singleton child.
aci_attachable_access_entity_profile.thisis the single resource that owns identity and domain relations;aci_access_generic.thisis afor_eachover a 0-or-1-entry map derived from the nullableaccess_genericinput — nevercount— so the resource exists only when the caller opts in. - Domain relations live on the keystone, not as separate resources. The migrated (plugin-framework) shape exposes
relation_to_domainsas a typed nested attribute directly onaci_attachable_access_entity_profile; this module wires the caller's typed list straight onto the keystone rather than also declaring the standaloneaci_aaep_to_domainoraci_relation_from_attachable_access_entity_profile_to_domainresources, which would manage the identical child object from a second place. aci_access_generic's name is fixed. The ACI object model constrains this child to the single name"default"; the module hardcodes it inmain.tfand does not expose it as a variable, so there is no invalid-name state to validate against.- Unmanaged when empty. When
annotations/tags/relation_to_domainsare empty the module passesnullrather than an empty list, so it never fights provider-computed state or produces a spurious diff. - Immutable identity.
attachable_access_entity_profile.nameis force-new: a rename destroys and recreates the AAEP. The twovalidationblocks reject names that violate the ACI length/character rules at plan time, not apply time. - Secure by omission. The minimal call preserves the
orchestrator:terraformannotation, binds no domains, and creates no access-generic container — nothing permissive is created by default.
| Concern | Secure default | How to opt out (deliberately) |
|---|---|---|
attachable_access_entity_profile.annotation |
orchestrator:terraform — Terraform-managed objects stay identifiable in APIC |
Extend the marker (e.g. add a team suffix); do not blank it. |
annotations / tags |
{} — no user metadata managed, no spurious diffs |
Populate the maps explicitly. |
relation_to_domains |
[] — no domain bound by default |
Add entries to bind physical/VMM/L3/FC domains by DN. |
access_generic |
null — no "default" container created |
Set it explicitly if your fabric configuration expects the container to exist. |
| Transport (provider) | This suite instructs callers to set insecure = false with CA trust |
The provider default is insecure = true; do not keep it as a steady state. |
| Secrets | None accepted or emitted | n/a — the AAEP carries no secret material; credentials are provider config. |
# From the module directory (offline, no credentials, no backend):
terraform init -backend=false
terraform validate
terraform fmt -check- Pin the module by immutable tag:
?ref=v1.0.0— never a branch. - This module is plan-only from the library's perspective. A human runs
terraform plan/applyagainst a sub-production APIC from their own pipeline, with a login scoped to the permissions above. No cloud apply happens here.
The offline proof gate for this module:
- ✅
terraform validate— parses the module, resolves theattachable_access_entity_profileandaccess_genericobject types, runs thenameandrelation_to_domainsvalidations, and confirms every argument exists in the provider schema. - ✅
terraform fmt -check— canonical formatting. - ⛔ Not exercised offline (only a real
plan/applyagainst an APIC covers these): DN validation ofrelation_to_domains(server-sidevalidate_relation_dn), APIC-side name-collision checks, and the computed DN returned asid.
$ terraform output
id = "uni/infra/attentp-aaep-compute-hosts"
name = "aaep-compute-hosts"
access_generic_dns = {}
| Symptom | Cause | Fix |
|---|---|---|
attachable_access_entity_profile.name must be 1-64 characters |
Name is empty or too long | Use a 1-64 character name. |
attachable_access_entity_profile.name may contain only letters, digits, and the characters _ . : - |
Name has spaces or unsupported characters | Remove spaces/special characters (ACI naming rules). |
Changing name wants to destroy/recreate the AAEP |
attachable_access_entity_profile.name is immutable (force-new) |
Treat a rename as a migration; expect the AAEP and its interface-policy-group bindings to need re-pointing. |
| Apply fails validating a domain relation | relation_to_domains[*].target_dn points at a domain that does not exist |
Create the domain first (or in the same apply); do not disable validate_relation_dn. |
Plan shows a conflicting change to the same infraRsDomP object from two resources |
A standalone aci_aaep_to_domain / aci_relation_from_attachable_access_entity_profile_to_domain resource was declared alongside this module's relation_to_domains |
Manage the relationship through relation_to_domains only; remove the standalone resource. |
Post ... 401 / authentication error |
Provider not configured or wrong credentials | Configure the aci provider with valid credentials and url; prefer signature auth for automation. |
| TLS verification error against the APIC | insecure = false (correct) but no CA trust |
Install the APIC's CA chain in the caller's trust store rather than reverting to insecure = true. |
- Cisco ACI provider —
aci_attachable_access_entity_profile - Cisco ACI provider —
aci_access_generic - Cisco ACI provider — provider configuration & authentication
- Cisco APIC object model — class
infraAttEntityP(the AAEP) and classinfraRsDomP(the AAEP-to-domain relation). - Sibling modules:
terraform-aci-physical-domain,terraform-aci-vlan-pool,terraform-aci-application-epg,terraform-aci-tenant. - This module's
SCOPE.md— the cross-module contract.
💙 "Infrastructure as Code should be standardized, consistent, and secure."