In my previous blog, I onboarded the existing vCenter workloads to vRealize Automation in an existing project. The customer has asked me to create a workflow to create a project and then onboard the workloads to that project.


  • Create a project for each team.
  • Add custom properties to the group, which are key value pairs.
  • Project should have a custom naming template with the format resource Name followed by 4 random numbers i.e resourceName-4467.
  • Add the manager of the team as a viewer role and the team members as member role.
  • Add all the available cloud zones to the project, available for provisioning.


Custom properties had to be the input to the workflow, in Key: Value pair format. vRO does not provide the Key:Value pair input type out of the box, so I had to create a New Composite Type. All inputs are coming from SNOW, so they are being validated before coming to vRO.

To create the project, I used the api call /project-service/api/projects. I looped through the values in the New Composite Type and inserted them into the request content. Full code is below.

var url = "/project-service/api/projects";
var contentType = "application/json"
var requestContent = '{ \n' +
   '"name": "' + groupName + '", \n' +
   '"description": "' + groupDescription + '", \n' +
   '"constraints":{ \n' +
      '"network":null, \n' +
      '"storage":null, \n' +
      '"extensibility":null \n' +
   '}, \n' +
   '"sharedResources":true, \n' +
   '"operationTimeout":0 \n' +

requestContentJson = JSON.parse(requestContent);
var properties = new Object;
properties.__namingTemplate = "${}-${####}";
properties.__projectPlacementPolicy = "DEFAULT";
for each (var item in customProperties){
    properties[item["Name"]] = item["Value"];

requestContentJson["properties"] = properties;
var requestResponse = System.getModule("").executeRestOp("POST",url,(JSON.stringify(requestContentJson)),contentType);

System.log("Create project requestResponse: " + requestResponse);

var projectId = JSON.parse(requestResponse).id;
if (projectId) {
    System.log("projectId found: " + JSON.stringify(projectId));
} else {throw ("projectid not found, check your rest call")};

Once the project was created, I added the user/groups and assigned them their respective roles. The workflow does not validate if the users exist in vRA because the users will be coming from Active Directory and the validation is done in the workflow that adds the users to the AD. The below code adds the local users because I do not have AD integrated into vRA in my lab.

var url = "project-service/api/projects/"+projectId+"/principals"
var contentType = "application/json"

//TO do
// validate if users exist in vRA, if multiple users > loop them

var requestContent = '{ \n' +
   '"modify":[ \n ' +
      '{ \n' +
         '"email":"'+memberUserId+'", \n' +
         '"type":"user", \n' +
         '"role":"member" \n' +
      '}, \n'+
      '{ \n' +
         '"email":"'+managerUserId+'", \n' +
         '"type":"user", \n' +
         '"role":"viewer" \n' +
      '} \n'+
   '] \n' +
var requestResponse = System.getModule("").executeRestOp("PATCH",url,requestContent,contentType);

The final step was to add the zones. I only have one zone in my lab but the code factors in multiple zones and will add each zone by its id. There were no resource limits(CPU, memory, no of instances etc) to be set in my use case.

//Get zone
var url = "/iaas/api/zones";
var contentType = "application/json";
var requestResponse = System.getModule("").executeRestOp("GET",url,null,contentType);

System.log("requestResponse for get zone : " + requestResponse);

// Add zones to project
var url = "/iaas/api/projects/"+ projectId;
var requestContent = {};
var zoneAssignmentConfigurations = [];
var zone = {};

System.log("no of zones found: " + requestResponse.numberOfElements);
    System.log("zone id is: " +
    zone.storageLimitGB = 0;
    zone.cpuLimit = 0;
    zone.memoryLimitMB = 0;
    zone.zoneId =;
    zone.maxNumberInstances = 0;
    zone.priority = 100;

requestContent.zoneAssignmentConfigurations = zoneAssignmentConfigurations;
var requestResponse = System.getModule("").executeRestOp("PATCH",url,JSON.stringify(requestContent),contentType);

System.log("request response for add zones : " + requestResponse);

Below is the workflow in action.


Leave a Reply

Avatar placeholder

Your email address will not be published. Required fields are marked *