VCF Automation 9.1 has two ways to build things, side by side, as two types of organisation. If you’ve come from Aria Automation, you’ll recognise one of them immediately. The other looks like Kubernetes because it is Kubernetes.

Choosing between them isn’t a matter of taste. They have genuinely different shapes, and some use cases are natural in one and awkward in the other.

I’ve now pushed the same list of requirements through both on a live VCF 9.1 lab. This is the comparison I wish I’d had at the start. Hindsight, as usual, turned up late.

The two shapes

VM Apps: Org, Project, Cloud Zone, Cloud Account, profiles, Cloud Template, then the IaaS engine drives vCenter, imperatively, with state in the IaaS database. All Apps: Org, CCI Project, Region, VPC, Supervisor Namespace, blueprint, then Supervisor controllers reconcile, declaratively, with state in etcd The same request, brokered on the left and declared on the right. The text versions below carry the detail.

VM Apps, the classic Aria Automation model:

Org ─ Project ─ Cloud Zone(s)
                   │
        Cloud Account (vCenter / NSX)
                   │
   flavor · image · network · storage profiles
                   │
   Cloud Template (formatVersion 1) ──▶ IaaS engine ──▶ vCenter API
        Cloud.vSphere.Machine, Cloud.NSX.Network, customization spec

Provisioning is imperative through a broker. The IaaS engine holds the vCenter session. The tenant references abstractions (flavors, image mappings) that resolve at request time. State lives in the IaaS database.

All Apps, supervisor-native, through the Cloud Consumption Interface:

Org ─ CCI Project ─ Region
          │
   VPC (tenant-created; overlapping privateIPs allowed)
          │   + VPCAttachment   + LoadBalancer (before the namespace!)
   Supervisor Namespace (spec.vpcName pins it)
          │
   Kubernetes objects reconciled by the Supervisor:
     VirtualMachine / VirtualMachineService / Subnet / BindingMap / VKS Cluster
          │
   Blueprint (formatVersion 2, CCI.Supervisor.*) → BlueprintVersion → Catalog

Provisioning is declarative. The blueprint states the desired objects, and the supervisor’s controllers make reality match them and keep it that way. State lives in etcd. Networking is NSX VPC-native.

Scorecard by use case

Every row below was actually built, not read about. It’s a slow way to fill in a table, but an honest one.

Use caseVM AppsAll Apps
Linux VM + softwareCloud.vSphere.Machine + cloudConfigVM Service VM + cloud-init (typed field)
Windows VMcustomization spec + software componentsbootstrap.sysprep; ISO attachable declaratively
ISO / CD-ROM attachday-2 edit in vCenterhardware.cdrom in the manifest
Multi-NICNICs across network profilesmultiple interfaces on VPC subnets; failover verified
Self-service catalogtemplate released to catalogblueprint → version → publish (one live version)
Load-balanced accessNSX LB via network profileVirtualMachineService → VPC LB VIP
Kubernetes clustersseparate TKG integrationnative Cluster object in the namespace
Identical isolated environmentshard: on-demand NAT nets, unique addressing usually forcednatural: VPC per pod, overlapping CIDRs, zero route between
Nested ESXi / VLAN networkstrunk portgroups on the physical vDS — a fabric changetrunk subnet + binding maps — no fabric change
Shared infra (WSUS, repos)shared segment routed everywhereone PrivateTGW subnet, one-way reachability
ExtensibilityvRO, ABX, event broker (rich)controllers, GitOps, kubectl (thinner day-2 today)
Deep per-device vSphere tuninganything vCenter can dowhat the VM Service API models

The two bold rows are the ones that decided it for me. Both are documented in this series. Both are genuinely hard in VM Apps, and simply the default in All Apps.

Where VM Apps still wins

Be fair to the incumbent:

  • Years of content. vRO workflows, ABX actions, template libraries and a mature day-2 action framework carry over unchanged. If you have an estate of them, that’s real value you’d be throwing away.
  • Deep vSphere reach. Anything vCenter can do to a VM (RDMs, per-device tuning, exotic customization), the IaaS engine can do, because it drives vCenter directly.
  • Familiar network model. Segments, portgroups, on-demand routed/NAT networks from a network profile. No new mental model.
  • Multi-cloud lineage. The same template idiom stretched to other endpoints.

The Windows Server 2025 pipeline elsewhere on this blog is a VM Apps build, and it’s a good one. It has Event Broker hooks for hostname allocation and placement metadata, cloudbase-init staging, and a reboot-safe state machine in the guest. Nothing about it needs rewriting, which, for a pipeline, is high praise.

Where All Apps wins, and why it’s structural

  • Declarative and self-healing. Desired state lives in etcd, and controllers reconcile to it. There’s no second database to drift from vCenter.
  • Structural multi-tenancy. A VPC per tenant is a hard NSX boundary, not an administrative one. Overlapping CIDRs are allowed, so cookie-cutter environments deploy side by side.
  • VMs and Kubernetes are one model. The same blueprint composes a VKS cluster, VMs, secrets and networking. It’s GitOps-able with ordinary tools.
  • VPC networking is first-class. Trunk subnets, binding maps, PrivateTGW, a per-VPC gateway firewall: none of it has a VM Apps equivalent.
  • Modern bootstrap. cloud-init and sysprep as typed API fields.

Where All Apps hurts today (all observed live)

  • Ordering matters, and the errors are opaque. The LB must exist before the namespace. New namespaces reject VMs until images sync. Blueprint validation has seven sharp edges, and I found every one of them by walking into it.
  • The tenancy layer is only partly blueprintable. VPC and VPCAttachment have blueprint types (CCI.VPC, CCI.VPC.Configuration). But there’s no LoadBalancer kind, and a blueprint-made VPC comes up with load balancing off. So all three go through the VPC API: scripted, not catalogued.
  • Two endpoints. The CCI proxy serves tenancy objects, and workload manifests go to the supervisor. You’ll hold two kubeconfigs.
  • Day-2 is thinner. There’s no event broker. Extensibility means controllers and GitOps, which is fine if that’s your team and a gap if it isn’t.

Recommendation

Default to All Apps for new build-outs. Every use case on the list is natural in the VPC model, including the two that are genuinely hard in VM Apps. And the whole estate is version-controlled YAML.

Keep VM Apps as the compatibility surface for existing vRA content, and for the rare thing that needs direct vCenter device manipulation. They coexist as organisations of different types on one platform. So migration is incremental, and nobody has to rewrite a working pipeline on a deadline.

And whichever you pick, codify the ordering rules into the scripts that provision tenancy. The sharp edges stay wrapped up in there, and the people requesting catalog items never meet them.

Why this matters outside the lab

Most customers arriving at VCF 9 have an estate of Aria Automation content, and a question: rewrite, coexist, or migrate? The answer above is the one we take into design workshops.

In practice it starts with an assessment:

  • which existing templates and workflows still earn their keep;
  • which use cases are genuinely better served by the VPC model;
  • where the boundaries sit.

Then comes a coexistence plan that moves workloads across opportunistically, not on a deadline. What makes that low-risk is the two architectures sharing one platform, as organisations of different types.

Rules learned

  • Two shapes, not two skins: imperative-through-a-broker vs declarative-reconciled. Pick per use case, not once for the estate.
  • All Apps is structurally better at isolation with identical addressing and nested/VLAN networks without fabric changes.
  • VM Apps is still the home for existing vRO/ABX content and deep vCenter device work.
  • All Apps’ pain is ordering, in this order: VPC, attachment, LB, namespace, subnets, image sync, then workloads. Script it once.
  • They coexist, so migrate opportunistically.

Broadcom documentation


Lab environment; opinions my own. Grounded in a VCF 9.1 / vSphere Supervisor with NSX VPC networking build-out; every row was deployed.