about_Functions

Descrizione breve

Descrive come creare e usare funzioni in PowerShell.

Descrizione lunga

Una funzione è un elenco di istruzioni di PowerShell con un nome assegnato. Quando si esegue una funzione, si digita il nome della funzione. Le istruzioni nell'elenco vengono eseguite come se fossero state digitate al prompt dei comandi.

Le funzioni possono essere semplici come:

function Get-PowerShellProcess { Get-Process PowerShell }

Una funzione può anche essere complessa come un cmdlet o un'applicazione.

Come i cmdlet, le funzioni possono avere parametri. I parametri possono essere denominati, posizionali, switch o parametri dinamici. I parametri della funzione possono essere letti dalla riga di comando o dalla pipeline.

Le funzioni possono restituire valori che possono essere visualizzati, assegnati a variabili o passati ad altre funzioni o cmdlet. È anche possibile specificare un valore restituito usando la return parola chiave . La return parola chiave non influisce o elimina altri output restituiti dalla funzione. Tuttavia, la return parola chiave esce dalla funzione in corrispondenza di tale riga. Per altre informazioni, vedere about_Return.

L'elenco di istruzioni della funzione può contenere diversi tipi di elenchi di istruzioni con le parole chiave begin, process, ende clean. Queste istruzioni elencano l'handle di input dalla pipeline in modo diverso.

La parola chiave filter viene usata per creare un tipo di funzione eseguita su ogni oggetto nella pipeline. Un filtro è simile a una funzione con tutte le relative istruzioni in un process blocco.

Le funzioni possono anche agire come cmdlet. È possibile creare una funzione che funziona esattamente come un cmdlet senza usare la C# programmazione. Per altre informazioni, vedere about_Functions_Advanced.

Importante

All'interno di file di script e moduli basati su script, le funzioni devono essere definite prima di poter essere chiamate.

Sintassi

Di seguito è riportata la sintassi per una funzione:

function [<scope:>]<name> [([type]$parameter1[,[type]$parameter2])]
{
  begin {<statement list>}
  process {<statement list>}
  end {<statement list>}
  clean {<statement list>}
}
function [<scope:>]<name>
{
  param([type]$parameter1 [,[type]$parameter2])
  dynamicparam {<statement list>}
  begin {<statement list>}
  process {<statement list>}
  end {<statement list>}
  clean {<statement list>}
}

Una funzione include gli elementi seguenti:

  • Parola function chiave
  • Ambito (facoltativo)
  • Nome selezionato
  • Qualsiasi numero di parametri denominati (facoltativo)
  • Uno o più comandi di PowerShell racchiusi tra parentesi graffe {}

Per altre informazioni sulla dynamicparam parola chiave e sui parametri dinamici nelle funzioni, vedere about_Functions_Advanced_Parameters.

Metodi di elaborazione dell'input

I metodi descritti in questa sezione sono detti metodi di elaborazione dell'input. Per le funzioni, questi tre metodi sono rappresentati dai beginblocchi , processe end della funzione . PowerShell 7.3 aggiunge un clean metodo di processo a blocchi.

Non è necessario usare uno di questi blocchi nelle funzioni. Se non si usa un blocco denominato, PowerShell inserisce il codice nel end blocco della funzione. Tuttavia, se si usa uno di questi blocchi denominati o si definisce un dynamicparam blocco, è necessario inserire tutto il codice in un blocco denominato.

Nell'esempio seguente viene illustrata la struttura di una funzione che contiene un begin blocco per la pre-elaborazione monouso, un process blocco per l'elaborazione di più record e un end blocco per la post-elaborazione una tantum.

Function Test-ScriptCmdlet
{
[CmdletBinding(SupportsShouldProcess=$True)]
    Param ($Parameter1)
    begin{}
    process{}
    end{}
}

begin

Questo blocco viene usato per fornire la pre-elaborazione occasionale facoltativa per la funzione. Il runtime di PowerShell usa il codice in questo blocco una volta per ogni istanza della funzione nella pipeline.

process

Questo blocco viene usato per fornire l'elaborazione record per record per la funzione. È possibile usare un process blocco senza definire gli altri blocchi. Il numero di esecuzioni di process blocchi dipende dalla modalità di utilizzo della funzione e dall'input ricevuto dalla funzione.

La variabile $_ automatica o $PSItem contiene l'oggetto corrente nella pipeline da usare nel process blocco. La $input variabile automatica contiene un enumeratore disponibile solo per le funzioni e i blocchi di script. Per altre informazioni, vedere about_Automatic_Variables.

  • La chiamata alla funzione all'inizio o all'esterno di una pipeline esegue il process blocco una sola volta.
  • All'interno di una pipeline, il process blocco viene eseguito una volta per ogni oggetto di input che raggiunge la funzione.
  • Se l'input della pipeline che raggiunge la funzione è vuoto, il process blocco non viene eseguito.
    • I beginblocchi , ende clean continuano a essere eseguiti.

Importante

Se un parametro di funzione è impostato per accettare l'input della pipeline e un process blocco non è definito, l'elaborazione dei record per record avrà esito negativo. In questo caso, la funzione verrà eseguita una sola volta, indipendentemente dall'input.

end

Questo blocco viene usato per fornire una sola volta post-elaborazione facoltativa per la funzione.

clean

Il clean blocco è stato aggiunto in PowerShell 7.3.

Il clean blocco è un modo pratico per consentire agli utenti di pulire le risorse che si estendono tra i beginblocchi , processe end . È semanticamente simile a un finally blocco che copre tutti gli altri blocchi denominati di una funzione script o un cmdlet di script. La pulizia delle risorse viene applicata per gli scenari seguenti:

  1. quando l'esecuzione della pipeline viene completata normalmente senza errori irreversibili
  2. quando l'esecuzione della pipeline viene interrotta a causa di un errore irreversibile
  3. quando la pipeline viene interrotta da Select-Object -First
  4. quando la pipeline viene arrestata da CTRL+c o StopProcessing()

Attenzione

L'aggiunta del clean blocco è una modifica che causa un'interruzione. Poiché clean viene analizzato come parola chiave, impedisce agli utenti di chiamare direttamente un comando denominato clean come prima istruzione in un blocco di script. Tuttavia, non è probabile che si tratti di un problema. Il comando può comunque essere richiamato usando l'operatore di chiamata (& clean).

Funzioni semplici

Le funzioni non devono essere complicate per essere utili. Le funzioni più semplici hanno il formato seguente:

function <function-name> {statements}

Ad esempio, la funzione seguente avvia PowerShell con l'opzione Esegui come Amministrazione istrator.

function Start-PSAdmin {Start-Process PowerShell -Verb RunAs}

Per usare la funzione, digitare: Start-PSAdmin

Per aggiungere istruzioni alla funzione, digitare ogni istruzione in una riga separata o usare un punto ; e virgola per separare le istruzioni.

Ad esempio, la funzione seguente trova tutti i .jpg file nelle directory dell'utente corrente modificate dopo la data di inizio.

function Get-NewPix
{
  $start = Get-Date -Month 1 -Day 1 -Year 2010
  $allpix = Get-ChildItem -Path $env:UserProfile\*.jpg -Recurse
  $allpix | Where-Object {$_.LastWriteTime -gt $Start}
}

È possibile creare una casella degli strumenti di funzioni di piccole dimensioni utili. Aggiungere queste funzioni al profilo di PowerShell, come descritto in about_Profiles e versioni successive in questo argomento.

Nomi di funzione

È possibile assegnare qualsiasi nome a una funzione, ma le funzioni condivise con altri utenti devono seguire le regole di denominazione stabilite per tutti i comandi di PowerShell.

I nomi delle funzioni devono essere costituiti da una coppia verbo-sostantivo in cui il verbo identifica l'azione eseguita dalla funzione e il sostantivo identifica l'elemento in cui il cmdlet esegue l'azione.

Le funzioni devono usare i verbi standard approvati per tutti i comandi di PowerShell. Questi verbi consentono di mantenere i nomi dei comandi coerenti e facili da comprendere agli utenti.

Per altre informazioni sui verbi di PowerShell standard, vedere Verbi approvati.

Funzioni con parametri

È possibile usare parametri con funzioni, inclusi parametri denominati, parametri posizionali, parametri switch e parametri dinamici. Per altre informazioni sui parametri dinamici nelle funzioni, vedere about_Functions_Advanced_Parameters.

parametri denominati

È possibile definire qualsiasi numero di parametri denominati. È possibile includere un valore predefinito per i parametri denominati, come descritto più avanti in questo argomento.

È possibile definire i parametri all'interno delle parentesi graffe usando la param parola chiave , come illustrato nella sintassi di esempio seguente:

function <name> {
  param ([type]$parameter1 [,[type]$parameter2])
  <statement list>
}

È anche possibile definire parametri esterni alle parentesi graffe senza la Param parola chiave , come illustrato nella sintassi di esempio seguente:

function <name> [([type]$parameter1[,[type]$parameter2])] {
  <statement list>
}

Di seguito è riportato un esempio di questa sintassi alternativa.

function Add-Numbers([int]$one, [int]$two) {
    $one + $two
}

Anche se il primo metodo è preferibile, non esiste alcuna differenza tra questi due metodi.

Quando si esegue la funzione, il valore fornito per un parametro viene assegnato a una variabile contenente il nome del parametro. Il valore di tale variabile può essere usato nella funzione .

L'esempio seguente è una funzione denominata Get-SmallFiles. Questa funzione ha un $Size parametro . La funzione visualizza tutti i file inferiori al valore del $Size parametro ed esclude le directory:

function Get-SmallFiles {
  Param($Size)
  Get-ChildItem $HOME | Where-Object {
    $_.Length -lt $Size -and !$_.PSIsContainer
  }
}

Nella funzione è possibile usare la $Size variabile , ovvero il nome definito per il parametro .

Per usare questa funzione, digitare il comando seguente:

Get-SmallFiles -Size 50

È anche possibile immettere un valore per un parametro denominato senza il nome del parametro. Ad esempio, il comando seguente restituisce lo stesso risultato di un comando che denomina il parametro Size :

Get-SmallFiles 50

Per definire un valore predefinito per un parametro, digitare un segno di uguale e il valore dopo il nome del parametro, come illustrato nella variante seguente dell'esempio Get-SmallFiles :

function Get-SmallFiles ($Size = 100) {
  Get-ChildItem $HOME | Where-Object {
    $_.Length -lt $Size -and !$_.PSIsContainer
  }
}

Se si digita Get-SmallFiles senza un valore, la funzione assegna 100 a $size. Se si specifica un valore, la funzione usa tale valore.

Facoltativamente, è possibile fornire una breve stringa della Guida che descrive il valore predefinito del parametro, aggiungendo l'attributo PSDefaultValue alla descrizione del parametro e specificando la proprietà Help di PSDefaultValue. Per fornire una stringa della Guida che descrive il valore predefinito (100) del parametro Size nella Get-SmallFiles funzione, aggiungere l'attributo PSDefaultValue come illustrato nell'esempio seguente.

function Get-SmallFiles {
  param (
      [PSDefaultValue(Help = '100')]
      $Size = 100
  )
}

Per altre informazioni sulla classe di attributi PSDefaultValue, vedere Membri dell'attributo PSDefaultValue.

Parametri posizionali

Un parametro posizionale è un parametro senza un nome di parametro. PowerShell usa l'ordine del valore del parametro per associare ogni valore di parametro a un parametro nella funzione.

Quando si usano parametri posizionali, digitare uno o più valori dopo il nome della funzione. I valori dei parametri posizionali vengono assegnati alla $args variabile di matrice. Il valore che segue il nome della funzione viene assegnato alla prima posizione nella $args matrice , $args[0].

La funzione seguente Get-Extension aggiunge l'estensione .txt del nome file a un nome file specificato:

function Get-Extension {
  $name = $args[0] + ".txt"
  $name
}
Get-Extension myTextFile
myTextFile.txt

Parametri switch

Un'opzione è un parametro che non richiede un valore. Digitare invece il nome della funzione seguito dal nome del parametro switch.

Per definire un parametro switch, specificare il tipo [switch] prima del nome del parametro, come illustrato nell'esempio seguente:

function Switch-Item {
  param ([switch]$on)
  if ($on) { "Switch on" }
  else { "Switch off" }
}

Quando si digita il On parametro switch dopo il nome della funzione, la funzione visualizza Switch on. Senza il parametro switch, viene visualizzato Switch off.

Switch-Item -on
Switch on
Switch-Item
Switch off

È anche possibile assegnare un valore booleano a un'opzione quando si esegue la funzione, come illustrato nell'esempio seguente:

Switch-Item -on:$true
Switch on
Switch-Item -on:$false
Switch off

Uso dello splatting per rappresentare i parametri dei comandi

È possibile usare lo splatting per rappresentare i parametri di un comando. Questa funzionalità è stata introdotta in Windows PowerShell 3.0.

Usare questa tecnica nelle funzioni che chiamano i comandi nella sessione. Non è necessario dichiarare o enumerare i parametri del comando o modificare la funzione quando i parametri di comando cambiano.

La funzione di esempio seguente chiama il Get-Command cmdlet . Il comando usa @Args per rappresentare i parametri di Get-Command.

function Get-MyCommand { Get-Command @Args }

È possibile usare tutti i parametri di Get-Command quando si chiama la Get-MyCommand funzione . I parametri e i valori dei parametri vengono passati al comando usando @Args.

Get-MyCommand -Name Get-ChildItem
CommandType     Name                ModuleName
-----------     ----                ----------
Cmdlet          Get-ChildItem       Microsoft.PowerShell.Management

La @Args funzionalità usa il $Args parametro automatico, che rappresenta i parametri e i valori non dichiarati dei cmdlet degli argomenti rimanenti.

Per altre informazioni, vedere about_Splatting.

Piping di oggetti in funzioni

Qualsiasi funzione può accettare input dalla pipeline. È possibile controllare il modo in cui una funzione elabora l'input dalla pipeline usando beginparole chiave , processend, e clean . La sintassi di esempio seguente illustra queste parole chiave:

L'elenco process di istruzioni viene eseguito una volta per ogni oggetto nella pipeline. Mentre il process blocco è in esecuzione, ogni oggetto pipeline viene assegnato alla $_ variabile automatica, un oggetto pipeline alla volta.

La funzione seguente usa la process parola chiave . La funzione visualizza i valori della pipeline:

function Get-Pipeline
{
  process {"The value is: $_"}
}

1,2,4 | Get-Pipeline
The value is: 1
The value is: 2
The value is: 4

Se si vuole una funzione che può accettare input o input della pipeline da un parametro, il process blocco deve gestire entrambi i casi. Ad esempio:

function Get-SumOfNumbers {
    param (
        [int[]]$Numbers
    )

    begin { $retValue = 0 }

    process {
        if ($null -ne $Numbers) {
           foreach ($n in $Numbers) {
               $retValue += $n
           }
        } else {
           $retValue += $_
        }
    }

    end { $retValue }
}

PS> 1,2,3,4 | Get-SumOfNumbers
10
PS> Get-SumOfNumbers 1,2,3,4
10

Quando si usa una funzione in una pipeline, gli oggetti inviati tramite pipe alla funzione vengono assegnati alla $input variabile automatica. La funzione esegue istruzioni con la begin parola chiave prima che tutti gli oggetti provengano dalla pipeline. La funzione esegue istruzioni con la end parola chiave dopo che tutti gli oggetti sono stati ricevuti dalla pipeline.

Nell'esempio seguente viene illustrata la $input variabile automatica con begin parole chiave e end .

function Get-PipelineBeginEnd {
    begin   { "Begin: The input is $input" }
    end     { "End:   The input is $input" }
}

Se questa funzione viene eseguita usando la pipeline, vengono visualizzati i risultati seguenti:

1,2,4 | Get-PipelineBeginEnd
Begin: The input is
End:   The input is 1 2 4

Quando l'istruzione begin viene eseguita, la funzione non ha l'input dalla pipeline. L'istruzione end viene eseguita dopo che la funzione ha i valori.

Se la funzione ha una process parola chiave, ogni oggetto in $input viene rimosso da $input e assegnato a $_. L'esempio seguente include un elenco di process istruzioni:

function Get-PipelineInput
{
    process {"Processing:  $_ " }
    end     {"End:   The input is: $input" }
}

In questo esempio, ogni oggetto inviato tramite pipe alla funzione viene inviato all'elenco process di istruzioni. Le process istruzioni vengono eseguite su ogni oggetto, un oggetto alla volta. La $input variabile automatica è vuota quando la funzione raggiunge la end parola chiave .

1,2,4 | Get-PipelineInput
Processing:  1
Processing:  2
Processing:  4
End:   The input is:

Per altre informazioni, vedere Uso di enumeratori

PowerShell 7.3 ha aggiunto il clean blocco. Il clean blocco è un modo pratico per consentire agli utenti di pulire le risorse create e usate nei beginblocchi , processe end . È semanticamente simile a un finally blocco che copre tutti gli altri blocchi denominati di una funzione script o un cmdlet di script. La pulizia delle risorse viene applicata per gli scenari seguenti:

  1. quando l'esecuzione della pipeline viene completata normalmente senza errori irreversibili
  2. quando l'esecuzione della pipeline viene interrotta a causa di un errore irreversibile
  3. quando la pipeline viene interrotta da Select-Object -First
  4. quando la pipeline viene arrestata da CTRL+C o StopProcessing()

Attenzione

L'aggiunta del clean blocco è una modifica che causa un'interruzione. Poiché clean viene analizzato come parola chiave, impedisce agli utenti di chiamare direttamente un comando denominato clean come prima istruzione in un blocco di script. Tuttavia, non è probabile che si tratti di un problema. Il comando può comunque essere richiamato usando l'operatore di chiamata (& clean).

Filtri

Un filtro è un tipo di funzione eseguita su ogni oggetto nella pipeline. Un filtro è simile a una funzione con tutte le relative istruzioni in un process blocco.

La sintassi di un filtro è la seguente:

filter [<scope:>]<name> {<statement list>}

Il filtro seguente accetta le voci di log dalla pipeline e quindi visualizza l'intera voce o solo la parte del messaggio della voce:

filter Get-ErrorLog ([switch]$Message)
{
  if ($Message) { Out-Host -InputObject $_.Message }
  else { $_ }
}

È possibile usare questa funzione come descritto di seguito:

Get-WinEvent -LogName System -MaxEvents 100 | Get-ErrorLog -Message

Ambito funzione

Esiste una funzione nell'ambito in cui viene creato.

Se una funzione fa parte di uno script, la funzione è disponibile per le istruzioni all'interno di tale script. Per impostazione predefinita, una funzione in uno script non è disponibile all'esterno di tale script.

È possibile specificare l'ambito di una funzione. Ad esempio, la funzione viene aggiunta all'ambito globale nell'esempio seguente:

function global:Get-DependentSvs {
  Get-Service | Where-Object {$_.DependentServices}
}

Quando una funzione si trova nell'ambito globale, è possibile usare la funzione negli script, nelle funzioni e nella riga di comando.

Le funzioni creano un nuovo ambito. Gli elementi creati in una funzione, ad esempio le variabili, esistono solo nell'ambito della funzione.

Per altre informazioni, vedere about_Scopes.

Ricerca e gestione di funzioni tramite la funzione: unità

Tutte le funzioni e i filtri in PowerShell vengono archiviati automaticamente nell'unità Function: . Questa unità viene esposta dal provider di funzioni di PowerShell.

Quando si fa riferimento all'unità Function: , digitare due punti dopo Funzione, come si farebbe quando si fa riferimento all'unità C o D di un computer.

Il comando seguente visualizza tutte le funzioni nella sessione corrente di PowerShell:

Get-ChildItem function:

I comandi nella funzione vengono archiviati come blocco di script nella proprietà di definizione della funzione. Ad esempio, per visualizzare i comandi nella funzione della Guida fornita con PowerShell, digitare:

(Get-ChildItem function:help).Definition

È anche possibile usare la sintassi seguente.

$function:help

Per altre informazioni sull'unità, vedere l'argomento Function: della Guida per il provider di funzioni . Digitare Get-Help Function.

Riutilizzo di funzioni nelle nuove sessioni

Quando si digita una funzione al prompt dei comandi di PowerShell, la funzione diventa parte della sessione corrente. La funzione è disponibile fino al termine della sessione.

Per usare la funzione in tutte le sessioni di PowerShell, aggiungere la funzione al profilo di PowerShell. Per altre informazioni sui profili, vedere about_Profiles.

È anche possibile salvare la funzione in un file di script di PowerShell. Digitare la funzione in un file di testo e quindi salvare il file con l'estensione .ps1 del nome file.

Scrittura della Guida per funzioni

Il Get-Help cmdlet ottiene la Guida per le funzioni, nonché per cmdlet, provider e script. Per ottenere assistenza per una funzione, digitare Get-Help seguito dal nome della funzione.

Ad esempio, per ottenere assistenza per la Get-MyDisks funzione, digitare:

Get-Help Get-MyDisks

È possibile scrivere la Guida per una funzione usando uno dei due metodi seguenti:

  • Guida basata su commenti per funzioni

    Creare un argomento della Guida usando parole chiave speciali nei commenti. Per creare una Guida basata su commenti per una funzione, è necessario inserire i commenti all'inizio o alla fine del corpo della funzione o sulle righe che precedono la parola chiave della funzione. Per altre informazioni sulla Guida basata su commenti, vedere about_Comment_Based_Help.

  • Guida basata su XML per le funzioni

    Creare un argomento della Guida basato su XML, ad esempio il tipo creato in genere per i cmdlet. La Guida basata su XML è necessaria se si localizzano argomenti della Guida in più lingue.

    Per associare la funzione all'argomento della Guida basata su XML, usare la .EXTERNALHELP parola chiave della Guida basata su commenti. Senza questa parola chiave, Get-Help non è possibile trovare l'argomento della Guida della funzione e le chiamate a Get-Help per la funzione restituiscono solo la Guida generata automaticamente.

    Per altre informazioni sulla .EXTERNALHELP parola chiave, vedere about_Comment_Based_Help. Per altre informazioni sulla Guida basata su XML, vedere How to Write Cmdlet Help.For more information about XML-based help, see How to Write Cmdlet Help.

Vedi anche