VMware vCloud Director REST API with Terraform
Overview
If you work with VMware vCloud Director (vCD) and Terraform regularly, you're likely familiar with the vcd provider for interacting with the vCD API. This provider is an excellent tool for automating the deployment of vCD resources and managing the lifecycle of your virtual datacenters.
However, you may have noticed some limitations in the vcd provider, particularly when it comes to managing infrastructure components. To handle these components with Terraform, you will need to interact directly with the vCD REST API. In this post, I'll share how I approach this specific use case.
Terraform providers
In this particular situation I use the following providers:
1terraform {
2 required_version = ">= 1.6"
3 required_providers {
4 vcd = {
5 source = "vmware/vcd"
6 }
7 restful = {
8 source = "magodo/restful"
9 }
10 }
11}
- The
vmware/vcdprovider is the official VMware provider for vCloud Director. We will use it to retrieve arefresh tokenthat we will use to authenticate to the vCD API. - The
magodo/restfulwill provide a simple way to authenticate using the refresh token with oauth2 and to run requests over the REST API of vCloud.
Authentication process
vCD provider configuration
With a set of variables to define URI, credentials, and other parameters, we can configure the vCD provider for the System Org.
1# Configure the VMware Cloud Director Provider for the System Org
2provider "vcd" {
3 alias = "vcd-sys"
4 user = var.vcloud_admin_username
5 password = var.vcloud_admin_password
6 auth_type = "integrated"
7 org = "System"
8 url = "${var.vcloud_uri}/api"
9 max_retry_timeout = 30
10 allow_unverified_ssl = var.vcloud_insecure
11}
Refresh token generation
vmware/vcd provider provides a vcd_api_token resource that allows you to create a refresh token that you can use to authenticate to the vCD API to generate a bearer token.
The refresh_token will be stored in a file to be reused by the next provider.
1# Create a refresh token
2resource "vcd_api_token" "vcd_sys" {
3 provider = vcd.vcd-sys
4 name = "vcd-sys"
5 file_name = ".vcd-sys-token.json"
6 allow_token_file = true
7}
8
9# Load refresh token file
10data "local_file" "vcd_sys_token" {
11 filename = vcd_api_token.vcd_sys.file_name
12}
restful provider configuration
In this step, we will use the magodo/restful provider and specify the refresh_token information to configure a oauth2.refresh_token section.
I provided an alias name to this provider in order to be able to dissociate sysadmin tasks and normal users ones.
1# Create a vcd provider with the refresh token
2provider "restful" {
3 alias = "vcd-sys"
4 base_url = var.vcloud_uri
5 security = {
6 oauth2 = {
7 refresh_token = {
8 token_url = "${var.vcloud_uri}/oauth/provider/token"
9 refresh_token = jsondecode(data.local_file.vcd_sys_token.content)["refresh_token"]
10 }
11 }
12 }
13 header = {
14 "Accept" = "*/*;version=${var.vcloud_api_version}",
15 "Content-Type" = "application/json"
16 }
17 client = {
18 tls_insecure_skip_verify = var.vcloud_insecure
19 }
20}
Objects management through the REST API
We can now use the above provider and the restful_operation resource to create objects by using the REST API, like the creation of a vCenter Server object to associate with the vCloud Director instance:
1resource "restful_operation" "register_avs_vcenter" {
2 provider = restful.vcd-sys
3 path = "/cloudapi/1.0.0/virtualCenters"
4 method = "POST"
5 data = jsonencode({
6 "vcId" : null,
7 "name" : "vCenter01",
8 "description" : "vCenter01 resources",
9 "username" : var.vcenter_username,
10 "password" : var.vcenter_password,
11 "url" : var.vcenter,
12 "isEnabled" : true,
13 "vsphereWebClientServerUrl" : null,
14 "hasProxy" : false,
15 "rootFolder" : null,
16 "vcNoneNetwork" : null,
17 "vcNoneNetworkMoref" : null,
18 "tenantVisibleName" : null,
19 "isConnected" : true,
20 "mode" : "NONE",
21 "listenerState" : "INITIAL",
22 "clusterHealthStatus" : "GRAY",
23 "vcVersion" : null,
24 "buildNumber" : null,
25 "uuid" : "${var.vcenter}/sdk",
26 "nsxVManager" : null,
27 "proxyConfigurationUrn" : null
28 })
29}
Conclusion
The example above demonstrates a scenario where the vmware/vcd provider lacks the necessary functionality to manage certain objects. In such cases, the vCD REST API can be used to manage these objects and automate the deployment of vCD resources.
However, it's important to note that the vCD REST API is not as user-friendly as the vmware/vcd provider and does not provide sufficient abstraction for managing other lifecycle operations like updates and deletes without significant effort. Therefore, it is recommended to use the vCD REST API only when necessary and to rely on the vmware/vcd provider for most operations.