A little while ago VMware released Horizon View 6.1, which for the first time allowed Linux VDI desktops among many other new improvements. All customer that have Horizon 6 Enterprise Edition, or VMware Workspace Suite are entitled to use Horizon Linux Desktops. Supported Linux distributions include Ubuntu, RHEL, CentOS, and NeoKylin. Importantly VMware also supports 3D GPU Hardware Acceleration with these operating systems leveraging NVIDIA. At the moment however there is no automatic way to install the Horizon View Linux Agent on the desktops out of the box, so you have to automate it if you want to use this at scale. After I had built my first Linux desktop and started using it I liked it so much I wanted to provision more desktops, and see how fast I could do it. This article will take you through some of the steps and the scripts I used to provision 400 Linux desktops from template and register them as managed machines with Horizion View in just 11 minutes.
First before we look at the scripts there are some pre-requisites. You’ll need to have a working VMware Horizon View 6.1 environment, VMware PowerCLI installed (latest version recommended), a Linux desktop based on one of the supported distributions, the VMware Horizon View Agent for Linux, and a Linux customization specification created in vCenter.
In order for the new desktops that you provision to be able to automatically register with the Horizon View Connection Server you need to place some first boot scripts into the template of your Linux Desktop, and you need to ensure that the Horizon View Agent is installed on the template VM. In the scripts below the directory for the Horizon View Agent is /root/VMware-viewagent-linux-x86_64-6.1.1-2772438.
In the template, which I have called LinuxDT-Template, the first script is placed in /etc/rc.d. This script is called at startup and will check for the existence of the first boot script, and if it exists will be executed.
/etc/rc.d/rc.local:
#!/bin/sh # # This script will be executed *after* all the other init scripts. # You can put your own initialization stuff in here if you don't # want to do the full Sys V style init stuff. touch /var/lock/subsys/local FBSCRIPT="/root/firstbootview.sh" if [ -f $FBSCRIPT ]; then echo "Firstboot script exists, executing..." $FBSCRIPT fi
The next script is the first boot script itself. This will check to see if the Horizon View Agent is already installed and if so will clean that out. It will also check that the script is not being run on template itself. This script will install and configure the Horizon View Agent on the Linux Desktop and register the desktop with Horizon View. It checks to make sure the hostname of the VM matches the DNS records, else the registration process will not be successful.
/root/firstbootview.sh
#!/bin/bash VIEWAGENTDIR="/etc/vmware" VIEWAGENTINSTALL="/root/VMware-viewagent-linux-x86_64-6.1.1-2772438" VIEWMANAGER="nxviewmgr.nxmgmt.local" DOMAINNAME="nxmgmt.local" USERNAME="viewmgr" PW="YourPass" HOSTNAME=`hostname` LOOKUP=`nslookup $HOSTNAME | grep $HOSTNAME | cut -c 7-` echo "Checking if Horizon View Agent was previously installed" if [ -d $VIEWAGENTDIR ]; then echo "$VIEWAGENTDIR exists, uninstaling" /usr/lib/vmware/viewagent/bin/uninstall_viewagent.sh >> /root/viewagentinstall.log rm -rf $VIEWAGENTDIR fi while [ "$LOOKUP" != "$HOSTNAME.$DOMAINNAME" ]; do sleep 5 LOOKUP=`nslookup $HOSTNAME | grep $HOSTNAME | cut -c 7-` done echo "Installing VMware Horizon View Agent for Linux..." cd $VIEWAGENTINSTALL echo "Working directory" `pwd` $VIEWAGENTINSTALL/install_viewagent.sh -b $VIEWMANAGER -d $DOMAINNAME -u $USERNAME -p $PW >>/root/viewagentinstall.log cat /root/viewagentinstall.log if [ "$HOSTNAME" != "LinuxDT-Template" ]; then echo "Firstboot script complete, self destructing in 5 seconds..." sleep 5 echo "Deleting $0 ..." rm -rf $0 reboot fi
Now that you have the Linux Desktop Template created and the first boot scripts set up, along with the other pre-requisites, you can proceed to deploying as many Linux VDI desktops as you wish. Each will be registered with Horizon View, and then you will be able to add them to a desktop pool. The sample PowerCLI script below will rapidly provision as many desktops as you like. It has been written to be multi-threaded, and will use all of the CPU on the client system it is run from. Also because it runs all clone tasks in parallel, it will also place a fairly high load on vCenter. So it is recommended you test this first in a non-production environment and decide if it’s safe to use in production before you go provisioning all of the desktops on any existing systems. As with all the scripts in this post, use them at your own risk, they are provided for informational and educational purposes only.
Clone-LinuxDT.ps1:
# PowerCLI to create VMs from existing vSphere VM # Version 1.1 # Original Author: Magnus Andersson RTS # Updated by: Michael Webster # # Specify vCenter Server, vCenter Server username and vCenter Server user password $vCenter="YourvCenter" $vCenterUser="YourUsername" $vCenterUserPassword="YourPassword" # # Specify number of VMs you want to create $vm_count = 400 # #Specify where to start the VM Numbering Sequence $start_count = 11 # # Specify the VM you want to clone $clone = "LinuxDT-Template" # # Specify the Customization Specification to use $customspecification = "Linux" # # Specify the datastore or datastore cluster placement $ds = "Erebor" # # Specify vCenter Server Virtual Machine & Templates folder $Folder = "NXPERFENG" # # Specify the vSphere Cluster $Cluster = "NXNZTest2-3000" # # Specify the VM name to the left of the ñ sign $VM_prefix = "LinuxDT" # # End of user input parameters #_______________________________________________________ # write-host "Connecting to vCenter Server $vCenter" -foreground green Connect-viserver $vCenter -user $vCenterUser -password $vCenterUserPassword -WarningAction 0 $start_count..(($vm_count+$start_count)-1) | foreach { $y="{0:D2}" -f $_ $VM_name= $VM_prefix + $y $ToD = (Get-Date).ToLongTimeString() Write-Host "Script Stated Executing at" $ToD $ESXi=Get-Cluster $Cluster | Get-VMHost -state connected | Get-Random write-host "Creation of VM $VM_name initiated" -foreground green start-process powershell -NoNewWindow -ArgumentList "Add-PSSnapin VM*; Connect-viserver $vCenter -user $vCenterUser -password $vCenterUserPassword -WarningAction 0 | out-null; New-VM -Name $VM_Name -VM $clone -VMHost $ESXi -Datastore $ds -Location $Folder -OSCustomizationSpec $customspecification | out-null; Start-VM $VM_Name | out-null; write-host 'Creation of VM $VM_name initiated' (GetDate).ToLongTimeString() -foreground white;" }
I used the script above to successfully provision 400 Linux VDI desktops in 11 minutes. In order to do this you not only need a decent client system to run the script (I used a Windows VDI Desktop running on a Nutanix cluster), you also need a very good back end infrastructure to stand up all of the cloned desktops. They will all be provisioned, customized and booted essentially in parallel. There will be a lot of IO and a lot of CPU usage across the system. It would be normal for this to tax the CPU’s on the hosts to 100% utilization for a sustained period.
Part of the reason I was able to do all of this in 11 minutes was because I was using a Nutanix 4 node NX3000 cluster (albeit a 3 year old cluster) and ESXi 6.0. So on a newer more modern cluster I probably would have been able to do the same task in less than 10 minutes. Remember, this is provisioning all desktops from template, customizing them, powering them on, and registering them with VMware Horizon View, for 400 desktops, in 11 minutes. If I doubled the number of desktops and doubled the number of Nutanix hosts in the cluster (to say 8), the provisioning time wouldn’t take twice as long, provided I have enough horsepower on vCenter and on the system executing the clone tasks, it would take the same amount of time. This is because the Nutanix platform scales linearly. Once you know how many VM’s you get per node, every node you add, you get exactly the same, consistent, predictable performance.
Here is a copy of the LinuxVMCustomizationSpec.xml file you can modify and import into vCenter. This is pretty simple. Uses DHCP for IP addressing. It has been configured to use the Google DNS Servers. So you will need to change that to your DNS servers.
LinuxVMCustomizationSpec.xml
<ConfigRoot> <_type>vim.CustomizationSpecItem</_type> <info> <_type>vim.CustomizationSpecInfo</_type> <changeVersion>1414648162</changeVersion> <description/> <lastUpdateTime>2014-10-30T05:49:22Z</lastUpdateTime> <name>LinuxVM</name> <type>Linux</type> </info> <spec> <_type>vim.vm.customization.Specification</_type> <globalIPSettings> <_type>vim.vm.customization.GlobalIPSettings</_type> <dnsServerList> <_length>2</_length> <_type>string[]</_type> <e id="0">8.8.8.8</e> <e id="1">8.8.1.1</e> </dnsServerList> <dnsSuffixList> <_length>1</_length> <_type>string[]</_type> <e id="0">nxmgmt.local</e> </dnsSuffixList> </globalIPSettings> <identity> <_type>vim.vm.customization.LinuxPrep</_type> <domain>nxmgmt.local</domain> <hostName> <_type>vim.vm.customization.VirtualMachineNameGenerator</_type> </hostName> <hwClockUTC>true</hwClockUTC> <timeZone>Pacific/Auckland</timeZone> </identity> <nicSettingMap> <_length>1</_length> <_type>vim.vm.customization.AdapterMapping[]</_type> <e id="0"> <_type>vim.vm.customization.AdapterMapping</_type> <adapter> <_type>vim.vm.customization.IPSettings</_type> <ip> <_type>vim.vm.customization.DhcpIpGenerator</_type> </ip> </adapter> </e> </nicSettingMap> <options> <_type>vim.vm.customization.LinuxOptions</_type> </options> </spec> </ConfigRoot>
Now if you were running these scripts in a test environment and planning to run the tests over and over again you will quickly realize that Horizon View allows duplicate entries in it’s database. You’ll also quickly realize that there is no easy way to quickly remove lots and lots of registered machines from Horizon View. You’ll also notice, if you research it, that there is currently no way to do anything about either of these problems with the Horizon View PowerCLI CMDLets. So where does that leave us? Well I’m glad you asked. In this case you will have to edit the Horizon View LDAP directory directly to remove the machines after they have been deleted. You can do this also when you decommission large numbers of VDI VM’s. But it is certainly advisable to have a backup before doing anything like this. The PowerShell script below uses LDIFDE to interrogate the Horizon View LDAP Directory and search for any machines that are showing as Agent Unreachable. This means they are off or not longer can be contacted (probably as you’ve deleted them). Any agents that fall into that category will be removed form the Horizon View LDAP Directory and therefore be removed from the Registered Machines in View Manager.
RemoveUnreachableDesktops.ps1
$desktopcn = @() $removedesktops=(Get-DesktopPhysicalMachine -State "Agent unreachable").displayName $removedesktops | foreach { write-host "Searching for dn of $_" ldifde -s localhost -d "dc=vdi,dc=vmware,dc=int" -r "(description=$_)" -l dn -f "$_.txt" write-host "Writing output to $_.txt" $getcn = (Get-Content "$_.txt")[0] $desktopcn += "$getcn" Remove-Item "$_.txt" write-host "Desktop DN's to Remove = $getdn" } $desktopcn | foreach { $output = @() write-host "Adding items to remove file..." write-host "$_" write-host "changetype: delete" $output += "$_" $output += "changetype: delete`n" $output | Out-File -Filepath removedesktops.txt -Append write-output `n | Out-File -Filepath removedesktops.txt -Append } write-host "About to remove all of the desktops..." pause ldifde -i -f removedesktops.txt -s localhost Remove-Item removedesktops.txt
I’m no scripting expert, but I’ve used all of these scripts above in my lab environment. They could have probably been written more efficiently and more elegantly. But I just wrote them in a brief period of time to do a job and that’s it. So please feel free to improve upon them and if you do I’d greatly appreciate it if you could post any updates here.
Final Word
The combination of VMware Horizon View, VMware vSphere 6.0 and Nutanix web-scale converged infrastructure is an unparalleled combination for running any desktop workload (and almost all non-desktop workload as well). In this example I have used the new functionality in Horizon View 6.1 to provision Linux VDI Desktops rapidly. Due to the smart cloning features of the Nutanix platform the clones didn’t consume any additional storage space. This was not dedupe, this was data avoidance. No point creating unnecessary data in the first place. This is a demonstration of what you can do with a smart modern infrastructure platform to move your business forward, do non-disruptive upgrades in your lunch time, and with self healing capabilities, spend more time with your friends and family. If you like the sound of that, get in touch with any of the Nutanix team and ask us about it.
—
This post first appeared on the Long White Virtual Clouds blog at longwhiteclouds.com. By Michael Webster +. Copyright © 2012 – 2015 – IT Solutions 2000 Ltd and Michael Webster +. All rights reserved. Not to be reproduced for commercial purposes without written permission.
[…] am using two of Michael Webster ‘s scripts to clone my Linux template. Visit his site longwhiteclouds, great […]
[…] am using two of Michael Webster ‘s scripts to clone my Linux template. Visit his site longwhiteclouds, great […]