10 Replies Latest reply on Feb 14, 2012 6:07 AM by bgallagher72

    PowerCLI to change network from standard vSwitch to Distributed vSwitch

    bgallagher72 Novice

      I am working on a deployment script to build my VMs from a template. After its built I need to change the network over to a dvSwitch. I need help to figure out the correct syntex.

       

      This did not work:

      $vmname = test2008_11

      $vlan = XXX_XX_57_x

      Get-vm $vmname | Get-NetworkAdapter | Set-NetworkAdapter -StartConnected $true -DistributedSwitch dvSwitch1 -NetworkName $vlan -Confirm:$false

       

      Here is the info from powerCLI

       

      PowerCLI > Get-VirtualSwitch -Name dvSwitch1

       

      Name            NumPorts   Num Ports  Mtu   Key                            Notes
                                 Available
      ----            --------   ---------- ---   ---                            -----
      dvSwitch1       2474                  1500  cf b2 12 50 f2 a5 1c b5-64 ...


      PowerCLI C:\Users\bxg4211\Documents\PowerCli\Deploy> Get-VirtualSwitch -Name dvSwitch1 | Get-VirtualPortGroup

       

      Name                      Key                            VLanId PortBinding NumPorts
      ----                      ---                            ------ ----------- --------
      XXX_XX_61_x               dvportgroup-12662                     Static      128
      XXX_XX_50_x               dvportgroup-12676                     Static      128
      XXX_XX_44_x               dvportgroup-12675                     Static      128
      dvSwitch1-DVUplinks-12654 dvportgroup-12655                     Static      42
      XXX_XX_00_x               dvportgroup-12664                     Static      128
      XXX_XX_40_x               dvportgroup-12674                     Static      128
      XXX_XX_60_x               dvportgroup-12680                     Static      128
      XXX_XX_01_x               dvportgroup-12665                     Static      128
      XXX_XX_14_x               dvportgroup-12673                     Static      128
      XXX_XX_02_x               dvportgroup-12666                     Static      128
      XXX_XX_13_x               dvportgroup-12672                     Static      128
      XXX_XX_03_x               dvportgroup-12667                     Static      128
      XXX_XX_12_x               dvportgroup-12671                     Static      128
      XXX_XX_56_x               dvportgroup-12679                     Static      128
      XXX_XX_04_x               dvportgroup-12668                     Static      128
      XXX_XX_11_x               dvportgroup-12670                     Static      128
      XXX_XX_57_x               dvportgroup-12678                     Static      128
      dvSwitch1 All             dvportgroup-12661                     Static      128
      XXX_XX_10_x               dvportgroup-12669                     Static      128
      XXX_XX_54_x               dvportgroup-12677                     Static      128

       

      The names and Ps have been changed to protect the innocents.

        • 1. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
          LucD Guru
          Community WarriorsvExpertUser Moderators

          To change a connection to a dvSwitch you'll have to use the dvSwitch and the PortKey parameter only.

           

          Get-vm $vmname | Get-NetworkAdapter | 
          Set-NetworkAdapter -StartConnected $true -DistributedSwitch dvSwitch1 -PortKey 123 -Confirm:$false

          The  only problem is to find the free portkeys on the dvSwitch portgroup

          Let me know if you need a routine for that ?

          1 person found this helpful
          • 2. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
            bgallagher72 Novice

            That helps.

             

            If you have a routine to find the next open portkey that would be greatly helpful.

            • 3. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
              bgallagher72 Novice

              Where does the netowrk name come into play? I have many portgroups on the one dvSwitch. How do I specify which one to use?

              • 4. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                bgallagher72 Novice

                That helps.

                 

                If you have a routine to find the next open portkey that would be greatly helpful.

                • 5. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                  LucD Guru
                  vExpertCommunity WarriorsUser Moderators

                  On the portgroup the script finds all the available ports.

                  Then it checks all the VMs that have already a connection to that portgroup and removes that portkey from the list.

                   

                  I keep the portkeys in a hash table because that makes it easy to remove entries.

                   

                  $nicTypes = "VirtualE1000","VirtualE1000e","VirtualPCNet32","VirtualVmxnet","VirtualVmxnet2","VirtualVmxnet3" 
                  $ports
                  = @{}
                  $pgName = "MyPG"

                  #
                  Get all the portkeys on the portgroup
                  $pg
                  = Get-VirtualPortGroup -Distributed -Name $pgName
                  $pg
                  .ExtensionData.PortKeys | %{$ports.Add($_,$pg.Name)}

                  # Remove the portkeys in use
                  Get-View
                  $pg.ExtensionData.Vm | %{
                     
                  $nic = $_.Config.Hardware.Device |
                       
                  where {$nicTypes -contains $_.GetType().Name -and $_.Backing.GetType().Name -match "Distributed"}
                     
                  $nic | %{$ports.Remove($_.Backing.Port.PortKey)}
                  }

                  # Assign the first free portkey
                  $key = ($ports.Keys | Sort-Object)[0]
                  • 6. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                    bgallagher72 Novice

                    I get the following errors while trying to run this:

                     

                    Exception calling "Remove" with "1" argument(s): "Key cannot be null.
                    Parameter name: key"
                    At \DeployFromTemplatetest.ps1:127 char:29
                    +             $nic | %{$ports.Remove <<<< ($_.Backing.Port.PortKey)}
                        + CategoryInfo          : NotSpecified: (:) [], MethodInvocationException
                        + FullyQualifiedErrorId : DotNetMethodException

                     

                    Is this nrmal? Seems that it is still getting the next avaliable port number.

                    • 7. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                      LucD Guru
                      Community WarriorsvExpertUser Moderators

                      Although I don't understand why this can happen, you seem to have some NICs that are connected to a dvSwitch portgroup but that do not have a portkey. We can filter those out with a Where-clause.

                      See if this variation runs error-free

                       

                      $nicTypes = "VirtualE1000","VirtualE1000e","VirtualPCNet32","VirtualVmxnet","VirtualVmxnet2","VirtualVmxnet3" 
                      $ports = @{}
                      $pgName = "MyPG"

                      # Get all the portkeys on the portgroup
                      $pg = Get-VirtualPortGroup -Distributed -Name $pgName
                      $pg.ExtensionData.PortKeys | %{$ports.Add($_,$pg.Name)}

                      # Remove the portkeys in use Get-View
                      $pg
                      .ExtensionData.Vm | %{
                         
                      $nic = $_.Config.Hardware.Device |
                           
                      where {$nicTypes -contains $_.GetType().Name -and $_.Backing.GetType().Name -match "Distributed"}
                         
                      $nic | where {$_.Backing.Port.PortKey} | %{$ports.Remove($_.Backing.Port.PortKey)}
                      }

                      # Assign the first free portkey
                      $key
                      = ($ports.Keys | Sort-Object)[0]
                      $key
                      • 8. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                        bgallagher72 Novice

                        I am not sure whats going on but it looks like it is choosing the first used port. I ran it both ways and the port for $key is the first used one in the port group. So when I try and setup a VM using it I get port is in use. I am also getting a bunch of errors but it still give me a key. Is there anyway to find the first unused port and at leat suppress the errors?

                         

                        PowerCLI > get-vm -Name test2008_14 | Get-NetworkAdapter | Set-NetworkAdapter -StartConn
                        ected $true -DistributedSwitch dvswitch1 -portkey 2055

                         

                        Confirm
                        Are you sure you want to perform this action?
                        Performing operation "Setting StartConnected: True" on Target "Network adapter 1".
                        [Y] Yes  [A] Yes to All  [N] No  [L] No to All  [S] Suspend  [?] Help (default is "Y"): y
                        Set-NetworkAdapter : 2/14/2012 8:33:21 AM    Set-NetworkAdapter        The specified port '2055' does not exists or it's not avai
                        lable for vnic connection.
                        At line:1 char:67
                        + get-vm -Name test2008_14 | Get-NetworkAdapter | Set-NetworkAdapter <<<<  -StartConnected $true -DistributedSwitch dvswitch1 -po
                        rtkey 2055
                            + CategoryInfo          : InvalidArgument: (:) [Set-NetworkAdapter], InvalidArgument
                            + FullyQualifiedErrorId : Client20_VirtualNetworkServiceImpl_TryGetAvailableDVPortGroup_PortNotFound,VMware.VimAutomation.Vi
                           Core.Cmdlets.Commands.VirtualDevice.SetNetworkAdapter

                         

                        Hear is the errors that I get while running the script, multiple times.


                        C:\Users\XXXXXXXX\Documents\PowerCli\Deploy\DeployFromTemplate2.ps1:123 char:46
                                       where {$nicTypes -contains $_.GetType <<<< ().Name -and $_.Backing.GetType().Name -match "Distributed"}
                           + CategoryInfo          : InvalidOperation: (GetType:String) [], RuntimeException
                           + FullyQualifiedErrorId : InvokeMethodOnNull

                         

                        The part of the script I am using to connect the VM to the DVS.

                         

                             #Get Free DVS port
                                $nicTypes = "VirtualE100","VirtualE100e","VirtualPCNet32","VirtualVmxnet","VirtualVmxnet2","VirtualVmxnet3"
                                $ports = @{}
                                $pgName = "XXX_XX_57_x"

                         

                                # Get all the portkeys on the portgroup 
                                $pg = Get-VirtualPortGroup -Distributed -Name $pgName
                                $pg.ExtensionData.PortKeys | %{$ports.Add($_,$pg.Name)}

                         

                                # Remove the portkeys in use  Get-View
                                $pg.ExtensionData.Vm | %{
                                    $nic = $_.Config.Hardware.Device |
                                      where {$nicTypes -contains $_.GetType().Name -and $_.Backing.GetType().Name -match "Distributed"}
                                    $nic | where {$_.Backing.Port.PortKey} | %{$ports.Remove($_.Backing.Port.PortKey)}
                                }

                         

                                # Assign the first free portkey
                                $key = ($ports.Keys | Sort-Object)[0]
                                $key
                            #Connect to DVS
                            $VMStatus = GET-VM $vmname | Get-NetworkAdapter
                            if (!(($VMStatus.NetworkName -eq $vlan) -and (($VMStatus.ConnectionState).StartConnected -eq "False")))
                                {
                                    Get-VM -Name $vmname | Get-NetworkAdapter | Set-NetworkAdapter -StartConnected $true `
                                        -DistributedSwitch dvSwitch1 -PortKey $key -Confirm:$false
                                    Get-VM -Name $vmname
                                }

                        • 9. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                          LucD Guru
                          Community WarriorsUser ModeratorsvExpert

                          Looks like my nictypes where missing a zero in the "VirtualE1000" and "VirtualE1000e" types.

                          Did you have NIC of that type ?

                          If yes, can you try again ? I updated the scripts above.

                          1 person found this helpful
                          • 10. Re: PowerCLI to change network from standard vSwitch to Distributed vSwitch
                            bgallagher72 Novice

                            Awesome, the first script worked.

                             

                            Thanks so much for your help!