Kann ich mit bash alle Funktionen in einer Skriptdatei abrufen?

0

Wenn ich eine Datei habe:
dome.sh

$ls -l dome.sh
-rwxrwxr-x 1 user user 0 Aug  8 11:19 dome.sh

und der Inhalt der Datei ist ähnlich wie:

#!/bin/bash
function() {
    'work'
    }
another() {
    'different work'
    }
...
#30 functions later
yetANOTHERfunction () {
    'even more work'
    }

Wobei "# 30 Funktionen später" bedeutet, dass es 30 eindeutige Zusatzfunktionen gibt

Kann ich alle Funktionen in diesem Skript irgendwie durchlaufen, um sie zu identifizieren?

so etwas wie:

for i in $(get all functions in this file); do
    echo $i
done

produzieren:

function
another
...
yetANOTHERfunction
spezticle
quelle

Antworten:

1

Wenn Sie das "F" in "declare -F" großschreiben, werden Zeilen wie "declare -f functionName" zurückgegeben. Jetzt müssen Sie nur noch den ersten Teil dieser Zeile abschneiden. Hier ist der Code:

#!/bin/bash
function () {
   return
}
another () {
   return
}
yetANOTHERfunction () {
   return
}
IFS=$'\n'
for f in $(declare -F); do
   echo "${f:11}"
done
bashBedlam
quelle
Oder gerade Rohr cutso: declare -F | cut -d ' ' -f3.
Toby Speight
0

Versuchen:

get_fcn_list () {
    env -i bash --noprofile --norc -c '
    source "'"$1"'"
    typeset -f |
    grep '\''^[^{} ].* () $'\'' |
    awk "{print \$1}" |
    while read -r fcn_name; do
        type "$fcn_name" | head -n 1 | grep -q "is a function$" || continue
        echo "$fcn_name"
    done
'
}

for fcn_name in $(get_fcn_list dome.sh); do
    echo "$fcn_name"
done

Erläuterung:

  • Anstatt die Funktionen selbst zu bashanalysieren , lassen Sie sie analysieren (mit source) und den Inhalt sichern ( typeset -f).

  • Der Aufruf env -i bash --noprofile --norcsoll verhindern bash, dass Initialisierungsdateien gelesen werden. Andernfalls erhalten Sie möglicherweise Funktionen, die z ~/.bashrc. B. in definiert sind .

  • typeset -fDump alle Funktionen und deren Definitionen. Jede Definition beginnt mit: Funktionsname , Raum , (), Raum , Newline . grepund awkextrahieren Sie die Funktionsnamen aus diesen Zeilen.

  • Der Grund für den Filter ist, dass Sie möglicherweise falsche Positive erhalten, wenn Sie Funktionen wie:

    f () 
    { 
        echo "
    a () 
    "
    }

    Hier whilewürde die Schleife fälschlicherweise gedruckt a, aber der Filter kümmert sich darum.

  • Bearbeitet, um Funktionen aus einer Datei zu drucken und Startdateien nicht einzuschließen.

Matei David
quelle
Danke für diese Antwort. Möglicherweise brauche ich ein oder zwei Tage, um mich wieder mit diesem Projekt zu befassen, aber ich werde es überprüfen und als Antwort markieren.
Artikel
Um die Sache zu vereinfachen, können Sie das Builtin declare -fohne weitere Argumente innerhalb des Skripts aufrufen , um eine Liste der darin enthaltenen Funktionsdefinitionen zu erhalten. Mit anderen Worten, wenn Sie die Zeile declare -f am Ende eines Skripts hinzugefügt und aus einer Shell bezogen haben, werden die Funktionsdefinitionen nur in diesem Skript an das Terminal ausgegeben. Es gibt sowohl den Funktionsnamen als auch den Hauptteil aus. Wenn Sie also nur den Namen wünschen, müssen Sie diese Ausgabe durch sed / grep leiten. In einer realen Anwendung möchten Sie die Funktionsliste wahrscheinlich selektiv basierend auf den Kriterien Ihrer Wahl ( dh Argument).
Argonauten
1) declareund typesetsind der gleiche Befehl. 2) Alle Funktionen Ihrer Shell (nicht unbedingt aus der Datei von Interesse) werden in der Ausgabe angezeigt. Dies ist der zweite Punkt oben.
Matei David