Funcții PowerShell

Acest articol este partea 12 din 13 din seria Învățați PowerShell

În acest episod al seriei Învățați PowerShell vom examina funcțiile PowerShell. În ultimul episod am abordat scripturile PowerShell în care am început să creăm soluții și să rezolvăm probleme cu ajutorul PowerShell. Scripturile PowerShell sunt grozave și mulți oameni petrec destul de mult timp în această etapă atunci când învață PowerShell. Scripturile vă permit să păstrați lucrurile destul de simple și vă pot ajuta să automatizați rapid sarcinile. Pe măsură ce vă perfecționați și începeți să scrieți mai mult PowerShell, va trebui să căutați să creați funcții PowerShell!

Video

Dacă preferați formatul video în locul documentației scrise, discut acest subiect în următorul videoclip TechThoughts:

Când ar trebui să scrieți o funcție PowerShell

La sfârșitul zilei, un script PowerShell este un set de cod care execută o sarcină. Asta este ceea ce face și o funcție PowerShell! Așadar, de ce ați alege să scrieți o funcție față de un script? Ne vom scufunda în câteva motive mai jos. În general, totuși, un script este ceva pentru dvs. Atunci când doriți să începeți să vă partajați codul sau să cereți colegilor de echipă să îl angajeze, veți dori să începeți să angajați unele dintre capacitățile pe care le oferă funcțiile. Nu există o linie fermă. Pentru o sarcină rapidă care va fi executată o singură dată pe stația dvs. de lucru, un script ar putea avea sens. Dacă scrieți niște PowerShell pe care alții le-ar putea folosi sau pe care s-ar putea să le folosiți de mai multe ori, probabil că o funcție va servi mai bine.

  • Cu un singur scop – o funcție este folosită de obicei pentru a îndeplini o sarcină îngustă și „face un singur lucru și îl face excelent”. Acest lucru face ca funcțiile să fie foarte ușor de reutilizat. Dacă scrieți o funcție de logare, de exemplu, puteți utiliza apoi acea funcție de logare PowerShell cu alte funcții sau scripturi.
  • Ajutor – funcțiile acceptă comentarii bazate pe ajutor. Acest lucru le permite utilizatorilor dvs. să facă lucruri cum ar fi să tasteze Get-Help și să-și dea seama cum să utilizeze funcția dvs..
  • Parametri – suportul pentru declarații și control simplu și avansat al parametrilor permite funcției dvs. să fie dinamică și să preia diverse forme de intrare a utilizatorului.
  • Testabile – funcțiile pot fi testate și simulate, ceea ce îmbunătățește foarte mult calitatea codului.

Anatomia unei funcții PowerShell

Iată aspectul și ordinea de bază a unei funcții PowerShell. Ne vom scufunda în fiecare dintre aceste secțiuni mai jos și le vom explora în detaliu.

# function help - (optional but strongly encouraged)# function name# CmdletBinding - (optional)# parameters - (optional)# function logic (optional Begin / Process / End)# return - (optional)function Verb-Noun { param ( ) begin { } process { } end { }}

Ajutorul funcției

Când includeți ajutorul în partea de sus a funcției dumneavoastră, acesta va fi afișat atunci când Get-Help este rulat împotriva funcției dumneavoastră. Aceasta este o capacitate puternică atunci când alte persoane vă explorează codul. Dacă vă acordați timpul necesar pentru a completa un Synopsis și o descriere bune, combinate cu exemple solide, îi va ajuta pe ceilalți să înțeleagă la ce servește funcția dvs. și cum să o folosească.

Toate câmpurile de ajutor sunt opționale și le puteți adăuga sau elimina după bunul dvs. plac. Vă recomand să includeți cel puțin câmpurile de mai jos cel puțin.

CmdletBinding

Când scrieți o funcție grozavă și îi dați un nume precum Get-AllFileInformation, aceasta arată și va acționa ca un cmdlet. Dar este o distincție importantă faptul că o funcție PowerShell nu este un cmdlet. Cmdlet-urile sunt scrise și compilate în C#, iar funcția dvs. PowerShell este scrisă în PowerShell.

CmdletBinding este un atribut al funcțiilor care permite capacități care le face să funcționeze mai mult ca niște cmdlet-uri compilate. Adăugarea acestuia în partea de sus a funcției dvs. va oferi funcției dvs. o mulțime de capabilități suplimentare, cum ar fi:

  • Write-Verbose – permiteți utilizatorilor să folosească comutatorul -Verbose pentru a vedea ce face funcția dvs. în timp ce o face.
  • ShouldProcess – dacă funcția dvs. va face o modificare a unui sistem care prezintă un risc ridicat, este posibil să doriți ca utilizatorul să confirme acțiunea.
  • PositionalBinding – permite ca funcția dvs. să fie executată fără a furniza în mod explicit numele fiecărui parametru. Valorile pot fi deduse prin ordinea în care sunt furnizate funcției dvs.

parameters

param ( $City, $Units = 'USCS', $Language = 'en', $Short)

Parametrii servesc pentru a oferi utilizatorului o modalitate de a interacționa în mod dinamic cu funcția dvs. Puteți primi diverse forme de intrare și puteți efectua o mare varietate de verificări și validări pentru a vă asigura că obțineți tipul corect de informații.

Puteți să rămâneți foarte simplu și să declarați doar numele parametrilor dumneavoastră. Alternativ, puteți deveni foarte specific cu privire la ceea ce este necesar pentru parametrii dumneavoastră:

  • Dacă parametrul este obligatoriu
  • Poziția unui parametru (ordinea)
  • Tipul parametrului (string/int/bool/etc)
  • Stabilirea valorilor implicite
  • Validarea intrărilor
  • Seturi de parametri
  • Mult mai multe

Acest post nu poate acoperi fiecare configurație posibilă a parametrilor. Chiar și după ani de zile în care am scris PowerShell, mi se pare dificil să memorez toate setările de parametri și sintaxa. Să știți că declarațiile de parametri sunt modul dvs. de a prelua date de intrare în funcția dvs. Puteți să le oferiți o mulțime de detalii și controale sau să le păstrați simple, în funcție de nevoile dumneavoastră. Marcați ca favorite linkurile de parametri din partea de jos a acestei postări. Chiar și astăzi, le vizitez frecvent!

Begin Process End

Aceste trei cuvinte cheie sunt faze pe care le puteți declara în cadrul funcției dumneavoastră.

  • Begin va inițializa unele etape la început
  • Process va procesa fiecare obiect așa cum este primit
  • End poate efectua curățarea.

Acest lucru este util mai ales dacă doriți ca funcția dvs. să susțină procesarea intrărilor din pipeline.

Acest lucru poate fi dificil de înțeles în teorie, așa că iată un exemplu care demonstrează utilizarea sa.

function Get-PipelineBeginEnd { param ( $SomeInput ) begin { "Begin: The input is $SomeInput" } process { "The value is: $_" } end { "End: The input is $SomeInput" }}#Get-PipelineBeginEnd1, 2, 3 | Get-PipelineBeginEnd -SomeInput 'Test'

Când rulați codul de mai sus, observați că Begin se execută o singură dată, la fel ca și End. Process este executat pentru fiecare element trecut în el, iar Process are acces la obiectul curent din pipeline.

Logica funcției

Logica conținută în interiorul unei funcții PowerShell nu este diferită de cea a unui script. Acesta este locul în care veți scrie logica de bază care îndeplinește sarcina pentru care este destinată funcția dumneavoastră. Acest aspect a fost abordat în episoadele 1-10 din acest curs. De asemenea, puteți vedea un exemplu live complet în episodul PowerShell Scripts.

Returnarea funcției

Nu toate funcțiile returnează ceva atunci când sunt executate. Dacă funcția dvs. va returna ceva, puteți folosi opțional return. Rețineți că atunci când utilizați return, toate acțiunile ulterioare din funcție se vor opri și funcția se va încheia.

function Get-Total { param ( $Number1, $Number2 ) $total = $Number1 + $Number2 return $total}Get-Total -Number1 2 -Number2 2

În exemplul de mai sus, această funcție simplă conține doi parametri de tip integer. Logica funcției însumează cele două numere și returnează utilizatorului numărul întreg.

Prima dvs. funcție PowerShell

Aruncă o privire la funcția PowerShell de mai jos. Observați că aspectul aderă la ceea ce am acoperit anterior. Observați, de asemenea, că secțiunea de ajutor oferă o cantitate mare de detalii cu privire la scopul și utilizarea funcției.

<#.SYNOPSIS Returns your public IP address..DESCRIPTION Queries the ipify Public IP Address API and returns your public IP..EXAMPLE Get-PublicIP Returns the public IP..OUTPUTS System.String.NOTES https://github.com/rdegges/ipify-api#>function Get-PublicIP { $uri = 'https://api.ipify.org' try { $invokeRestMethodSplat = @{ Uri = $uri ErrorAction = 'Stop' } $publicIP = Invoke-RestMethod @invokeRestMethodSplat } catch { Write-Error $_ } return $publicIP}#Get-PublicIP

Acum logica reală a acestei funcții este destul de simplă, ar putea fi tentant să o lăsăm ca script. Rețineți totuși că aceasta face un lucru specific și îl face bine. Acum ați putea încorpora această funcție în altă logică avansată, în loc să trebuiască să faceți trimitere sau să importați un script. Alți utilizatori din mediul dumneavoastră ar putea, de asemenea, să înceapă să angajeze această funcție odată ce se vor familiariza cu ea.

Domeniul de aplicare al funcției

Ca majoritatea limbajelor, PowerShell are reguli de domeniu de aplicare pentru variabile. Atunci când o variabilă se află în interiorul unei funcții, nu veți mai putea „vedea” valoarea acesteia. Iată un exemplu de acest comportament:

function Get-NumberTimesTwo { param ( $Number ) $total = $Number * 2 return $total}#Get-NumberTimesTwoGet-NumberTimesTwo -Number 2

Funcția se comportă conform așteptărilor și va înmulți corect un număr cu doi. În consola dvs. totuși, încercați să vedeți care este valoarea lui $total. Nu veți putea să o faceți. Acest lucru se datorează faptului că $total este atribuit funcției, și nu sesiunii dvs. active de consolă.

Acest lucru poate fi derutant pentru persoanele noi în PowerShell și poate face ca scrierea funcțiilor să fie mai dificilă. Există câteva strategii pentru a face față acestui lucru.

Ați putea scrie majoritatea logicii dvs. într-un format de tip script, testând variabilele pe parcurs. Odată ce sunteți sigur că logica funcționează conform intenției, ați putea apoi să înfășurați logica în interiorul unei funcții.

Alternativ, puteți folosi Write-Host, Write-Output sau, mai bine, Write-Debug pentru a vedea ce se întâmplă cu variabilele dvs. în interiorul funcției!

function Get-NumberTimesTwo { param ( $Number ) $total = $Number * 2 Write-Debug $total return $total}#Get-NumberTimesTwoGet-NumberTimesTwo -Number 2 -Debug

Rețineți că, cu ajutorul comutatorului de depanare, avem acces la valoarea din interiorul $total pentru a ne asigura că logica noastră face ceea ce intenționăm.

Exemplu de închidere

Iată un exemplu mai amplu de închidere a două funcții PowerShell care vă va permite să navigați pe popularul site reddit folosind PowerShell!

Vizitați linkul GitHub gist de mai jos pentru a accesa codul și a-l încărca în consola dumneavoastră.

https://gist.github.com/techthoughts2/cd2b720c9b291510cbd643e6ca73e05f

În timp ce explorați aceste funcții, încercați să răspundeți la următoarele întrebări:

  • Dintre cele două funcții, care este funcția principală?
  • Sunt funcții standard sau avansate?
  • Ce funcție va suporta intrarea în conductă?

Additional Reading

  • Functions
  • Parameters
  • Functions Advanced
  • Functions Advanced Parameters
  • PowerShell Approved Verbs
  • CmdletBindingAttribute

Series Navigation << PowerShell ScriptsManage Cloud with PowerShell >>