Posted in: Základy PowerShellu

Funkce v PowerShellu

Dnes po dlouhé době opět píši něco pro ty, kteří chtějí s PowerShellem začínat a již nějak zvládli základní syntaxi. Pro dnešní práci budeme potřebovat nějaký nástroj k psaní skriptů, viz článek.

Jak jsem se již určitě zmínil v některém předešlém článku, skript je posloupnost příkazů, které se vykonají v daném pořadí. Skript může obsahovat, stejně jako program v některém programovacím jazyce, cykly, podmínky a další řídící příkazy, které vedou na opakování nějakého bloku, nebo naopak přeskočení nějakého bloku kódu. Stejně jako v programování, i při psaní skriptů, můžeme potřebovat opakovat nějaký blok, kus kódu, na různých místech skriptu. Prvním nápadem může být, prostě daný blok kódu zkopírovat a vložit jej na požadovaná místa. Toto je nevýhodné, protože se zkopírovaný blok špatně opravuje, rozšiřuje apod. Proto máme lepší řešení, to jsou funkce, které si umíme volat.

Jmenná konvence

Když si vzpomenete na základní syntaxi PowerShellu, příkazy mají základní podobu:
sloveso-PodstatnéJméno
Tento formát pojmenování je potřeba dodržet i u našich funkcí. Mnohé z vás by mohlo napadnou použít vlastní kombinaci jako například:
Vypis-PCinfo
sice syntakticky vyhovíme, ale není to zcela správné. PowerShell definuje rovněž sadu sloves, která máme využívat a uživatelé jazyka je očekávají a očekávají, že budou mít daný význam. Seznam podporovaných sloves vrátí příkaz:

Get-Verb | Sort-Object -Property Verb

Výstup této funkce rovněž uvádím v článku o syntaxi.

Obecná syntaxe

function Sloveso-PodstatneJmeno
{
    #vlastní kód (tělo) funkce
}

Příklad:

function Get-WinInfo
{
    cls
    Write-Host "Základní informace o počítači"
    Write-Host ""
    $info = Get-ComputerInfo | select WindowsProductName, WindowsCurrentVersion, CsModel, CsName
    Write-Host "Název OS      :" $info.WindowsProductName
    Write-Host "Verze jádra OS:" $info.WindowsCurrentVersion
    Write-Host "Model zařízení:" $info.CsModel
    Write-Host "Název zařízení:" $info.CsName
}

Funkci spustíme tak, že napíšeme její jméno, tedy pro náš příklad by volání vypadalo:

Get-WinInfo

Výše uvedená je nejsprostější verze, samozřejmě i základní funkce může mít parametry, případně vracet hodnoty.

Funkce s parametrem

Výše popsaný základ je dobrý, ale pořád se jedná o poměrně hloupé funkce. Výše popsaná syntaxe slouží k deduplikaci kódu a umí modifikovat globální proměnné, vypisovat na obrazovku, komunikovat s uživatelem atd. Bohužel nemůžeme takto definované funkci předat hodnoty ke zpracovaní. Pojďme se podívat na to, jak tento problém řešit.

Obecná syntaxe:

function Sloveso-PodstatneJmeno
{
     param(
       $NázevParametru,
       $NázevDruhéhoVolitelnéhoParametru
       )
     #vlastní kód (tělo) funkce
}

Čárkou se oddělují jednotlivé parametry, tudíž se uvádí pouze tam, kde za parametrem následuje další parametr. Pojďme si uvést příklad funkce s jedním parametrem.

function Get-OSInfo { 
    param (
        $ComputerName
    ) 
    Get-WmiObject -ComputerName $ComputerName -Class Win32_OperatingSystem | select Caption, Version, SystemDrive | Format-Table 
}

Nyní je na čase si ukázat, jak tuto funkci volat. Obecně voláme funkci v podobě:

Sloveso-PodstatneJmeno -NázevParametru hodnota -NázevDruhéhoVolitelnéhoParametru hodnota

Pojďme si to zkonkrétnit na našem příkladu s funkcí Get-OSInfo pro lokální počítač:

Get-OSInfo -ComputerName localhost

Toto vše je krásné, ale občas bychom potřebovali, aby vstup, který nám dává parametr, byl určitého datového typu, například číslo. Pojďme si na příkladu jednoduché kalkulační funkce ukázat, jak určit datový typ, který parametr bude akceptovat.

function Get-Vysledek { 
    param (
        [double]$cislo1,
        [double]$cislo2,
        [switch]$soucet,
        [switch]$soucin,
        [switch]$rozdil,
        [switch]$podil
    ) 
    if($soucet)
    {
        $vysledek = $cislo1 + $cislo2
        Write-Host "Soucet je:" $vysledek
    }
    if($rozdil)
    {
        $vysledek = $cislo1 - $cislo2
        Write-Host "Soucet je:" $vysledek
    }
    if($soucin)
    {
        $vysledek = $cislo1 * $cislo2
        Write-Host "Soucet je:" $vysledek
    }
    if($podil)
    {
        if($cislo2 -gt 0)
        {
            $vysledek = $cislo1 / $cislo2
            Write-Host "Soucet je:" $vysledek
        }
        else
        {
            Write-Host "Nulou nelze dělit"
        }
    }
}

Datový typ, kterého musí daný parametr nabývat, určíme tak, že název datového typu uvedeme do hranatých závorek před požadovaný parametr. Jedinou výjimkou, která funguje pouze u parametrů, nelze ji uplatnit na proměnné v jiných částí kódu je „datový typ“ switch. Pokud je nějaký parametr typu switch, pak daný parametr nabyde hodnoty True (logické jedničky) tím, že dojde k uvedení daného parametru při volání procedury. Úplné informace o datových typech jsou v dokumentaci. Někdy příště, se na vybrané datové typy podíváme. Příklad volání naší ukázkové funkce Get-Vysledek:

Get-Vysledek -cislo1 6.6 -cislo2 3 -podil

Návratová hodnota

Od PowerShell verze 5 nám funkce může vrátit návratovou hodnotu, stejně jako je tomu v běžných programovacích jazycích. Na rozdíl do programovacích jazyků ovšem PowerShell nevrací hodnotu, ale výraz. Na rozdíl od programovacích jazyků u funkce nedefinujeme datový typ návratové hodnoty. Stejně jako v případě běžných programovacích jazyků máme k dispozici příkaz return, jehož syntax je jednoduchá:

return vyraz

Pojďme si to ukázat na příkladu převzatém z dokumentace a lehce upraveném.

function Get-Kalkuace {
    param ($hodnota)

    $hodnota ="Prosím vyčkejte, počítám...`n" #znak `n je zalomení řádku
    $hodnota += 73
    return $hodnota
}

Takovouto funkci lze volat napřímo, nebo její výstup, který vrací příkaz return přiřadit do proměnné. Pojďme si ukázat verzi, kdy hodnotu navrácenou funkcí (v mé modifikaci strinng) přiřadíme do proměnné, kterou rovnou vypíšeme:

Write-Host ($a = Get-Kalkuace 14)

Závěr

Toto je vše z dnešního úvodu do funkcí. Funkce toho umí dalece více, ale o tom až někdy později u tzv. pokročilých funkcí. Funkce jsou klíčovou součástí jazyka PowerShell, protože moduly jazyka PowerShell vždy funkce obsahují a uživatel modulu volá právě funkce v něm obsažené.

Back to Top