Mostrando entradas con la etiqueta Virtual. Mostrar todas las entradas
Mostrando entradas con la etiqueta Virtual. Mostrar todas las entradas

lunes, 28 de mayo de 2012

Balancear maquinas virtuales en un cluster con PowerShell

Otro Offtopic, pero no podía dejar de publicar este script de Powershell que hice para distribuir las virtuales en un cluster.
Primero vale aclarar que mis conocimientos de PowerShell son mínimos, y es un lenguaje que me resulta muy difícil de entender y aprender. Vengo del mundo de la programación dura y estructurada, y PowerShell se toma demasiadas "licencias" para mi gusto, por lo que me resulta difícil entender su comportamiento muchas veces.
Aún así hice este sencillo script cuya tarea es bastante simple. Lo que hace es contar el número de maquinas virtuales en un cluster y distribuirlas entre todos los nodos. El "balanceo" no tiene en cuenta recursos, ni nada parecido, es simplemente un conteo de virtuales, pero en mi caso y dentro de nuestra infraestructura resulta bastante útil.

Aquí el script:


Import-Module FailoverClusters

$Cluster=""

$Cluster = Read-Host "Indique nombre del cluster"

$Total=(Get-ClusterResource -cluster $Cluster | where {$_.resourcetype.name -eq "Virtual Machine"}).Count

$Nodos=Get-ClusterNode -cluster $Cluster

$CantNodos=(Get-ClusterNode -cluster $Cluster).count

Write-host "El cluster $Cluster tiene un total de $Total maquinas virtuales a distribuir en $CantNodos nodos."

$Promedio=[MATH]::ROUND($Total/$CantNodos)

Write-host "En total debería haber $Promedio maquinas virtuales por nodo."

Foreach ($Nodo in $Nodos)

{

    $PorNodo=(Get-ClusterNode $Nodo.Name -cluster $Cluster | Get-ClusterResource | where {$_.resourcetype.name -eq "Virtual Machine"}).count

    Write-Host "El nodo $Nodo tiene $PorNodo maquinas virtuales"

    if ($PorNodo -gt $Promedio)

        {

        $Diferencia=$PorNodo-$Promedio

        Write-Host "Se debe mover $Diferencia maquina/s virtual/es del nodo $Nodo"

        for($i=1; $i -le $Diferencia; $i++)

            {

            Foreach ($Nodo1 in $Nodos)

                {

                $PorNodo1=(Get-ClusterNode $Nodo1.Name -cluster $Cluster | Get-ClusterResource | where {$_.resourcetype.name -eq "Virtual Machine"}).count

                if ($PorNodo1 -lt $Promedio)

                    {

                        $Maquina=Get-ClusterNode $Nodo.Name -cluster $Cluster | Get-ClusterResource | where {$_.resourcetype.name -eq "Virtual Machine"} | Select-object -first 1

                        Write Host "Se procede a mover la maquina virtual $Maquina"

                        Move-ClusterVirtualMachineRole -Name $Maquina.OwnerGroup -Cluster $Cluster -node "$Nodo1"
                        Break

                    }

                }

            }

        }



}


Como dije, no soy experto en PowerShell, y estoy seguro de que esto puede hacerse mejor, más fácil y con menos líneas de código. Pero esto funciona y lo hace muy bien.

Las máquinas virtuales se mueven utilizando LiveMigration, así que el uso del script no implica corte de servicios, y solo es válido en cluster de Hyper-V 2008 R2.

jueves, 19 de abril de 2012

Colección para maquinas virtuales

Hoy una query sencillita, pero que puede resultar bastante útil. En este caso armaremos una colección dinámica poblada exclusivamente por maquinas virtuales.

La query para la colección sería esta:

select 
SMS_R_SYSTEM.ResourceID,
SMS_R_SYSTEM.ResourceType,
SMS_R_SYSTEM.Name,
SMS_R_SYSTEM.SMSUniqueIdentifier,
SMS_R_SYSTEM.ResourceDomainORWorkgroup,
SMS_R_SYSTEM.Client 
from SMS_R_System inner join 
SMS_G_System_COMPUTER_SYSTEM 
on SMS_G_System_COMPUTER_SYSTEM.ResourceId = SMS_R_System.ResourceId 
where SMS_G_System_COMPUTER_SYSTEM.Model in 
("Virtual Machine","VMware Virtual Platform")

En este caso agrupamos en la misma colección las maquinas virtuales creadas con software de Microsoft ("Virtual Machine") y aquellas que utilizan VMWare ("VMWare Virtual Platform").

Esta consulta puede armarse usando el asistente del SCCM, y no reviste mayor complejidad.



Del mismo modo, puede usarse una query similar, pero negando el operador "IN" para encontrar todas las computadoras que no son virtuales, las "físicas", por llamarlas de algún modo.

select 
SMS_R_SYSTEM.ResourceID,
SMS_R_SYSTEM.ResourceType,
SMS_R_SYSTEM.Name,
SMS_R_SYSTEM.SMSUniqueIdentifier,
SMS_R_SYSTEM.ResourceDomainORWorkgroup,
SMS_R_SYSTEM.Client 
from SMS_R_System inner join 
SMS_G_System_COMPUTER_SYSTEM 
on SMS_G_System_COMPUTER_SYSTEM.ResourceId = SMS_R_System.ResourceId 
where SMS_G_System_COMPUTER_SYSTEM.Model NOT IN 
("Virtual Machine","VMware Virtual Platform")

Como siempre que armamos colecciones dinámicas, es importante no olvidar crear un schedule para la actualización de los recursos, y en el caso de SCCM 2007 R3, tildar la opción para agregar recursos dinámicamente.

Saludos
Franco