Comando type in Bash: distinguere alias, funzioni, builtin e file

type è un comando interno di Bash, detto builtin, che indica come la shell interpreta un nome: alias, parola riservata, funzione, comando interno o file eseguibile. Usatelo per capire perché un comando richiama una funzione o un programma diverso da quello atteso.

type tiene conto dello stato della shell in cui lo eseguite, compresi alias e funzioni. which cerca invece soprattutto eseguibili nel PATH, secondo la sua implementazione. Per diagnosticare una sessione Bash, iniziate quindi da type.

Che cos’è type in Bash?

Bash interpreta la sintassi e le eventuali espansioni degli alias, poi risolve i nomi dei comandi tramite funzioni, builtin ed eseguibili nel PATH. type descrive questa interpretazione senza eseguire il comando cercato. Il risultato va letto nel contesto della shell e delle sue opzioni.

Questa guida riguarda Bash. Altre shell offrono comandi simili, ma possono usare opzioni e formati diversi; controllate il loro aiuto prima di riutilizzare gli esempi.

Sintassi di base e tipi di risultato

type [-afptP] [name...]

Indicate uno o più nomi dopo le opzioni; [name...] è un segnaposto, non testo da copiare. Questi esempi chiedono informazioni su programmi, builtin e sulla parola riservata if, senza eseguirli:

type ls
type cd
type if
type printf

L’output normale è descrittivo e può cambiare con versione e lingua. Il valore dipende dagli alias, dalle funzioni e dai programmi disponibili nella shell corrente:

Tipo Significato
alias Alias: sostituzione testuale del nome durante la lettura del comando, quando l’espansione è attiva.
keyword Parole riservate della shell come if e for.
function Funzioni definite nella shell corrente.
builtin Comando eseguito internamente da Bash.
file File eseguibile esterno; può essere individuato tramite PATH o un percorso esplicito.

Vedere tutti i candidati con lo stesso nome

-a elenca le corrispondenze disponibili: alias, parole riservate, funzioni, builtin e file eseguibili. È utile per scoprire candidati nascosti da un nome già definito.

type -a printf
type -a test
type -a ls

printf può essere sia un builtin sia un programma esterno. type printf mostra l’interpretazione principale; type -a printf può mostrare entrambe. Per limitare l’elenco agli eseguibili nel PATH, potete combinare -a e -p: type -ap printf non consulta la tabella hash.

Opzioni per la selezione del formato di output

Ottenere soltanto il tipo con -t

-t restituisce una sola parola per nome: alias, keyword, function, builtin o file. Se il nome non viene trovato, non stampa il tipo e termina con uno stato diverso da zero. Con più nomi, lo stato complessivo è di successo solo se vengono trovati tutti.

type -t cd
type -t if
type -t ls

Cercare percorsi con -p e -P

-p stampa il percorso solo quando il nome è risolto come file eseguibile. Per un alias, una funzione o un builtin può non stampare nulla: l’assenza di percorso non dimostra da sola che il nome sia sconosciuto. Per esempio, cd è normalmente un builtin.

type -p ls
type -p cd

-P cerca un file eseguibile anche se il nome identifica un alias, una funzione o un builtin. L’operazione è soltanto una ricerca: non cambia la precedenza usata quando eseguite normalmente quel nome.

type -P printf
type -P test

Se Bash ha memorizzato un percorso nella tabella hash, -p e -P possono mostrare quel valore anziché il primo file del PATH. Per confrontare la ricerca senza questa cache, usate type -ap NOME; per svuotare la cache della shell corrente usate hash -r.

Opzioni di type

Opzione Descrizione
-a Stampa tutti i candidati che corrispondono al nome.
-f Salta la ricerca delle funzioni; funziona anche senza -a.
-p Stampa il percorso quando il risultato dell'interpretazione predefinita è un eseguibile esterno.
-P Cerca un file anche se il nome è un alias, una funzione o un builtin; non modifica la precedenza dei comandi.
-t Stampa il tipo di comando come una singola parola.

Diagnosticare alias e funzioni

Controllare gli alias

Una sessione interattiva può definire alias che aggiungono opzioni, per esempio a ls. type ls mostra l’interpretazione corrente e alias ls ne mostra la definizione se esiste. Se l’alias non è definito, il secondo comando termina senza successo: non significa che manchi il programma ls.

type ls
alias ls

Un backslash davanti al nome impedisce l’espansione dell’alias, ma non salta una funzione con lo stesso nome. Un percorso assoluto identifica invece il file da eseguire: /usr/bin/ls è un percorso comune su Linux, da verificare sul vostro sistema con type -P ls.

\ls
/usr/bin/ls

Controllare le funzioni

Una funzione può nascondere un programma esterno con lo stesso nome. L’esempio seguente definisce una funzione dimostrativa, senza eseguire alcuna distribuzione software, poi ne mostra definizione e tipo. Provatelo in una nuova sessione Bash e rimuovete la funzione al termine con unset -f deploy.

deploy() {
  printf '%s\n' 'Funzione dimostrativa: nessuna distribuzione eseguita.'
}
type deploy
type -t deploy

Dentro una funzione, command NOME esegue il comando saltando la ricerca delle funzioni. Può però scegliere un builtin prima di un file esterno: per richiedere uno specifico programma usate un percorso assoluto verificato. Anche type -f NOME salta le funzioni durante la diagnosi, senza eseguire il nome cercato.

Confronto tra type, command -v e which

Metodo Caratteristiche
type name Spiega in dettaglio alias, parole riservate, funzioni, comandi integrati e file in Bash.
type -a name Controlla tutti i possibili candidati con lo stesso nome.
command -v name Relativamente portabile per controllare l'esistenza e la risoluzione dei comandi negli script shell.
which name A seconda dell'implementazione, trova principalmente file eseguibili in PATH e potrebbe non riflettere accuratamente le funzioni shell o gli alias.

Per la diagnosi in Bash usate type; negli script destinati a shell conformi a POSIX, command -v è una scelta portabile per verificare la risoluzione di un nome. Nessuno di questi controlli dimostra che il programma, una volta avviato, completerà correttamente il lavoro.

Usare type negli script Bash

Distinguere i tipi di comando

if [ "$#" -ne 1 ] || [ -z "$1" ]; then
  printf '%s\n' 'Uso: bash tipo-comando.sh NOME' >&2
  exit 2
fi

kind=$(type -t -- "$1") || {
  printf 'Nome non trovato: %s\n' "$1" >&2
  exit 1
}

case $kind in
  alias|function|builtin|file|keyword)
    printf '%s: %s\n' "$1" "$kind"
    ;;
esac

Salvate l’esempio completo in tipo-comando.sh ed eseguite bash tipo-comando.sh cd. In una sessione senza ridefinizioni, il risultato è cd: builtin; un nome inesistente produce un messaggio e stato 1. Lo script richiede Bash e un solo nome non vuoto. Una nuova esecuzione di Bash non eredita automaticamente gli alias o tutte le funzioni della sessione interattiva: per diagnosticare quella sessione, eseguite lì direttamente type.

Controllare lo stato di uscita

Se vi interessa soltanto se Bash riconosce un nome, controllate lo stato di uscita e non la frase stampata. L’esempio seguente riconosce il nome git, anche se è un alias o una funzione. Per richiedere un eseguibile esterno, scegliete invece type -P git. Salvate il blocco in verifica-git.sh ed eseguite bash verifica-git.sh: se il nome è riconosciuto, stampa il messaggio di successo; altrimenti stampa un messaggio sullo standard error e termina con stato 1.

if type git >/dev/null 2>&1; then
  printf '%s\n' 'Bash riconosce il nome git.'
else
  printf '%s\n' 'Nome git non trovato.' >&2
  exit 1
fi

Domande frequenti

type -p non restituisce nulla

Il nome può essere un alias, una funzione o un builtin; oppure può mancare un eseguibile esterno. Guardate type -a NOME per vedere le forme disponibili e type -P NOME per richiedere un percorso di file. Un builtin noto può dare output vuoto con -p e avere comunque stato di successo.

Perché vedo un percorso memorizzato o diverso da quello atteso?

Un percorso memorizzato può influire su -p e -P. Tuttavia, in Bash una normale assegnazione a PATH svuota la tabella hash: dopo una modifica non attribuite automaticamente il vecchio risultato alla cache. Controllate anche alias, funzioni, valore effettivo di PATH e sessione in cui avete fatto la modifica. Questi comandi mostrano la cache, la svuotano e cercano di nuovo ls:

hash
hash -r
type -P ls

Perché gli alias della sessione non compaiono negli script?

In Bash non interattivo l’espansione degli alias è disabilitata per impostazione predefinita; inoltre, una nuova shell non eredita automaticamente gli alias della sessione chiamante. Definire un alias non basta a renderlo attivo nel contesto dello script. Per l’automazione preferite funzioni o comandi espliciti, senza dipendere dagli alias interattivi.

Il comando type trova solo la posizione dei file eseguibili?

No. Distingue anche alias, parole riservate, funzioni e builtin. Con -P potete limitare la diagnosi alla ricerca di un file eseguibile.

L'ordine dell'output di type -a indica la priorità di esecuzione?

L’elenco aiuta a capire quali definizioni si sovrappongono, ma non sostituisce le regole della sintassi, le opzioni o il contesto. Un percorso memorizzato può differire dall’elenco dei candidati nel PATH; confrontate l’output normale con type -ap NOME se sospettate una differenza.

Le altre shell usano le stesse opzioni?

Non necessariamente. Le opzioni descritte qui appartengono a Bash; per Zsh, Dash o altre shell consultate la rispettiva documentazione. Evitate di copiare opzioni specifiche di Bash in uno script avviato con un’altra shell.

Scegliere il controllo corretto

Partite da type NOME per leggere l’interpretazione corrente, usate -a per vedere le alternative e -t per ottenere il tipo. Per cercare un file anche quando un builtin o una funzione lo nasconde, usate -P, ricordando il possibile effetto della tabella hash.

Quando un comando si comporta in modo inatteso, controllate lo stesso ambiente in cui viene eseguito: nomi, alias, funzioni, PATH e cache possono differire tra terminale, script e nuove sessioni Bash.

Documentazione di riferimento