Ich verwende git und poste dann die Festschreibungsnachricht und andere Bits als JSON-Payload auf einem Server.
Zur Zeit habe ich:
MSG=`git log -n 1 --format=oneline | grep -o ' .\+'`
was setzt MSG auf etwas wie:
Calendar can't go back past today
dann
curl -i -X POST \
-H 'Accept: application/text' \
-H 'Content-type: application/json' \
-d "{'payload': {'message': '$MSG'}}" \
'https://example.com'
Mein echter JSON hat noch ein paar Felder.
Das funktioniert gut, aber wenn ich eine Commit-Nachricht wie die oben stehende mit einem Apostroph darin habe, ist die JSON natürlich ungültig.
Wie kann ich die in bash benötigten Zeichen entziehen? Ich bin nicht mit der Sprache vertraut, daher bin ich mir nicht sicher, wo ich anfangen soll. Das Ersetzen von '
durch \'
würde die Aufgabe zumindest erfüllen, was ich vermute.
OK, herausgefunden, was zu tun ist. Bash unterstützt dies nativ wie erwartet, allerdings ist die Syntax wie immer nicht wirklich erraten!
Im Wesentlichen gibt ${string//substring/replacement}
das Bild zurück, das Sie erstellt haben, sodass Sie es verwenden können
MSG=${MSG//\'/\\\'}
Um dies zu tun. Das nächste Problem ist, dass der erste Regex nicht mehr funktioniert, der aber durch ersetzt werden kann
git log -n 1 --pretty=format:'%s'
Am Ende musste ich ihnen nicht einmal entkommen. Stattdessen habe ich einfach alle 'in der JSON zu\"ausgetauscht.
Python verwenden:
Diese Lösung ist keine reine Bash, aber sie ist nicht invasiv und verarbeitet Unicode.
json_escape () {
printf '%s' "$1" | python -c 'import json,sys; print(json.dumps(sys.stdin.read()))'
}
Beachten Sie, dass JSON bereits seit langer Zeit Teil der Standard-Python-Bibliotheken ist. Daher ist dies eine ziemlich geringe Abhängigkeit von Python.
Oder mit PHP:
json_escape () {
printf '%s' "$1" | php -r 'echo json_encode(file_get_contents("php://stdin"));'
}
Gebrauch wie folgt:
$ json_escape "ヤホー"
"\u30e4\u30db\u30fc"
Statt sich darum zu kümmern, wie die Daten korrekt zitiert werden sollen, speichern Sie sie einfach in einer Datei und verwenden Sie das @
-Konstrukt, das curl
mit der Option --data
zulässt. Um sicherzustellen, dass die Ausgabe von git
für die Verwendung als JSON-Wert korrekt escape ist, verwenden Sie ein Tool wie jq
, um den JSON zu generieren, anstatt ihn manuell zu erstellen.
jq -n --arg msg "$(git log -n 1 --format=oneline | grep -o ' .\+')" \
'{payload: { message: $msg }}' > git-tmp.txt
curl -i -X POST \
-H 'Accept: application/text' \
-H 'Content-type: application/json' \
-d @git-tmp.txt \
'https://example.com'
Sie können mit -d @-
auch direkt aus der Standardeingabe lesen. Ich lasse das als Übung für den Leser, um die Pipeline zu erstellen, die aus git
liest und die korrekte Nutzlastnachricht erzeugt, die mit curl
hochgeladen wird.
(Hinweis: es ist jq ... | curl ... [email protected] 'https://example.com'
)
JSON, когда натолкнулся экранировать символы Bash для передачи с помощью JSON, когда натолкнулся нато. Я обнаружил, что на самом деле есть больший список символов, которые должны быть экранированы - особенно если вы пытаетесь обрабатывать текст произвольной формы.
Weitere Informationen zu diesem Produkt:
${string//substring/replacement}
, описанный в этой теме.Weitere Informationen zu Bash:
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//\\/\\\\} # \
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//\//\\\/} # /
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//\'/\\\'} # ' (not strictly needed ?)
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//\"/\\\"} # "
JSON_TOPIC_RAW=${JSON_TOPIC_RAW// /\\t} # \t (tab)
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//
/\\\n} # \n (newline)
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//^M/\\\r} # \r (carriage return)
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//^L/\\\f} # \f (form feed)
JSON_TOPIC_RAW=${JSON_TOPIC_RAW//^H/\\\b} # \b (backspace)
In diesem Fall können Sie den Artikel (in englischer Sprache) von (in englischer Sprache) von (in englischer Sprache) von (in englischer Sprache) eingeben. Я обновлю свой ответ, если я решу это.
jq
kann dies tun.
Leicht, kostenlos und in C geschrieben, genießt jq
weit verbreitete Community-Unterstützung mit über 12,5.000 Sternen auf GitHub . Ich persönlich finde es sehr schnell und nützlich in meinem täglichen Arbeitsablauf.
jq -aR . <<< '猫に小判'
Erklären,
-a
bedeutet "ASCII-Ausgabe"-R
bedeutet "rohe Eingabe".
bedeutet "Ausgabe des Stammes des JSON-Dokuments"<<<
übergibt einen String an stdin (nur bash?)Um das vom OP angegebene Codebeispiel zu korrigieren, leiten Sie einfach jq durch.
MSG=`git log -n 1 --format=oneline | grep -o ' .\+' | jq -aR .`
Ich habe so etwas gefunden:
MSG=`echo $MSG | sed "s/'/\\\\\'/g"`
Der einfachste Weg ist die Verwendung von jshon , einem Befehlszeilentool zum Analysieren, Lesen und Erstellen von JSON.
jshon -s 'Your data goes here.' 2>/dev/null
git log -n 1 --format=oneline | grep -o ' .\+' | jq --Slurp --raw-input
Die obige Zeile funktioniert für mich. Weitere jq
-Tools finden Sie unter https://github.com/stedolan/jq
Dies ist eine Escape-Lösung, die Perl verwendet und Backslash (\
), Anführungszeichen ("
) und Steuerzeichen U+0000
bis U+001F
:
$ echo -ne "Hello, ????\n\tBye" | \
Perl -pe 's/(\\(\\\\)*)/$1$1/g; s/(?!\\)(["\x00-\x1f])/sprintf("\\u%04x",ord($1))/eg;'
Hello, ????\u000a\u0009Bye
Ich hatte die gleiche Idee, eine Nachricht mit Commit-Nachricht nach Commit zu verschicken . Zuerst versuchte ich es ähnlich wie hier als Autor. Aber später eine bessere und einfachere Lösung gefunden.
Erstellte gerade eine PHP-Datei, die eine Nachricht sendet, und rufe sie mit wget . In hooks/post-receive auf:
wget -qO - "http://localhost/git.php"
in git.php:
chdir("/opt/git/project.git");
$git_log = exec("git log -n 1 --format=oneline | grep -o ' .\+'");
Erstellen Sie anschließend JSON und rufen Sie CURL im Stil PHP auf