Was macht dieser reguläre Ausdruck?

Was macht dieser reguläre Ausdruck?

Mir wurde ein %post-Skript in einer Spezifikationsdatei bereitgestellt, um eine Konfigurationsdatei (mit dem Namen foo) zu bearbeiten. Ich wurde beauftragt, ein weiteres, fast identisches Skript zu schreiben, um eine Datei mit dem Namen „bar“ zu bearbeiten.

Meine Lösung für „bar“ funktioniert zwar technisch, unterscheidet sich aber semantisch erheblich. Der Verwalter bittet mich, sie der Einheitlichkeit halber neu zu schreiben.

foo.groovy vorher

messageQueue.secretKey = "<ENTER-KEY-HERE>" 

foo.groovy nach

messageQueue.secretKey = "y775hUYKR1Bm4gUWNRbzqg65"

Das mir gegebene Skript lautet wie folgt:

%define oauth_client_Secret \
echo "  Setting the message queue secret key..." \
MESSAGEQUEUESECRETKEY=`dd if=/dev/urandom count=16 bs=1 2>/dev/null | base64` \
for config_file in `find /opt/foo/etc -name *.groovy` \
do \
sed -i -e "/messageQueue.secretKey/ { " \\\
        -e "    s?^//\s*??" \\\
        -e "    s?<ENTER-KEY-HERE>?${MESSAGEQUEUESECRETKEY}?" \\\
        -e "}" \\\
    ${config_file} \
done

Was ich versuche herauszufinden:

  1. Was macht dieser reguläre Ausdruck? s?^//\s*??"Ich nehme an, er sucht nach einem Gleichheitszeichen?
  2. Was ist der Zweck der abschließenden Schrägstriche?\\\
  3. Warum hat der vorherige Autor den Ausdruck in Klammern gesetzt { }?

Als Referenz ist hier mein Skript (für Bar), das ich versuche, so umzuschreiben, dass es dem obigen Skript (für Foo) entspricht.

bar.groovy vorher

clientSecret:"<ENTER-CLIENTSECRET-HERE>",

bar.groovy nach

clientSecret:"4gUWNRbzqg65y775hUYKR1Bm",

Balkenskript

%define oauth_client_Secret \
echo "  Generating oauth clientSecret..." \
MESSAGEQUEUESECRETKEY=`dd if=/dev/urandom count=16 bs=1 2>/dev/null | base64` \
for config_file in `find /opt/bar/etc -name *.groovy` \
do \
sed -i "s/<ENTER-CLIENTSECRET-HERE>/${MESSAGEQUEUESECRETKEY}/g" ${config_file} \
done

Antwort1

In jeder Zeile, die den String enthält, messageQueue.secretKeyentfernt es den String //und alle darauf folgenden Leerzeichen, wenn sie am Anfang der Zeile vorhanden sind, und ersetzt das erste Vorkommen von <ENTER-KEY-HERE>durch den Inhalt der Shell-Variable ${MESSAGEQUEUESECRETKEY}. Die {Curlys beschränken die Entfernungen/Ersetzungen aufnurZeilen, die die Zeichenfolge enthalten messageQueue.secretKey. Diese Operationen werden auf der Datei ausgeführt, auf die durch die Shell-Variable verwiesen wird${config_file}.

Die \\\Backslashs setzen die Anweisung in einer langen Zeile fort und maskieren das unmittelbar folgende \nEwline-Zeichen, wenn das Skript von der Shell eingelesen wird. Drei sind notwendig, da diese in "Anführungszeichen stehen und der Backslash sich in diesem Kontext selbst maskiert. Die Shell erhält also eine maskierte Zeilenumbruchzeile und sedeine maskierte Zeilenumbruchzeile. Obwohl ich nicht weiß, wie es der Shell in diesem Kontext geht, glaube ich nicht, dass es sedihr etwas ausmachen würde, wenn die Zeilenumbrüche überhaupt nicht maskiert würden.

Antwort2

  1. Was macht dieser reguläre Ausdruck?s?^//\s*??"

Entfernen Sie in Zeilen, die messageQueue.secretKey enthalten, das //und alle auf den Zeilenanfang folgenden Leerzeichen mit:

  • das Fragezeichen ?als Mustertrennzeichen
  • ^entspricht dem Anfang einer Zeile
  • //stimmt genau damit überein (nebenbei bemerkt ist das der Grund, warum man als Mustertrennzeichen das Fragezeichen anstelle des gebräuchlicheren verwendet, /das ziemlich viel Escape verhindert, weil sonst der reguläre Ausdrucks/^\/\/\s*//
  • \s*ist GNU sed spezifisch für match oder oder mehr Leerzeichen spaceund/oder Tab; POSIX sed würde verwenden[:space:]

Und @mikeserv hat gerade eine noch umfassendere Antwort gepostet …

verwandte Informationen