With the VCF 3.9.1 release, support for hosts with multiple physical NICs has been added. This allows you to dedicate specific traffic across specific physical NICs to conform to your best practices. Let’s take a quick look at how this is configured…
By default, VCF will use the first two physical NICs (vmnic0 and vmnic1) on a host for all traffic. When working with a host with multiple physical NICs, you will need to define what the physical NICs are connected to (VDS or N-VDS). The VDS or N-VDS will need to exist, of course.
Currently, the VCF API has to be used in order to create a workload domain with hosts using multiple physical NICs. The same applies to related operations, such as creating a cluster in a workload domain or adding a new host with multiple physical NICS.
To help explain how to do this, let’s use the scenario that we need to create a new workload domain comprised of hosts with multiple physical NICs. The workload domain will be based on NSX-V and will leverage two VDS named SDDC-Dswitch-Private1 and SDDC-Dswitch-Private2. The two VDSs will be created automatically as part of the workload creation workflow.
Two physical NICs from each host will be assigned to each VDS. This means vmnic0 and vmnic1 will be assigned to the first VDS and vmnic2 and vmnic3 will be assigned to the second VDS.
First, we need to commission the hosts. This process is the same that would be followed if the host only had two physical NICs.

Once the host is commissioned, you need to verify that the license keys you intend to use for each host are entered into the SDDC Manager.
Next, we need to obtain the IDs for each of the hosts that are intended to be used in the workload domain. At this point, the hosts should be commissioned, but unassigned. Logging into the SDDC Manager, we can use the API call to get this information:
root@sddc-manager [ ~ ]# curl -k https://sddc-manager.vcf.sddc.local/v1/hosts?status=UNASSIGNED_USEABLE -u ‘admin:VMware123!’ -X GET -H ‘accept: application/json’ | json_pp
Of course, you would want to change the URL and the password information to match your environment.

This command can generate a bit of output, but we are just interested in the ID. It’s a good idea to ensure you are using the desired hosts as well.
Once you have the IDs for all of the hosts, you can then create a JSON formatted file which we will use for the payload information. This is a example of what that file would look like.
{
"domainCreationSpec":{
"domainName":"WLD-1",
"vcenterSpec":{
"name":"wld-vcenter",
"networkDetailsSpec":{
"ipAddress":"10.0.0.30",
"dnsName":"wld-vcenter.vcf.sddc.local",
"gateway":"10.0.0.1",
"subnetMask":"255.255.255.0"
},
"rootPassword":"VMware123!",
"datacenterName":"WLD-1-DC"
},
"computeSpec":{
"clusterSpecs":[
{
"name":"Cluster-01",
"hostSpecs":[
{
"id":"fc00927b-5812-41fa-8d3a-cd72137c52a6",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
},
{
"id":"b6ea80a9-8c15-4509-b026-efe9e5c58ce4",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
},
{
"id":"c6e82f26-b130-4c0e-ac9b-5ac9f52e879f",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
}
],
"datastoreSpec":{
"vsanDatastoreSpec":{
"failuresToTolerate":0,
"licenseKey":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"datastoreName":"vSanDatastore"
}
},
"networkSpec":{
"vdsSpecs":[
{
"name":"SDDC-Dswitch-Private1",
"portGroupSpecs":[
{
"name":"SDDC-DPortGroup-Mgmt",
"transportType":"MANAGEMENT"
},
{
"name":"SDDC-DPortGroup-VSAN",
"transportType":"VSAN"
},
{
"name":"SDDC-DPortGroup-vMotion",
"transportType":"VMOTION"
}
]
},
{
"name":"SDDC-Dswitch-Private2",
"portGroupSpecs":[
{
"name":"SDDC-DPortGroup-Public",
"transportType":"PUBLIC"
}
]
}
],
"nsxClusterSpec":{
"nsxVClusterSpec":{
"vlanId":0,
"vdsNameForVxlanConfig":"SDDC-Dswitch-Private1"
}
}
}
}
]
},
"nsxVSpec":{
"nsxManagerSpec":{
"name":"wld-nsxmanager",
"networkDetailsSpec":{
"ipAddress":"10.0.0.31",
"dnsName":"wld-nsxmanager.vcf.sddc.local",
"gateway":"10.0.0.1",
"subnetMask":"255.255.255.0"
}
},
"nsxVControllerSpec":{
"nsxControllerIps":[
"10.0.0.51",
"10.0.0.52",
"10.0.0.53"
],
"nsxControllerPassword":"VMware123!VMware123!",
"nsxControllerGateway":"10.0.0.1",
"nsxControllerSubnetMask":"255.255.255.0"
},
"licenseKey":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"nsxManagerAdminPassword":"VMware123!",
"nsxManagerEnablePassword":"VMware123!"
}
}
}
Of course, you would have to modify it to suit your environment. Make sure you change the host IDs to match the IDs that you obtained previously.
Now that we have the payload, we can leverage the VCF API to validate the information. The screenshot below shows the command line and expected output of the command.

Once you have validated the payload information successfully, then the next step is to actually start the workflow to create the workload domain. Before doing this, we need to slightly modify the JSON file. The change consists of the removal of two lines:
- “domainCreationSpec”:{ line at the beginning of the file
- The ending } character at the end of the file
This modification is needed due to how the different API calls need to be structured. Below is a example of the modified file:
{
"domainName":"WLD-1",
"vcenterSpec":{
"name":"wld-vcenter",
"networkDetailsSpec":{
"ipAddress":"10.0.0.30",
"dnsName":"wld-vcenter.vcf.sddc.local",
"gateway":"10.0.0.1",
"subnetMask":"255.255.255.0"
},
"rootPassword":"VMware123!",
"datacenterName":"WLD-1-DC"
},
"computeSpec":{
"clusterSpecs":[
{
"name":"Cluster-01",
"hostSpecs":[
{
"id":"fc00927b-5812-41fa-8d3a-cd72137c52a6",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
},
{
"id":"b6ea80a9-8c15-4509-b026-efe9e5c58ce4",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
},
{
"id":"c6e82f26-b130-4c0e-ac9b-5ac9f52e879f",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
}
],
"datastoreSpec":{
"vsanDatastoreSpec":{
"failuresToTolerate":0,
"licenseKey":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"datastoreName":"vSanDatastore"
}
},
"networkSpec":{
"vdsSpecs":[
{
"name":"SDDC-Dswitch-Private1",
"portGroupSpecs":[
{
"name":"SDDC-DPortGroup-Mgmt",
"transportType":"MANAGEMENT"
},
{
"name":"SDDC-DPortGroup-VSAN",
"transportType":"VSAN"
},
{
"name":"SDDC-DPortGroup-vMotion",
"transportType":"VMOTION"
}
]
},
{
"name":"SDDC-Dswitch-Private2",
"portGroupSpecs":[
{
"name":"SDDC-DPortGroup-Public",
"transportType":"PUBLIC"
}
]
}
],
"nsxClusterSpec":{
"nsxVClusterSpec":{
"vlanId":0,
"vdsNameForVxlanConfig":"SDDC-Dswitch-Private1"
}
}
}
}
]
},
"nsxVSpec":{
"nsxManagerSpec":{
"name":"wld-nsxmanager",
"networkDetailsSpec":{
"ipAddress":"10.0.0.31",
"dnsName":"wld-nsxmanager.vcf.sddc.local",
"gateway":"10.0.0.1",
"subnetMask":"255.255.255.0"
}
},
"nsxVControllerSpec":{
"nsxControllerIps":[
"10.0.0.51",
"10.0.0.52",
"10.0.0.53"
],
"nsxControllerPassword":"VMware123!VMware123!",
"nsxControllerGateway":"10.0.0.1",
"nsxControllerSubnetMask":"255.255.255.0"
},
"licenseKey":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"nsxManagerAdminPassword":"VMware123!",
"nsxManagerEnablePassword":"VMware123!"
}
}
After making the modifications, you can start the creation of the workload domain as shown below.

After the workflow completes, you can login to the vCenter instance and you will see the VDSs that were automatically created according to the JSON file we specified.

To add a additional host to this cluster, you would follow a similar set of steps:
- Commission the host
- Get the ID for the host using the same method you did previously
- Get the ID for the cluster you want to add the host to

- Ensure the appropriate license keys have been added to the SDDC Manager
- Create a JSON formatted file
- This file is different than what we used previously as we’re using a different API call.
- Here is a example:
{
"clusterUpdateSpec" : {
"clusterExpansionSpec":{
"hostSpecs":[
{
"id":"2d64a4bb-1476-42e6-83df-ad69c60f68db",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
}
]
}
}
}
- Validate the payload

- Modify the JSON file slightly for the next API call
- Note this time we are just removing the ‘”clusterUpdateSpec” : {‘ line and the corresponding closing bracket.
- Here’s a example:
{
"clusterExpansionSpec":{
"hostSpecs":[
{
"id":"2d64a4bb-1476-42e6-83df-ad69c60f68db",
"license":"XXXXX-XXXXX-XXXXX-XXXXX-XXXXX",
"hostNetworkSpec":{
"vmNics":[
{
"id":"vmnic0",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic1",
"vdsName":"SDDC-Dswitch-Private1"
},
{
"id":"vmnic2",
"vdsName":"SDDC-Dswitch-Private2"
},
{
"id":"vmnic3",
"vdsName":"SDDC-Dswitch-Private2"
}
]
}
}
]
}
}
- Add the host
curl -k https://sddc-manager.vcf.sddc.local/v1/clusters/8db86c7a-6b61-447e-9df5-5be527554f4f -i -u ‘admin:VMware123!’ -X PATCH -H ‘Content-Type: application/json’ -d @/root/add_mpnic_host-2.json
That’s all there is to it! You should now see the host being added into the cluster in the SDDC Manager UI.
Some quick things to note:
- If the workload domain is configured to use NFS for storage, the storage must be accessible through vmnic0
- A host in an NSX-T workload domain cannot be added to a VDS and N-VDS at the same time
- If you get an error in the workflow that states that it cannot add the license key to VCF, ensure that the license key matches the one in the SDDC Manager. You can manually add the license key to the ESXi host and retry the workflow.