Hej alle, jeg vil dele en simpel vejledning "Hvordan man kan stoppe med at pinge en håndfuld hoste manuelt. Uden registrering og SMS!".
Fra Internettets vidder
Det er vigtigt: Jeg er hverken programmør eller systemadministrator, men jeg arbejder ofte med et stort antal servere og tjenester, og dette script skrev jeg for min egen bekvemmelighed.
Hvis nogle kunne finde dette nyttigt, så kig her.
Hvorfor PowershellJeg har erfaring med at skrive simple programmer i Python, men det kræver enten en installeret fortolker eller retten til at køre .exe-filer, hvilket ikke altid er muligt i mit arbejde. Men et script i Powershell kan ofte finde en måde at køre på.
Ikke alle kan lide konsollen/terminalen
Jeg tror ikke, der er nogen modstrid; ellers ville alle stadig bruge konsolbaserede e-mailklienter, og GUI'en ville ikke være blevet introduceret i *nix-systemer.
Da jeg i hverdagen bruger Powershell ret primitivt, forsøgte jeg først at finde ud af, om man kunne tilføje GUI til det. Det viser sig, at det er muligt, og ret enkelt:

Add-Type -assembly System.Windows.Forms #Tilslut biblioteket
$main_form = New-Object System.Windows.Forms.Form #Opretter et objekt med vores "vindue"
#Sætter parametre for det
$main_form.Text ='Links op' #Titel i overskriften
$main_form.Width = 300 #Bredde på vinduet
$main_form.Height = 200 #Højde på vinduet
$main_form.AutoSize = $true #Giver det mulighed for automatisk at ændre størrelse, hvis nødvendigt
$main_form.ShowDialog() #Kalder "vinduet"
Tilføjer et output-element til dette og får et grundlæggende Windows-vindue; tautologi?

Add-Type -assembly System.Windows.Forms #Tilslut biblioteket
$main_form = New-Object System.Windows.Forms.Form #Opretter en variabel med vores "vindue"
#Indstiller parametre for vinduet
$main_form.Text ='Links op' #Titel på vinduet
$main_form.Width = 300 #Bredde på vinduet
$main_form.Height = 200 #Højde på vinduet
$main_form.AutoSize = $true #Lader det ændre størrelse automatisk efter behov
$Label = New-Object System.Windows.Forms.Label #Alle elementer af formen vil blive gemt i variable, men de er faktisk objekter ligesom andre variable i Powershell
$Label.Text = "Hej! Jeg er et simpelt Windows-vindue; hvad har du opnået?" #Den viste tekst
$Label.Location = New-Object System.Drawing.Point(10,65) #Positionen af objektet inden for vinduet (x,y)
$Label.AutoSize = $true
$main_form.Controls.Add($Label) #Tilføjer det oprettede objekt til vinduet, så det ikke går tabt under kørsel af scriptet
$main_form.ShowDialog() #Åbner det enkle vindueLad os tilføje noget dynamik
Det værktøj, hvor jeg "pingede Yandex" og monterede *.iso, har fået et separat GUI, men det er ikke nok. På samme måde kan man vise information om tilgængelighed, men for overvågning skal scriptet genstartes hver gang.
Lad os først tegne to ikoner og tilføje muligheden for at vise billeder.

$PictureBox = New-Object system.Windows.Forms.PictureBox #Objektet til at vise billeder kaldes rimeligt
$PictureBox.width = 10
$PictureBox.height = 10
$PictureBox.location = New-Object System.Drawing.Point(178,12)
#Her går vi til sagen og binder det viste billede til resultatet af tilgængelighedstesten af værten ved hjælp af cmdlet'en
#<b>test-connection</b>, hvor:
#-Count - sender antallet af forespørgsler
#-computer - IP eller domænenavn til forespørgslen
#-quiet - så vi kun får et Boolean resultat
if ((test-connection -Count 1 -computer ya.ru -quiet) -eq $True) {
$PictureBox.imageLocation = "C:Testyes.png" #Objektet henviser til det tilsvarende billede
}
Else {
$PictureBox.imageLocation = "C:Testno.png" #Objektet henviser til det tilsvarende billede
}
$PictureBox.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$main_form.Controls.Add($PictureBox)
Vores DNS-folk laver ballade igen...

Og lad os også tilføje en knap, så vi kan opdatere aflæsningerne.

$Button = New-Object System.Windows.Forms.Button
$Button.Location = New-Object System.Drawing.Size(100,150)
$Button.Size = New-Object System.Drawing.Size(80,30)
$Button.Text = "Opdater"
# Tilknytter knaptrykkbegivenheden til hver PictureBox i henhold til den tidligere beskrevne logik
$Button.Add_Click({
if ((Test-Connection -Count 1 -computer ya.ru -quiet) -eq $True)
{$PictureBox.imageLocation = "C:Testyes.png"}
Else {$PictureBox.imageLocation = "C:Testno.png"}
if ((Test-Connection -Count 1 -computer 8.8.8.8 -quiet) -eq $True)
{$PictureBox1.imageLocation = "C:Testyes.png"}
Else {$PictureBox1.imageLocation = "C:Testno.png"}
})
$main_form.Controls.Add($Button)

Fantastisk, nu til produktion!?
Da jeg manuelt indtastede omkring halvd dozen hoste, indså jeg en ting — dette projekt vil ende, hosts vil ændre sig, og jeg vil skulle redigere scriptet hver gang. På den ene side er det ikke så slemt, dette er jo en løsning til mig selv. På den anden side, se på hvad der bliver skabt:
Synet er ikke for de sarte sjæle
Add-Type -assembly System.Windows.Forms #Vi tilslutter biblioteket
$main_form = New-Object System.Windows.Forms.Form #Vi opretter en variabel til vores "vindue"
#Vi angiver parametrene for det gennem parametre
$main_form.Text ='Links up' #Titel i vinduet
$main_form.Width = 300 #Bredde på vinduet
$main_form.Height = 200 #Højde på vinduet
$main_form.AutoSize = $true #Vi giver det mulighed for automatisk at ændre størrelse, hvis nødvendigt
$Label = New-Object System.Windows.Forms.Label #Alle formens elementer vil blive gemt i variabler, men det er faktisk objekter, ligesom alle andre variabler i Powershell
$Label.Text = "ya.ru ............................" #Udsendt tekst
$Label.Location = New-Object System.Drawing.Point(15,10) #Placering af objektet inden for formen horisontalt og vertikalt (x,y)
$Label.AutoSize = $true
$Label1 = New-Object System.Windows.Forms.Label #Alle formens elementer vil blive gemt i variabler, men det er faktisk objekter, ligesom alle andre variabler i Powershell
$Label1.Text = "8.8.8.8 ............................" #Udsendt tekst fra Googles DNS
$Label1.Location = New-Object System.Drawing.Point(15,30) #Placering af objektet inden for formen horisontalt og vertikalt (x,y)
$Label1.AutoSize = $true
$Label2 = New-Object System.Windows.Forms.Label
$Label2.Text = "192.168.x.x ............................"
$Label2.Location = New-Object System.Drawing.Point(15,50)
$Label2.AutoSize = $true
$Label3 = New-Object System.Windows.Forms.Label
$Label3.Text = "192.168.x.x ............................"
$Label3.Location = New-Object System.Drawing.Point(15,70)
$Label3.AutoSize = $true
$Label4 = New-Object System.Windows.Forms.Label
$Label4.Text = "10.0.x.x ............................"
$Label4.Location = New-Object System.Drawing.Point(15,90)
$Label4.AutoSize = $true
$Label5 = New-Object System.Windows.Forms.Label
$Label5.Text = "162.102.x.x ............................"
$Label5.Location = New-Object System.Drawing.Point(15,110)
$Label5.AutoSize = $true
$PictureBox = New-Object system.Windows.Forms.PictureBox #Objektet til at fremvise billeder hedder fuldstændig logisk
$PictureBox.width = 10
$PictureBox.height = 10
#Her går vi over til det vigtige, vi binder det viste billede til resultatet af tilgængelighedstjekket ved at bruge cmdleten
#<b>test-connection</b>, hvor:
#-Count - overfører antallet af forespørgsler
#-computer - IP eller domænenavn til forespørgslen
#-quiet - så vi kun får et Boolean-værdi tilbage
$PictureBox.location = New-Object System.Drawing.Point(235,12)
if ((test-connection -Count 1 -computer ya.ru -quiet) -eq $True) {
$PictureBox.imageLocation = "C:Testyes.png" #Objektet refererer til det pågældende billede
}
Else {
$PictureBox.imageLocation = "C:Testno.png" #Objektet refererer til det pågældende billede
}
$PictureBox.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$PictureBox1 = New-Object system.Windows.Forms.PictureBox #Objektet til visning af billeder er navngivet logisk
$PictureBox1.width = 10
$PictureBox1.height = 10
$PictureBox1.location = New-Object System.Drawing.Point(235,32)
if ((test-connection -Count 1 -computer 8.8.8.8 -quiet) -eq $True) {
$PictureBox1.imageLocation = "C:Testyes.png" #Objektet refererer til det pågældende billede
}
Else {
$PictureBox1.imageLocation = "C:Testno.png" #Objektet refererer til det pågældende billede
}
$PictureBox1.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$PictureBox2 = New-Object system.Windows.Forms.PictureBox #Objektet til visning af billeder er navngivet logisk
$PictureBox2.width = 10
$PictureBox2.height = 10
$PictureBox2.location = New-Object System.Drawing.Point(235,52)
if ((test-connection -Count 1 -computer 192.168.x.x -quiet) -eq $True) {
$PictureBox2.imageLocation = "C:Testyes.png" #Objektet refererer til det pågældende billede
}
Else {
$PictureBox2.imageLocation = "C:Testno.png" #Objektet refererer til det pågældende billede
}
$PictureBox2.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$PictureBox3 = New-Object system.Windows.Forms.PictureBox #Objektet til visning af billeder er navngivet logisk
$PictureBox3.width = 10
$PictureBox3.height = 10
$PictureBox3.location = New-Object System.Drawing.Point(235,72)
if ((test-connection -Count 1 -computer 192.168.x.x -quiet) -eq $True) {
$PictureBox3.imageLocation = "C:Testyes.png" #Objektet refererer til det pågældende billede
}
Else {
$PictureBox3.imageLocation = "C:Testno.png" #Objektet refererer til det pågældende billede
}
$PictureBox3.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$PictureBox4 = New-Object system.Windows.Forms.PictureBox #Objektet til visning af billeder er navngivet logisk
$PictureBox4.width = 10
$PictureBox4.height = 10
$PictureBox4.location = New-Object System.Drawing.Point(235,92)
if ((test-connection -Count 1 -computer 10.0.x.x -quiet) -eq $True) {
$PictureBox4.imageLocation = "C:Testyes.png" #Objektet refererer til det pågældende billede
}
Else {
$PictureBox4.imageLocation = "C:Testno.png" #Objektet refererer til det pågældende billede
}
$PictureBox1.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$PictureBox5 = New-Object system.Windows.Forms.PictureBox #Objektet til visning af billeder er navngivet logisk
$PictureBox5.width = 10
$PictureBox5.height = 10
$PictureBox5.location = New-Object System.Drawing.Point(235,112)
if ((test-connection -Count 1 -computer 162.102.x.x -quiet) -eq $True) {
$PictureBox5.imageLocation = "C:Testyes.png" #Objektet refererer til det pågældende billede
}
Else {
$PictureBox5.imageLocation = "C:Testno.png" #Objektet refererer til det pågældende billede
}
$PictureBox5.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
$Button = New-Object System.Windows.Forms.Button
$Button.Location = New-Object System.Drawing.Size(100,150)
$Button.Size = New-Object System.Drawing.Size(80,30)
$Button.Text = "Genlæs"
# Tilknytter en handling til knappen, som refererer hvert PictureBox i henhold til den tidligere beskrevne logik
$Button.Add_Click({
if ((Test-Connection -Count 1 -computer ya.ru -quiet) -eq $True)
{$PictureBox.imageLocation = "C:Testyes.png"}
Else {$PictureBox.imageLocation = "C:Testno.png"}
if ((Test-Connection -Count 1 -computer 8.8.8.8 -quiet) -eq $True)
{$PictureBox1.imageLocation = "C:Testyes.png"}
Else {$PictureBox1.imageLocation = "C:Testno.png"}
if ((Test-Connection -Count 1 -computer 192.168.x.x -quiet) -eq $True)
{$PictureBox2.imageLocation = "C:Testyes.png"}
Else {$PictureBox2.imageLocation = "C:Testno.png"}
if ((Test-Connection -Count 1 -computer 192.168.x.x -quiet) -eq $True)
{$PictureBox3.imageLocation = "C:Testyes.png"}
Else {$PictureBox3.imageLocation = "C:Testno.png"}
if ((Test-Connection -Count 1 -computer 10.0.x.x -quiet) -eq $True)
{$PictureBox4.imageLocation = "C:Testyes.png"}
Else {$PictureBox4.imageLocation = "C:Testno.png"}
if ((Test-Connection -Count 1 -computer 162.102.x.x -quiet) -eq $True)
{$PictureBox5.imageLocation = "C:Testyes.png"}
Else {$PictureBox5.imageLocation = "C:Testno.png"}
})
$main_form.Controls.Add($Label) #vi tilføjer det oprettede objekt til formen, så det ikke går tabt under scriptets udførelse
$main_form.Controls.Add($Label1)
$main_form.Controls.Add($Label2)
$main_form.Controls.Add($Label3)
$main_form.Controls.Add($Label4)
$main_form.Controls.Add($Label5)
$main_form.Controls.Add($PictureBox)
$main_form.Controls.Add($PictureBox1)
$main_form.Controls.Add($PictureBox2)
$main_form.Controls.Add($PictureBox3)
$main_form.Controls.Add($PictureBox4)
$main_form.Controls.Add($PictureBox5)
$main_form.Controls.Add($Button)
$main_form.ShowDialog() #Viser den simple dialogboks
Selv hvis man holder det rent og holder sig til strukturen, vil den periodiske redigering ikke give de mest behagelige følelser.
For starters, we will extract the availability check into a separate function, and the path to the directory into a separate variable:
$script_path = "C:TestPS ping"
#We transition to the function using the already created PictureBox object and the IP address that needs to be checked.
#As a result, it changes the displayed image.
function get_status($PictureBox,$path_ip) {
if ((Test-Connection -Count 1 -computer $path_ip -quiet) -eq $True)
{$PictureBox.imageLocation = $script_path + "yes.png"}
Else {$PictureBox.imageLocation = $script_path + "no.png"}
}
We will move host data to an external file path.txt, recording it in the format "ip/host-functional-name/", and in the document, we will accept them in arrays. We will also make the Y position calculation more automated. All this allows us to create Labels and checkboxes by calling a function:

#создаем описательную линию, на вход идут: объект Label, IP-адресс, описание и позиция по оси Y
Function Create_line($label,$path_ip,$caption, $top){
$label.Location = New-Object System.Drawing.Point(1, $top)
$label.text = $path_ip+$caption
$label.font = $font
$Label.AutoSize = $true
}
#создаем индикатор для описательной линию, на вход идут: объект PictureBox, IP-адресс и позиция по оси Y
Function Create_link($PictureBox,$path_ip, $top){
$PictureBox.width = 10
$PictureBox.height = 10
$PictureBox.location = New-Object System.Drawing.Point(210,$top)
get_status -PictureBox $PictureBox -path_ip $path_ip
$PictureBox.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
}
$line = Get-content -LiteralPath $script_path"path.txt" #вытаскиваем данные о необходимых хостах
$len = $line.Length #вычисляем длину, а точнее массив длин каждой строки
$i = 0
#далее объявляем массивы которые понадобятся дальше
$ip = @() #массив ip
$capt = @() #массив описания
$Labels =@() #массив Label
$PictureBoxs =@() #массив PictureBox
while($i -lt $len){
$f = $line[$i].IndexOf("/") #вычисляем позицию начала описания
$l = $line[$i].LastIndexOf("/") #вычисляем позицию конца описания
$ip += $line[$i].Substring(0,$f) #вытаскиваем ip
$capt += $line[$i].Substring($f+1,$l-$f-1) #вытаскиваем описание
#создаем поле Label
Create_line -label ($label_obj = New-Object System.Windows.Forms.Label) -path_ip $ip[$i] -caption $capt[$i] -top $label_from_top
#создаем поле PictureBox
Create_link -PictureBox ($PictureBox_obj = New-Object system.Windows.Forms.PictureBox) -path_ip $ip[$i] -top $label_from_top
$label_from_top += 15 #делаем "шаг" по оси Y
$Labels += $label_obj #вносим созданный Label в общий массив
$PictureBoxs += $PictureBox_obj #вносим созданный PictureBox в общий массив
$main_form.Controls.Add($Labels[$i])
$main_form.Controls.Add($PictureBoxs[$i])
$i +=1
}
We will add a place to display the time of the last check, as it is convenient, and we will slightly enhance the action when the button is pressed.

$Label0 = New-Object System.Windows.Forms.Label
$Label0.Text = Get-Date
$Label0.Location = New-Object System.Drawing.Point(80,180)
$Label0.AutoSize = $true
$main_form.Controls.Add($Label0)
$Button.Add_Click({
while($i -lt $len){
get_status -PictureBox $PictureBoxs[$i] -path_ip $ip[$i]
$i +=1
}
$Label0.Text = Get-Date
})
I also added a small feature bug that, upon detecting an unavailable host, not only changes the indicator but also alerts through the speakers.
Add-Type -AssemblyName System.Speech
$voice = New-Object System.Speech.Synthesis.SpeechSynthesizer
$voice.Rate = 5
$voice.Speak("Warning! Warning! Base is under attack!")
So, after a few embellishments and bringing it into a readable and convenient form, it turned out like this:
Complete script code
Add-Type -AssemblyName System.Speech
Add-Type -assembly System.Windows.Forms
$script_path = "C:PS ping"
$label_from_top = 10
$voice = New-Object System.Speech.Synthesis.SpeechSynthesizer
$voice.Rate = 5
#Vi flytter til funktionen for allerede oprettet objekt PictureBox og IP-adressen, der skal kontrolleres.
#Som output ændrer det det indlæste billede.
function get_status($PictureBox,$path_ip) {
if ((Test-Connection -Count 1 -computer $path_ip -quiet) -eq $True) {
$PictureBox.imageLocation = $script_path + "yes.png"
}
Else {
$PictureBox.imageLocation = $script_path + "no.png"
$voice.Speak("Fejl! Vært " + $path_ip + ", er ikke tilgængelig!")
}
}
#Opretter en beskrivende linje, inputs: Label-objekt, IP-adresse, beskrivelse og position på Y-aksen.
Function Create_line($label,$path_ip,$caption, $top){
$label.Location = New-Object System.Drawing.Point(1, $top)
$label.text = $path_ip+$caption
$label.font = $font
$Label.AutoSize = $true
}
#Opretter en indikator for den beskrivende linje, inputs: PictureBox-objekt, IP-adresse og position på Y-aksen.
Function Create_link($PictureBox,$path_ip, $top){
$PictureBox.width = 10
$PictureBox.height = 10
$PictureBox.location = New-Object System.Drawing.Point(210,$top)
get_status -PictureBox $PictureBox -path_ip $path_ip
$PictureBox.SizeMode = [System.Windows.Forms.PictureBoxSizeMode]::zoom
}
$main_form = New-Object System.Windows.Forms.Form
$main_form.Text ='Links up' #Titel i vinduet
$main_form.Width = 300 #Bredde på vinduet
$main_form.Height = 200 #Højde på vinduet
$main_form.AutoSize = $true #Giv det mulighed for at ændre størrelse automatisk, efter behov
$main_form.TopMost = $true #Dette er meget vigtigt, det giver mulighed for at fastgøre vinduet over andre
$line = Get-content -LiteralPath $script_path"path.txt" #Henter data om nødvendige værter
$len = $line.Length #Beregner længden, faktisk længden af hver række i arrayet
$i = 0
#Udfører arrays som vil være nødvendige senere
$ip = @() #IP-array
$capt = @() #Beskrivende array
$Labels =@() #Label-array
$PictureBoxs =@() #PictureBox-array
while($i -lt $len){
$f = $line[$i].IndexOf("/") #Beregner startpositionen for beskrivelsen
$l = $line[$i].LastIndexOf("/") #Beregner slutpositionen for beskrivelsen
$ip += $line[$i].Substring(0,$f) #Henter IP
$capt += $line[$i].Substring($f+1,$l-$f-1) #Henter beskrivelse
#Opretter Label-felt
Create_line -label ($label_obj = New-Object System.Windows.Forms.Label) -path_ip $ip[$i] -caption $capt[$i] -top $label_from_top
#Opretter PictureBox-felt
Create_link -PictureBox ($PictureBox_obj = New-Object system.Windows.Forms.PictureBox) -path_ip $ip[$i] -top $label_from_top
$label_from_top += 15 #Skaber et "trin" langs Y-aksen
$Labels += $label_obj #Indsætter den oprettede Label i det samlede array
$PictureBoxs += $PictureBox_obj #Indsætter det oprettede PictureBox i det samlede array
$main_form.Controls.Add($Labels[$i])
$main_form.Controls.Add($PictureBoxs[$i])
$i +=1
}
#Dette felt viser den sidste kontroltid
$Label0 = New-Object System.Windows.Forms.Label
$Label0.Text = Get-Date
$Label0.Location = New-Object System.Drawing.Point(80,180)
$Label0.AutoSize = $true
#Tilknytter hvert PictureBox med tidligere beskrevne logik ved knaptryk.
$Button = New-Object System.Windows.Forms.Button
$Button.Location = New-Object System.Drawing.Size(100,200)
$Button.Size = New-Object System.Drawing.Size(80,30)
$Button.Text = "Genindlæs"
$Button.Add_Click({
while($i -lt $len){
get_status -PictureBox $PictureBoxs[$i] -path_ip $ip[$i]
$i +=1
}
$i = 0
$Label0.Text = Get-Date
})
$main_form.Controls.Add($Button)
$main_form.Controls.Add($Label0)
$main_form.ShowDialog()
Efterord
Jeg håber, at denne tutorial vil være nyttig for nogen. Hvis du derimod har gjort dette nærmest siden barndommen, tillykke, jeg har ikke. Men jeg er åben for at høre dine kommentarer og forslag.
Det har været en fornøjelse for mig at dykke ned i det og samle et lille, men nyttigt værktøj. Jeg planlægger også at implementere tilføjelse og fjernelse af noder fra GUI'en, samt sørge for, at det, der i første omgang skulle være implementeret, automatisk opdaterer statusser uden behov for at ''klikke'' på en knap og uden at det får ''powershell.exe'' til at hænge.
Den seneste version af scriptet er på GitHub
Kilde: habr.com
