Как работать с vCenter из C# .NET
На данный момент есть два варианта работы.
- Первый - традиционный - это обращение к классам библиотеки VMWare.Vim.
Например - создаем ASP.NET C# приложение, добавляем к проекту reference - VMware.Vim.dll, VimService60.dll, VimService60.XmlSerializers.dll (который берем из установленного PowerCLI) и работаем как примерно описано тут: Getting started with vSphere .NET application development for PowerCLI users
- Второй - использование современного vSphere Management C# .NET SDK - https://github.com/vmware/vsphere-automation-sdk-.net.
Разница между ними - в функционале. Многие вещи в современном SDK еще не доработаны.
Библиотеки **VMWare.Vim** из PowerCLI до версии 6.3 (включительно) работают с System.Runtime 4.0.0 и пригоден для использования в проектах ASP.NET. Более поздние версии уже ориентированы на ASP.NET Core и для работы с ними нужен System.Runtime 4.2.0.
VM provisioning and customization using ASP.NET
https://github.com/itsChris/vmware-net/tree/master/vmware-net - vmware-net-master.zip Необходимые изменения:
( VimClient vimClient = new VimClient(); => VimClient vimClient = new VimClientImpl();)
VMware.Vim из комплекта PowerCLI 6.3 - powercli_6.3_vimdlls.rar
А вот и весь VMWare PowerCLI 6.3 целикомVMware PowerCLI 6.3.0
С текущими версиями vcenter (6.5 и выше) этот пример работает, если включить сильное шифрование (TLS 1.1, TLS 1.2) для .NET: https://kb.vmware.com/s/article/2137109
Windows Registry Editor Version 5.00 [HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\.NETFramework\v3.5] "SchUseStrongCrypto"=dword:00000001 [HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\.NETFramework\v4.0.30319] "SchUseStrongCrypto"=dword:00000001 [HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\.NETFramework\v4.5.1] "SchUseStrongCrypto"=dword:00000001 [HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\.NETFramework\v4.5.23026] "SchUseStrongCrypto"=dword:00000001 [HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\.NETFramework\v4.5.25000] "SchUseStrongCrypto"=dword:00000001 [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\v4.0.30319] "SchUseStrongCrypto"=dword:00000001
В противном случае ошибка - 'The underlying connection was closed: An unexpected error occurred on a send.'
Этот пример хорошо бы переписать под ASP.NET Core 2.0
Его в принципе невозможно собрать с версией VMware.Vim.dll из более поздних powercli 11.2, потому что она хочет System.Runtime 4.2.0.0, а он есть уже только в ASP.NET Core. Последняя версия VMware.Vim.dll, которая есть работает с ASP есть в составе PowerCLI 6.3.
https://github.com/alex-lucid/NAnt.ContinuousIntegration - nant.continuousintegration-master.zip
https://kb.vmware.com/s/article/2137109
Документация (уже не сильно актуальная)
VMWare vSphere Infrastructure SDK 2.5
VMWare vSphere Guest SDK 4.0
VMWare vSphere Web Services SDK 5.0
https://blogs.vmware.com/PowerCLI/2014/06/working-customization-specifications-powercli-part-3.html
вот кажется (полу)рабочий кусочек кода для vim25 (https://communities.vmware.com/thread/154918)
public void AssignIpToVm(string vmUuid, string ipAddress) { ManagedObjectReference vmRef = service.FindByUuid(sic.searchIndex, null, vmUuid, true); CustomizationSpec customsSpec = new CustomizationSpec(); CustomizationAdapterMapping adapterMap = new CustomizationAdapterMapping(); CustomizationIPSettings adapter = new CustomizationIPSettings(); //CustomizationCustomIpGenerator obj =new CustomizationCustomIpGenerator(); CustomizationFixedIp fixedIP = new CustomizationFixedIp(); fixedIP.ipAddress = ipAddress; adapterMap.adapter = adapter; adapterMap.adapter.ip = fixedIP; customsSpec.nicSettingMap = new CustomizationAdapterMapping[] { adapterMap }; CustomizationIdentitySettings idSettings = new CustomizationIdentitySettings(); customsSpec.identity = idSettings; CustomizationGlobalIPSettings gloIpSettings = new CustomizationGlobalIPSettings(); customsSpec.globalIPSettings = gloIpSettings; service.CustomizeVMTask(vmRef, customsSpec); }
https://communities.vmware.com/thread/452924
CustomizationSpec customsSpec2 = new CustomizationSpec(); CustomizationAdapterMapping adapterMap = new CustomizationAdapterMapping(); CustomizationIPSettings adapter = new CustomizationIPSettings(); CustomizationFixedIp fixedIP = new CustomizationFixedIp(); fixedIP.IpAddress = "192.168.2.83"; adapter.Ip = new CustomizationIpGenerator(); adapter.Gateway = new string[] {"192.168.2.3"}; adapterMap.Adapter = adapter; adapterMap.Adapter.Ip = fixedIP; adapterMap.Adapter.SubnetMask = "255.255.255.0"; customsSpec2.NicSettingMap = new CustomizationAdapterMapping[] { adapterMap }; var custwinoptions = new CustomizationWinOptions(); customsSpec2.Options = custwinoptions; customsSpec2.GlobalIPSettings = new CustomizationGlobalIPSettings(); var idid=new CustomizationSysprep(); idid.Identification = new CustomizationIdentification(); //idid.Identification.DomainAdmin = ""; //idid.Identification. idid.GuiUnattended=new CustomizationGuiUnattended(); idid.GuiUnattended.AutoLogon = true; idid.UserData = new CustomizationUserData(); var custname = new CustomizationVirtualMachineName(); idid.UserData.ComputerName = custname; idid.UserData.FullName = "userdataFullName"; idid.UserData.OrgName = "userDataOrgName"; idid.UserData.ProductId = ""; customsSpec2.Identity = idid; var cName = new CustomizationName(); customizeVMTask = targetVirtualMachine.CustomizeVM_Task(customsSpec2);
I used ASP.net with C# as based language to clone VM and change the IP. The code is work and the IP changed. FYI I used vim25api. Here is the code. VirtualMachineCloneSpec cloneSpec = new VirtualMachineCloneSpec(); string guestCustomizationScript = “your guest customization script name”; //get your customization spec item by name. CustomizationSpecItem cusSpecItem = _service.GetCustomizationSpec(_sic.customizationSpecManager, guestCustomizationScript); cloneSpec.customization = cusSpecItem.spec; //SET IP ADDRESS CustomizationFixedIp fixedIP = new CustomizationFixedIp(); fixedIP.ipAddress = ipAddress; cloneSpec.customization.nicSettingMap[0].adapter.ip = fixedIP; //USE cloneSpec AS PARAMETER TO CLONEVM_TASK ManagedObjectReference cloneTask = _service.CloneVM_Task(vmRef, vmFolderRef, cloneName, cloneSpec);
Кусочек кода на java, который кастомизирует виртуалочку
CustomizationSpecItem specItem = null;
CustomizationSpecInfo info = new CustomizationSpecInfo();
specItem = new CustomizationSpecItem();
specItem.setInfo(info);
CustomizationSpec cspec = new CustomizationSpec();
CustomizationGlobalIPSettings gIP = new CustomizationGlobalIPSettings();
cspec.setGlobalIPSettings(gIP);
// This is windows so choose the sysprep
CustomizationSysprep sprep = new CustomizationSysprep();
CustomizationGuiUnattended guiUnattended = new CustomizationGuiUnattended();
guiUnattended.setAutoLogon(false); // do not autoLogin on reboot for customization.
guiUnattended.setAutoLogonCount(0); // do not autologin on reboot.
CustomizationPassword pass = new CustomizationPassword();
pass.setPlainText(true);
pass.setValue("ca$hc0wS");
guiUnattended.setPassword(pass);
guiUnattended.setTimeZone(4); // set to Eastern time.
sprep.setGuiUnattended(guiUnattended); // add VM to WORKGROUP
CustomizationIdentification identification = new CustomizationIdentification();
identification.setJoinWorkgroup("WORKGROUP");
sprep.setIdentification(identification);
String productId = ""; //"00477-001-0000347-84147";
/*String productId = queryProductId("OS");
// only needed for windows os's
if ("Windows2008")
{
CustomizationLicenseFilePrintData licenseFilePrintData = new CustomizationLicenseFilePrintData();
licenseFilePrintData.setAutoMode(CustomizationLicenseDataMode.PER_SERVER);
licenseFilePrintData.setAutoUsers(5);
sprep.setLicenseFilePrintData(licenseFilePrintData);
}*/
// setup UserData
CustomizationUserData userData = new CustomizationUserData();
CustomizationFixedName n = new CustomizationFixedName();
n.setName("WinSQLCustom");
userData.setComputerName(n);
userData.setProductId(productId);
userData.setFullName("WinSQLCustom.maithri");
// This may change in the future
userData.setOrgName("IGATE");
userData.setProductId(productId);
// Product Serial (needed for Windows 2003 and 2008)
sprep.setUserData(userData);
cspec.setIdentity(sprep);
// NicSettingMap part
CustomizationAdapterMapping adaptorMap = new CustomizationAdapterMapping();
CustomizationIPSettings adapter = new CustomizationIPSettings();
CustomizationFixedIp fixedIp = new CustomizationFixedIp();
String dnsList = "10.115.200.100";
adapter.setDnsDomain(dnsList);
fixedIp.setIpAddress("10.115.200.109");
adapter.setIp(fixedIp);
String subnetmask = "255.255.255.0";
adapter.setSubnetMask(subnetmask);
adaptorMap.setAdapter(adapter);
CustomizationWinOptions options = new CustomizationWinOptions();
options.setChangeSID(true);
options.setDeleteAccounts(false);
cspec.setOptions(options);
specItem.setSpec(cspec);
System.out.println("Check Point 4");
try{
System.out.printf("vm mor2: %s \n",vmToClone);
vimPort.customizeVMTask(vmToClone, specItem.getSpec());
System.out.println("Check Point 5");
}
//catch (CustomizationFault fault)
catch (Exception e) {
e.printStackTrace();System.err.println("Sample code failed ");
System.exit(1);
}
}
catch (Exception e) {
e.printStackTrace();System.err.println("Sample code failed 2 ");
System.exit(1);
}
finally {
// Always close connectionl, even if errors occure.
if (vimPort != null && serviceContent != null) {
try {
vimPort.logout(serviceContent.getSessionManager());
} catch (com.vmware.vim25.RuntimeFaultFaultMsg rffm) {
System.out.println("Sample code failed while logging out after a previous failure.");
rffm.printStackTrace();
}
}
}
Discussion