search
Categories
Sponsors
VirtualMetric Hyper-V Monitoring, Hyper-V Reporting
Archive
Blogroll

Badges
MCSE
Community

Cozumpark Bilisim Portali
Posted in Virtual Machine Manager, Windows Server | No Comment | 1,963 views | 09/06/2014 17:54

This is my notes and scripts for a Hyper-V Disaster Recovery with Storage Replication.

First script on Main Site, creates Volume identifiers under CSV Volumes. So after a Volume restore, we can restore Volume names with that index. Also scripts exports all virtual machine configs. That will make it easier to restore all Virtual Machines on Hyper-V.

On Main Site:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
##################################################
# START ON MAIN SITE
##################################################
 
# Clear VM Config
$TestVMConfigPath = Test-Path -Path "C:\ClusterStorage\Volume1\VMExport.Config"
 
if ($TestVMConfigPath)
{
	Clear-Content -Path "C:\ClusterStorage\Volume1\VMExport.Config"
}
 
# Export VM Config
$ClusterNodes = Get-Cluster | Get-ClusterNode
 
foreach ($ClusterNode in $ClusterNodes)
{
	# Get Virtual Machines
	$VMs = Get-VM -ComputerName $ClusterNode
 
	# Export VM Config
	foreach ($VM in $VMs)
	{
		# Get Virtual Machines
		$VMConfigPath = $VM.ConfigurationLocation + "\Virtual Machines\" + $VM.Id + ".xml"
 
		# Export to Config File
		Add-Content -Value $VMConfigPath -Path "C:\ClusterStorage\Volume1\VMExport.Config"
	}
}
 
# Read All CSV Directories
$CSVVolumes = Get-ChildItem "C:\ClusterStorage"
 
foreach ($CSVVolume in $CSVVolumes)
{
	# Get CSV Volume Name
	$CSVVolumeName = $CSVVolume.Name
 
	# Get CSV Identifier Name
	$CSVIdentifierName = $CSVVolumeName + ".CSV"
 
	# Get CSV Path
	$CSVPath = $CSVVolume.FullName
 
	# Get CSV Identifier Path
	$CSVIdentifierPath = $CSVPath + "\" + $CSVIdentifierName
 
	# Test CSV Identifier Path
	$TestCSVIdentifierPath = Test-Path $CSVIdentifierPath
 
	if (!$TestCSVIdentifierPath)
	{
		# Create CSV Identifier
		New-Item -Path "$CSVPath" -Name "$CSVIdentifierName" -ItemType File
	}
}

Second Script on DR site, clears all old objects on Hyper-V and Failover Cluster. Restores volume names according to Volume Identifiers. After that imports all virtual machines by using our virtual machine exports.

On DR Site:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
##################################################
# START ON DR SITE
##################################################
 
# Clear Failover Cluster Objects
$ClusterGroup = Get-ClusterGroup | Where GroupType -eq "VirtualMachine" | Remove-ClusterGroup -RemoveResources -Force
 
# Get All Cluster Nodes
$ClusterNodes = Get-Cluster | Get-ClusterNode
 
if ($ClusterNode in $ClusterNodes)
{
	Invoke-Command -ComputerName $ClusterNode -ScriptBlock {
 
		# Stop Hyper-V Management Service
		Set-Service "vmms" -StartupType Disabled
		Stop-Service "vmms"
 
		# Clear Hyper-V Database
		Get-ChildItem -Path "C:\ProgramData\Microsoft\Windows\Hyper-V\Virtual Machines" | Remove-Item
	}
}
 
# Read All CSV Directories
$CSVVolumes = Get-ChildItem "C:\ClusterStorage"
 
# Clear Iteration
$i = 1;
 
foreach ($CSVVolume in $CSVVolumes)
{	
	# Create Time Guid
	$TimeGuid = (Get-Date).ToString("ddMMyyyyhhmmss")
 
	# Change CSV Volume Name
	$CSVVolume | Rename-Item -NewName "CSVolume$TimeGuid$i"
 
	# Update Iteration
	$i++
}
 
# Read Updated CSV Directories
$CSVVolumes = Get-ChildItem "C:\ClusterStorage"
 
foreach ($CSVVolume in $CSVVolumes)
{
	# Get CSV Volume Name
	$CSVVolumeName = $CSVVolume.Name
 
	# Get CSV Volume Filter
	$CSVVolumeFilter = "*.CSV"
 
	# Get CSV Path
	$CSVPath = $CSVVolume.FullName
 
	# Find CSV Identifier
	$CSVIdentifier = $Null;
	$CSVIdentifier = (Get-ChildItem "$CSVPath" -Filter "$CSVVolumeFilter" -Recurse).Name
	$CSVIdentifier = $CSVIdentifier.Split(".")[0]
 
	if ($CSVIdentifier)
	{
		# CSV Volume ID
		$NewCSVVolumeName = "Volume" + $CSVIdentifier.Substring("0,6")
 
		# Change CSV Volume Name
		$CSVVolume | Rename-Item -NewName "$NewCSVVolumeName"
	}
	else
	{
		Write-Host "Error: Could not find CSV Identifier for $CSVVolume"
	}
}
 
# Get All Cluster Nodes
$ClusterNodes = Get-Cluster | Get-ClusterNode
 
if ($ClusterNode in $ClusterNodes)
{
	Invoke-Command -ComputerName $ClusterNode -ScriptBlock {
 
		# Start Hyper-V Management Service
		Set-Service "vmms" -StartupType Automatic
		Start-Service "vmms"
	}
}
 
# Get VM Import Config
$VMImportConfig = Get-Content "C:\ClusterStorage\Volume1\VMExport.Config"
 
foreach ($VM in $VMImportConfig)
{
	# Import Virtual Machine
	$ImportVM = Import-VM $VM
 
	# Get Virtual Machine Name
	$VMName = $ImportVM.Name
 
	# Add VM to Failover Cluster
	Add-VMToCluster $VMName
}

After that, you will be able to start your virtual machines.