{"id":1947,"date":"2014-02-24T00:01:00","date_gmt":"2014-02-24T00:01:00","guid":{"rendered":"https:\/\/blogs.technet.microsoft.com\/heyscriptingguy\/2014\/02\/24\/using-powershell-to-migrate-dhcp-servers-part-1\/"},"modified":"2014-02-24T00:01:00","modified_gmt":"2014-02-24T00:01:00","slug":"using-powershell-to-migrate-dhcp-servers-part-1","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/scripting\/using-powershell-to-migrate-dhcp-servers-part-1\/","title":{"rendered":"Using PowerShell to Migrate DHCP Servers: Part 1"},"content":{"rendered":"<p><b>Summary<\/b>: Microsoft PFE, Ian Farr, talks about using Windows PowerShell to migrate DHCP servers.<\/p>\n<p>Microsoft Scripting Guy, Ed Wilson, is here. Today we welcome back guest blogger, <a href=\"https:\/\/devblogs.microsoft.com\/scripting\/tag\/ian-farr\/\" target=\"_blank\">Ian Farr<\/a>.<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-1.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-1.png\" alt=\"Image of slogan\" title=\"Image of slogan\" \/><\/a><\/p>\n<h2>Episode 1: &nbsp;A New Hope<\/h2>\n<p>In a galaxy very, very near to here, when you are not cleaning-up droids, you administer a DHCP infrastructure in Windows Server 2003 with two servers in a <a href=\"http:\/\/support.microsoft.com\/kb\/280473\">split scope<\/a> configuration. Because extended support for Windows Server 2003 ends on the July 14, 2015, you&rsquo;ve read about the new features in Windows Server&nbsp;2012, and you want some DHCP failover goodness! (For more information, see <a href=\"http:\/\/technet.microsoft.com\/en-us\/library\/hh831385.aspx\" target=\"_blank\">Step-by-Step: Configure DHCP for Failover<\/a>.)<\/p>\n<p>So&hellip;how do you <b>seamlessly<\/b> migrate your current DHCP infrastructure, combining the split scopes into a load-balanced failover relationship? And how, on a desert-planet-in-a-binary-star-system, can the PowerShell help out?<\/p>\n<p>I&rsquo;ll answer with an example migration process:<\/p>\n<ol>\n<li>Transfer the configuration from the DHCP servers running Windows&nbsp;2003 to two newly-prepared DHCP servers running Windows Server&nbsp;2012.<\/li>\n<li>Compare the DHCP server configuration on the new servers.<\/li>\n<li>Compare the DHCP scope settings on the DHCP servers running Windows Server&nbsp;2012.<\/li>\n<li>Configure a load-balanced failover relationship between the DHCP servers running Windows Server&nbsp;2012.<\/li>\n<li>Activate the two servers running Windows Server&nbsp;2012 in Active Directory.<\/li>\n<\/ol>\n<p><b><a href=\"https:\/\/msdnshared.blob.core.windows.net\/media\/TNBlogsFS\/prod.evol.blogs.technet.com\/CommunityServer.Blogs.Components.WeblogFiles\/00\/00\/00\/76\/18\/Capture.PNG\"><img decoding=\"async\" src=\"https:\/\/msdnshared.blob.core.windows.net\/media\/TNBlogsFS\/prod.evol.blogs.technet.com\/CommunityServer.Blogs.Components.WeblogFiles\/00\/00\/00\/76\/18\/Capture.PNG\" alt=\"Image of flow chart\" title=\"Image of flow chart\" \/><\/a><br \/><\/b><\/p>\n<p><b>Figure 1<\/b>&nbsp; Migration overview<\/p>\n<p>Windows PowerShell is what gives scripters their power. You must learn the ways of the PowerShell if you are to implement a DHCP infrastructure in Windows Server&nbsp;2012. Let&rsquo;s begin our scripter training by looking at the first two migration steps&hellip;<\/p>\n<p><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-2.jpg\" alt=\"Image of capsule\" title=\"Image of capsule\" \/><\/p>\n<h2>Step 1: Migration tools<\/h2>\n<p>The migration tools you are looking for are the Windows PowerShell-based Windows Server Migration Tools. They are awesome! Need I say more? Well, yes&hellip;<\/p>\n<p>On each of the servers running Windows Server 2003, the Windows Server Migration Tools capture the DHCP configuration as separate images. Each image is then imported to the corresponding DHCP server running Windows Server&nbsp;2012. No need to worry about transferring from a 32-bit host to a 64-bit host. Apart from some initial configuration, it&rsquo;s as simple as that!<\/p>\n<p>Here&rsquo;s how you list the features available for export on the source servers:<\/p>\n<p style=\"margin-left:30px\">Get-SmigServerFeature<\/p>\n<p>For example:<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-3.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-3.png\" alt=\"Image of command output\" title=\"Image of command output\" \/><\/a><\/p>\n<p>Here&rsquo;s a sample export command:<\/p>\n<p style=\"margin-left:30px\">Export-SmigServerSetting -FeatureID &quot;DHCP&quot; -Path &quot;c:\\smig_export_dhcp&quot; -Verbose<\/p>\n<p>And here&rsquo;s a sample import command for the target servers:<\/p>\n<p style=\"margin-left:30px\">Import-SmigServerSetting -FeatureID &quot;DHCP&quot; -Path &quot;c:\\smig_import_dhcp&quot; -Verbose -Force<\/p>\n<p><b>Note<\/b>&nbsp;&nbsp;Add the DHCP server role to the servers running Windows Server&nbsp;2012 before you import the migration image to ensure that the management tools are present.<\/p>\n<p>For more information about the initial configuration of the Windows Server Migration Tools, see <a href=\"http:\/\/technet.microsoft.com\/library\/jj134202\" target=\"_blank\">Install, Use, and Remove Windows Server Migration Tools<\/a>.<span style=\"text-decoration:underline\"><\/span><\/p>\n<h2>Step 2: DHCP server comparison script<\/h2>\n<p>Are you a little short on DHCP server comparison script? On with the scripter training&hellip;<\/p>\n<p>Before you add DHCP host servers to a failover relationship, it&rsquo;s good practice to ensure that the server settings are consistent. I wrote a script to produce an Excel report that highlights discrepancies between two DHCP servers. You can download it here: <a href=\"http:\/\/gallery.technet.microsoft.com\/scriptcenter\/Compare-DHCP-Server-9ecf5f26\/file\/97941\/2\/Compare_DHCP_Server_Settings.ps1\" target=\"_blank\">Compare DHCP Server Settings with PowerShell DHCP Cmdlets<\/a>.<\/p>\n<p>The script performs a number of checks, and the results of each test are written to a separate worksheet.<\/p>\n<ul>\n<li>Matching objects are presented side by side in yellow and&nbsp;turquoise for ease of comparison<\/li>\n<\/ul>\n<p style=\"margin-left:30px\"><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-4.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-4.png\" alt=\"Image of worksheet\" title=\"Image of worksheet\" \/><\/a><\/p>\n<ul>\n<li>For matching objects, specific property discrepancies have the property name highlighted in red.<\/li>\n<li>Objects that are unique to one DHCP server are highlighted in green (for DHCP server 1) or in orange (for DHCP server 2). These entries appear at the end of the relevant worksheet.<\/li>\n<\/ul>\n<p>How do we generate the report content? Use Windows PowerShell, young scriptwalker!<\/p>\n<h3>DHCP server module for Windows PowerShell<\/h3>\n<p>There are 103 cmdlets in the DHCP server module for Windows PowerShell, which was introduced with Windows Server&nbsp;2012 and Windows PowerShell&nbsp;3.0. The script uses 10 of these cmdlets to jump to hyperspace to compare server settings:<\/p>\n<ul>\n<li>Get-DhcpServerAuditLog<\/li>\n<li>Get-DhcpServerDatabase<\/li>\n<li>Get-DhcpServerSetting<\/li>\n<li>Get-DhcpServerVersion<\/li>\n<li>Get-DhcpServerv4Class<\/li>\n<li>Get-DhcpServerv4DnsSetting<\/li>\n<li>Get-DhcpServerv4FilterList<\/li>\n<li>Get-DhcpServerv4OptionDefinition<\/li>\n<li>Get-DhcpServerv4OptionValue<\/li>\n<li>Get-DhcpServerv4Policy<\/li>\n<\/ul>\n<p>The Compare_DHCP_Server_Settings.ps1 script has a &ldquo;control panel&rdquo; (as shown in Figure 2) to determine which checks are included when the script is executed.<\/p>\n<p><b><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/7752.hsg-2-24-14-5.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/7752.hsg-2-24-14-5.png\" alt=\"Image of control panel\" title=\"Image of control panel\" \/><\/a><\/b><\/p>\n<p><b>Figure 2<\/b>&nbsp;&nbsp;Control panel used by script<\/p>\n<p>Hmmm, if only my script control panel looked more like the one in Figure 3!<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-6.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-6.png\" alt=\"Image of circuit board\" title=\"Image of circuit board\" \/><\/a><\/p>\n<p><b>Figure 3<\/b>&nbsp;&nbsp;Dream control panel<\/p>\n<p>Where was I? Oh, yes&hellip;<\/p>\n<p>Scripter training. Each of the included checks is executed against the two DHCP server names that were passed as script parameters.<\/p>\n<p>The checks are part of an array that is looped through <b>$Checks<\/b>. A <b>Switch<\/b> statement is used to evaluate each iterated check. Why? Some of the cmdlets return a single object; some cmdlets return multiple objects. A different function is used to perform the object comparison in each of these scenarios.<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ForEach ($Check in $Checks) {<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp; Switch ($Check) {<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &quot;DhcpServerAuditLog&quot; {$Single = $True}<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &quot;DhcpServerv4Class&quot; {$Single = $False; $ComparisonProperty = &quot;Name&quot;}<\/p>\n<p>Where a cmdlet returns a single object<b>, $Single<\/b> is set to True. Where a cmdlet returns multiple objects, <b>$Single<\/b> is False, and a common comparison property for the resultant objects is defined (more about this later).<\/p>\n<p>With the current check matched by <b>Switch<\/b>, <b>$Single<\/b> is tested to define the function to call. The test also determines what parameter values get passed to the function by a technique called splatting. If you&rsquo;ve not seen splatting before, it&rsquo;s used to pass parameter values as a single entity (use <b>Get-Help<\/b> to find more about splatting).<\/p>\n<p>In the script, the splatted parameter values are defined in a hash table.<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp; If ($Single) {<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #Splatted parameters<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Parameters = @{<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DhcpCmdlet = &quot;Get-$Check&quot;<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DhcpServer1 = $DhcpServer1<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DhcpServer2 = $DhcpServer2<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SheetNumber = $i<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SheetName = $Check<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }&nbsp;&nbsp; #End of $Parameters<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #Target function<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Function = &quot;Compare-SingleObject&quot;<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp; }&nbsp;&nbsp; #End of If ($Single)&#8230;<\/p>\n<p>Where <b>$Single<\/b> is false, an additional property is added to the splatted parameters. This is the <b>$ComparisonProperty<\/b> mentioned earlier:<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp; Else {<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #Splatted parameters<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Parameters = @{<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DhcpCmdlet = &quot;Get-$Check&quot;<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DhcpServer1 = $DhcpServer1<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DhcpServer2 = $DhcpServer2<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SheetNumber = $i<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SheetName = $Check<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ComparisonProperty = $ComparisonProperty<\/p>\n<p style=\"margin-left:30px\">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp;}&nbsp;&nbsp; #End of $Parameters<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; #Target function<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Function = &quot;Compare-MultipleObjects&quot;<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp; }&nbsp;&nbsp; #End of Else ($Single)&#8230;<\/p>\n<p>With <b>$Parameters<\/b> and <b>$Function<\/b> defined, the comparison check is executed:<\/p>\n<p style=\"margin-left:30px\">&amp;$Function @Parameters<\/p>\n<p>There are two things to note here. The first is the use of the call operator, <b>&amp;<\/b>, to invoke the stored function. Without this, <b>Compare-SingleObject<\/b> or <b>Compare-MultipleObjects<\/b> are returned as strings. The second is that <b>$Parameters<\/b> becomes <b>@Parameters<\/b>. <b>@ <\/b>means splat!<\/p>\n<p>The <b>Compare-SingleObject<\/b> function calls the current check, <b>$DhcpCmdlet<\/b>, against each DHCP server and stores the results in a variable:<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp; $Output1 = &amp;$DhcpCmdlet -ComputerName $DhcpServer1<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp; $Output2 = &amp;$DhcpCmdlet -ComputerName $DhcpServer2<\/p>\n<p>A list of property names for the resultant object type is then retrieved:<\/p>\n<p style=\"margin-left:30px\">$Properties = ($Output1[0] | Get-Member -Type Properties).Name&nbsp;<\/p>\n<p>Each property from each server is compared:<\/p>\n<p style=\"margin-left:30px\">ForEach ($Property in $Properties) {<\/p>\n<p style=\"margin-left:30px\">$Result = Compare-Object -ReferenceObject $Output1 -DifferenceObject $Output2 -IncludeEqual -Property $Property<\/p>\n<p style=\"margin-left:30px\">If they don&rsquo;t match, the property name in the Excel report is marked as red:<\/p>\n<p style=\"margin-left:30px\">If ($Result.SideIndicator -ne &quot;==&quot;) {<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp; $ExcelSheet.Cells.Item($j,1).Interior.ColorIndex = 3<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }&nbsp;&nbsp; #End of If ($Result.SideIndicator -ne &quot;==&quot;)<\/p>\n<p style=\"margin-left:30px\">Compare-MultipleObjects<\/p>\n<p>The <b>Compare-MultipleObejcts<\/b> function takes an extra parameter&mdash;a comparison property for the DHCP cmdlet executed. Here&rsquo;s how the function works&hellip;<\/p>\n<p>As with the <b>Compare-SingleObject<\/b> function, the check is executed against both servers, and a list of property names for the resultant objects are stored in a variable. This time the returned array of objects are compared with the aid of the comparison property. It is important that the selected <b>$ComparisonProperty<\/b> always have a value.<\/p>\n<p style=\"margin-left:30px\">$Comparison = Compare-Object -ReferenceObject $Output1 -DifferenceObject $Output2 -IncludeEqual -Property $ComparisonProperty<\/p>\n<p>Now, we need to deal with the fact that some objects might be on both servers, some objects on only the first DHCP server, and some objects on only the second DHCP server.<\/p>\n<p>To check for objects present on both servers, test for the equals indicator, <b>==<\/b>, from the comparison results:<\/p>\n<p style=\"margin-left:30px\">If ($Comparison.SideIndicator -Contains &quot;==&quot;) {<\/p>\n<p>Where objects are present on both servers, write the details to a <b>$Results<\/b> variable, and continue to use the comparison property as the common reference:<\/p>\n<p style=\"margin-left:30px\">$Results = $Comparison | Where-Object {$_.SideIndicator -eq &quot;==&quot;} | Select $ComparisonProperty<\/p>\n<p>Loop through each mutual object and rerun the current check again against a specific iteration of <b>$Result.$ComparisonProperty<\/b> on both servers:<\/p>\n<p style=\"margin-left:30px\">ForEach ($Result in $Results) {<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Value1 = &amp;$DhcpCmdlet $Result.$ComparisonProperty -ComputerName $DhcpServer1<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Value2 = &amp;$DhcpCmdlet $Result.$ComparisonProperty -ComputerName $DhcpServer2<\/p>\n<p>Then, as with <b>Compare-SingleObject<\/b>, loop through each of the object&rsquo;s properties and compare the value from each server. Highlight discrepancies in red, for example:<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-7.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-7.png\" alt=\"Image of worksheet\" title=\"Image of worksheet\" \/><\/a><\/p>\n<p>Next, check for objects that are present only on the first DHCP server. Test for the left side indicator (<b>&lt;=<\/b>):<\/p>\n<p style=\"margin-left:30px\">If ($Comparison.SideIndicator -Contains &quot;&lt;=&quot;) {<\/p>\n<p>Run the current DHCP cmdlet against the first DHCP server:<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $Value1 = &amp;$DhcpCmdlet $Result.$ComparisonProperty -ComputerName $DhcpServer1<\/p>\n<p>Loop through the properties and write them to the report. Highlight the Excel cells in green:<\/p>\n<p style=\"margin-left:30px\">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $ExcelSheet.Cells.Item($k,2).Interior.ColorIndex = 43<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-8.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-8.png\" alt=\"Image of worksheet\" title=\"Image of worksheet\" \/><\/a><\/p>\n<p>Finally, the check for objects that are present on only the second DHCP server has almost identical script to the first server check, except you are testing for the right-side indicator:<\/p>\n<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; If ($Comparison.SideIndicator -Contains &quot;=&gt;&quot;) {<\/p>\n<p>Loop through the properties, and write them to the report. Highlight the Excel cells in orange:<\/p>\n<p style=\"margin-left:30px\">$ExcelSheet.Cells.Item($j,3).Interior.ColorIndex = 44<\/p>\n<p><a href=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-9.png\"><img decoding=\"async\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/hsg-2-24-14-9.png\" alt=\"Image of worksheet\" title=\"Image of worksheet\" \/><\/a>&nbsp;<\/p>\n<p>Upon completion, you&rsquo;ll have an Excel spreadsheet in the same folder as the script, which is saved in the following format:<\/p>\n<p style=\"margin-left:30px\">&lt;YearMonthDayHourMinuteSecond&gt;_&lt;DhcpServer1&gt;_&lt;DhcpServer2&gt;_DHCP_Server_Comparison.xls<\/p>\n<p>Analyse the report and perform appropriate configuration changes to bring the servers in line. Pay particular attention to classes, option definitions, and option values. And please let me know if you spot a two meter-wide exhaust port!<\/p>\n<p>Well, that&rsquo;s it for Episode 1. Sadly, there are no huge explosions or fancy award ceremonies to finish with. However, our DHCP data from our server running Windows Server&nbsp;2003 is now seamlessly migrated to our DHCP servers running Windows Server&nbsp;2012, and we&rsquo;ve compared and corrected any errant settings. In Episode 2, we&rsquo;ll complete our scripter training and the migration process.<\/p>\n<p>May the PowerShell be with you!<\/p>\n<p>~Ian<\/p>\n<p>Thanks, Ian! Our DHCP migration lesson will continue tomorrow with Ian returning to conclude his series.<\/p>\n<p>I invite you to follow me on <a href=\"http:\/\/bit.ly\/scriptingguystwitter\" target=\"_blank\">Twitter<\/a> and <a href=\"http:\/\/bit.ly\/scriptingguysfacebook\" target=\"_blank\">Facebook<\/a>. If you have any questions, send email to me at <a href=\"mailto:scripter@microsoft.com\" target=\"_blank\">scripter@microsoft.com<\/a>, or post your questions on the <a href=\"http:\/\/bit.ly\/scriptingforum\" target=\"_blank\">Official Scripting Guys Forum<\/a>. See you tomorrow. Until then, peace.<\/p>\n<p><b>Ed Wilson, Microsoft Scripting Guy<\/b>&nbsp;<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Summary: Microsoft PFE, Ian Farr, talks about using Windows PowerShell to migrate DHCP servers. Microsoft Scripting Guy, Ed Wilson, is here. Today we welcome back guest blogger, Ian Farr. Episode 1: &nbsp;A New Hope In a galaxy very, very near to here, when you are not cleaning-up droids, you administer a DHCP infrastructure in Windows [&hellip;]<\/p>\n","protected":false},"author":596,"featured_media":87096,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[218,56,472,37,3,45],"class_list":["post-1947","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-scripting","tag-dhcp-server","tag-guest-blogger","tag-ian-farr","tag-networking","tag-scripting-guy","tag-windows-powershell"],"acf":[],"blog_post_summary":"<p>Summary: Microsoft PFE, Ian Farr, talks about using Windows PowerShell to migrate DHCP servers. Microsoft Scripting Guy, Ed Wilson, is here. Today we welcome back guest blogger, Ian Farr. Episode 1: &nbsp;A New Hope In a galaxy very, very near to here, when you are not cleaning-up droids, you administer a DHCP infrastructure in Windows [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts\/1947","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/users\/596"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/comments?post=1947"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts\/1947\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/media\/87096"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/media?parent=1947"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/categories?post=1947"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/tags?post=1947"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}