Remove a VMFS datastore using powershell

简介:

Recently I had to remove a lot of VMFS datastores from our VMWare infrastructure as we had migrated to new storage and no longer needed them.
In order to remove a datastore from your vmware infrastructure correctly you must follow the instructions given in this article. http://kb.vmware.com/selfservice/microsites/search.do?language=en_US&cmd=displayKC&externalId=2004605
Basically it says you have to make sure nothing is using the datastore and then unmount and detach the datastore from each connected host. Since we work with large clusters with many ESXi hosts I didn’t enjoy the prospect of manually unmounting and detaching each datastore from each host. To avoid this I found this article http://blogs.vmware.com/vsphere/2012/01/automating-datastore-storage-device-detachment-in-vsphere-5.html which explains how to automate datastore removal. It’s a great article and includes a few functions which give you the ability to unmount and detach datastores like described above. I simply used these functions to create the script in this blog.

If the functions are already there then why use this script?

I wrote this script so that it does everything for you in one go. You don’t have to mess around with the functions or cmd-lets yourself. Also, I made a few changes to the mentioned functions which I feel improve them. Basically all you have to do is put in the name of the datastore and run the script.

What does the script do exactly?

1. The script gets the datastore info and then asks for confirmation before beginning the removal process.
2. The datastore is unmounted on each host connected to it.
3. The datastore is detached on each host connected to it.
4. At the end of the script run the datastore name and LUN canonical name is returned. This is useful as you will probably need this information when you have to delete the LUN in your storage system later on.

How do I run the script?

I. Go through the checklist “Unmounting a LUN checklist” here http://kb.vmware.com/selfservice/microsites/search.do?language=en_US&cmd=displayKC&externalId=2004605 and make sure your datastore is ready for removal.
II.Copy the script to your computer and open it with and editor like powershell_ISE or powerGUI.
III. In the #Parameters section enter the name of your vCenter server and the name of the datastore you wish to remove.
IV. Hit F5 to run the script.

The script itself

I’m not going to go into details about the code as you can see all that in the links to KB articles above. I have simply copied in the script for you here. Please leave a comment if you find the script useful. Enjoy!


#############################################################################################################
##script:           Unmount_Detach-Datastore.ps1
##
##Description:      Unmounts and detaches a given datastore from all its connected hosts.
#+                  Before running make sure that the datastore doesn't have any live VMs or templates on it.
##Created by:       Noam Wajnman
##Creation Date:    August 4, 2014
##############################################################################################################
function  Connect-Vcenter  {
     #############################################################################################
     ##Function:         Connect-Vcenter
     ##
     ##Description:      Loads the VMWare snap-in for powershell and connects to vcenter.
     ##
     ##Created by:       Noam Wajnman
     ##Creation Date:    20 November, 2012
     ##Updated:          31 July, 2014
     ##############################################################################################
     param (
         $vcenter
     )
     #Load snap-in
     if  ( -not  ( Get-PSSnapin  -Name  VMware.VimAutomation.Core  -erroraction  "silentlycontinue"  )) {
         Write-Host  "Importing VMWare Snap-in VMware.VimAutomation.Core..."   
         Add-PSSnapin  VMware.VimAutomation.Core
     }
     Set-PowerCLIConfiguration  -DefaultVIServerMode  Single  -invalidCertificateAction  "ignore"  -confirm : $false  out-null
     #Connect to vCenter
     if  ( $global:DefaultVIServers .Count  -lt  1) {
         Write-Host  "Connecting to vcenter server $vcenter..."      
         Connect-VIServer  $vCenter
     }
}
Function  Get-DatastoreMountInfo  {
     #function copied from https://communities.vmware.com/docs/DOC-18008
     [ CmdletBinding ()]
     Param  (
         [ Parameter ( ValueFromPipeline = $true )]
         $Datastore
     )
     Process  {
         $AllInfo  = @()
         if  ( -not  $Datastore ) {
             $Datastore  Get-Datastore
         }
         Foreach  ( $ds  in  $Datastore ) { 
             if  ( $ds .ExtensionData.info.Vmfs) {
                 $hostviewDSDiskName  $ds .ExtensionData.Info.vmfs.extent[0].diskname
                 if  ( $ds .ExtensionData.Host) {
                     $attachedHosts  $ds .ExtensionData.Host
                     Foreach  ( $VMHost  in  $attachedHosts ) {
                         $hostview  Get-View  $VMHost .Key
                         $hostviewDSState  $VMHost .MountInfo.Mounted
                         $StorageSys  Get-View  $HostView .ConfigManager.StorageSystem
                         $devices  $StorageSys .StorageDeviceInfo.ScsiLun
                         Foreach  ( $device  in  $devices ) {
                             $Info  = '' | Select Datastore, VMHost, Lun, Mounted, State
                             if  ( $device .canonicalName  -eq  $hostviewDSDiskName ) {
                                 $hostviewDSAttachState  = ''
                                 if  ( $device .operationalState[0]  -eq  "ok" ) {
                                     $hostviewDSAttachState  "Attached"                        
                                 elseif  ( $device .operationalState[0]  -eq  "off" ) {
                                     $hostviewDSAttachState  "Detached"                        
                                 else  {
                                     $hostviewDSAttachState  $device .operationalstate[0]
                                 }
                                 $Info .Datastore =  $ds .Name
                                 $Info .Lun =  $hostviewDSDiskName
                                 $Info .VMHost =  $hostview .Name
                                 $Info .Mounted =  $HostViewDSState
                                 $Info .State =  $hostviewDSAttachState
                                 $AllInfo  +=  $Info
                             }
                         }
                         
                     }
                 }
             }
         }
         $AllInfo
     }
}
Function  Detach-Datastore {
     #function based on code found here https://communities.vmware.com/docs/DOC-18008
     [ CmdletBinding ()]
     Param  (
         [ Parameter ( ValueFromPipeline = $true )]
         $Datastore
     )
     Process  {
         if  ( -not  $Datastore ) {
             Write-Host  "No Datastore defined as input"
             Exit
         }
         Foreach  ( $ds  in  $Datastore ) {
             $hostviewDSDiskName  $ds .ExtensionData.Info.vmfs.extent[0].Diskname
             if  ( $ds .ExtensionData.Host) {
                 $attachedHosts  $ds .ExtensionData.Host
                 Foreach  ( $VMHost  in  $attachedHosts ) {
                     $hostview  Get-View  $VMHost .Key
                     $StorageSys  Get-View  $HostView .ConfigManager.StorageSystem
                     $devices  $StorageSys .StorageDeviceInfo.ScsiLun
                     Foreach  ( $device  in  $devices ) {
                         if  ( $device .canonicalName  -eq  $hostviewDSDiskName ) {
                             #If the device is attached then detach it (I added this to the function to prevent error messages in vcenter when running the script)
                             if  ( $device .operationalState[0]  -eq  "ok" ) {
                                 $LunUUID  $Device .Uuid
                                 Write-Host  "Detaching LUN $($Device.CanonicalName) from host $($hostview.Name)..."
                                 $StorageSys .DetachScsiLun( $LunUUID );
                             }
                             #If the device isn't attached then skip it (I added this to the function to prevent error messages in vcenter when running the script)
                             else  {
                                 Write-Host  "LUN $($Device.CanonicalName) is not attached on host $($hostview.Name)..."
                             }
                         }
                     }
                 }
             }
         }
     }
}
Function  Unmount-Datastore {
     #function based on code found here https://communities.vmware.com/docs/DOC-18008
     [ CmdletBinding ()]
     Param  (
         [ Parameter ( ValueFromPipeline = $true )]
         $Datastore
     )
     Process  {
         if  ( -not  $Datastore ) {
             Write-Host  "No Datastore defined as input"
             Exit
         }
         Foreach  ( $ds  in  $Datastore ) {
             $hostviewDSDiskName  $ds .ExtensionData.Info.vmfs.extent[0].Diskname
             if  ( $ds .ExtensionData.Host) {
                 $attachedHosts  $ds .ExtensionData.Host
                 Foreach  ( $VMHost  in  $attachedHosts ) {
                     $hostview  Get-View  $VMHost .Key
                     $mounted  $VMHost .MountInfo.Mounted
                     #If the device is mounted then unmount it (I added this to the function to prevent error messages in vcenter when running the script)
                     if  ( $mounted  -eq  $true ) {
                         $StorageSys  Get-View  $HostView .ConfigManager.StorageSystem
                         Write-Host  "Unmounting VMFS Datastore $($DS.Name) from host $($hostview.Name)..."
                         $StorageSys .UnmountVmfsVolume( $DS .ExtensionData.Info.vmfs.uuid);
                     }
                     #If the device isn't mounted then skip it (I added this to the function to prevent error messages in vcenter when running the script)
                     else  {
                         Write-Host  "VMFS Datastore $($DS.Name) is already unmounted on host $($hostview.Name)..."
                     }
                 }
             }
         }
     }
}
#VARIABLES
#Parameters
$vcenter  "Some_Vcenter_Server"
$DSName  "Some_Datastore"
#SCRIPT MAIN
clear
Connect-Vcenter  $vcenter
$datastore  Get-Datastore  -Name  $DSName
$CanonicalName  $datastore .ExtensionData.Info.Vmfs.Extent[0].DiskName
$GoAhead  Read-Host  "Are you sure that you want to unmount and detach: `n$DSName `n$CanonicalName`nfrom all its connected hosts?"
if  ( $GoAhead  -eq  "yes"  -or  $GoAhead  -eq  "y"  -or  $GoAhead  -eq  "Y" ) {
     Write-Host  "Unmounting datastore $DSName..."   
     $datastore  | Unmount-Datastore
     Write-Host  "Detaching datastore $DSName from hosts..."
     $datastore  | Detach-Datastore
}
$DSName
$CanonicalName


Forward from

https://scriptingblog.com/2014/08/13/remove-a-vmfs-datastore-using-powershell/

本文转自学海无涯博客51CTO博客,原文链接http://blog.51cto.com/549687/1983745如需转载请自行联系原作者


520feng2007

相关文章
|
虚拟化 Windows
VMware Workstation 与 Device/Credential Guard 不兼容。在禁用 Device/Credential Guard 后,可以运行 VMware Workstati
VMware Workstation 与 Device/Credential Guard 不兼容。在禁用 Device/Credential Guard 后,可以运行 VMware Workstati
396 0
VMware Workstation 与 Device/Credential Guard 不兼容。在禁用 Device/Credential Guard 后,可以运行 VMware Workstati