シェルスクリプトでWebサーバーの応答を解析しようとしています。応答は次のとおりです。
HTTP/1.0 404 NOT FOUND
Content-Length: 223
Content-Type: application/json
Last-Modified: Fri, 21 Aug 2020 15:24:23 GMT
Cache-Control: public, max-age=43200
Expires: Sat, 22 Aug 2020 08:04:19 GMT
ETag: "1598023463.02863-223-4034336499"
Date: Fri, 21 Aug 2020 20:04:19 GMT
Server: Werkzeug/1.0.1 Python/3.8.5
{
"message": {
"status": "404",
"message": "Not Found"
}
}
変数に割り当てます。
% foo="$(curl -i http://127.0.0.1/404)"
1つの変数ではなく、ステータスコード用の1つの変数と応答本文用の1つの変数が必要です。ステータスコードを取得するのは簡単です。
% echo "$foo" | head -n 1
難しい部分は、sedを使用してヘッダーをフィルタリングすることです。に基づいてブルース・バーネット(Bruce Barnett) 素晴らしい Sed グリモワール、私の考えはこれがうまくいくと思います:
% echo "$foo" | sed '1,/^$/ d'
または:
% echo "$foo" | sed -n '/^$/,$ p'
しかし、両方のコマンドの結果は何もありません。理由がわからない。
重要な場合は、Homebrewのzsh 5.8とGNU sed 4.8を使用し、Mac OSのcurl 7.64.1を使用しています。
ベストアンサー1
RFC7230では、ヘッダーはCR-LFペア、その後にCRLFペア(CRLF - CRLF)(緩い用語:空行)、HTTPレスポンスの「本文」で区切る必要があります。したがって、通常のhttp/1.1には一部が含まれます。入力する。
\n\n
Unixで説明したように、ヘッダーに無限の空白行がありません。これはまた、sedの場合、aがヘッダーの^$
末尾にある空(DOS)行と一致しないことを意味します。対応する行に\r
(キャリッジリターン)が含まれているためです。 (GNU)sedでこの(ほぼ)空の行を検出する別の方法は次のとおりです^\r$
。
$ printf '%s\n' "$foo" | sed '1,/^\r$/ d'
キャリッジリターンの削除
キャリッジリターンの削除が適用される場合、http応答(サーバーがエクスポートする完全なhttp / 1.1メッセージ)には、\n\n
ヘッダーと本文を区別するために2つの連続する改行()で空白行が含まれます。
そうであれば、特別な値であるnull RS
(awkの短絡モード)がこのヘッダーを処理できます。
$ echo "$foo" | tr -d '\r' | awk -v RS="" 'NR>1'
または、メール本文の空白行を保持するには、次の手順を実行します。
$ echo "$foo" | tr -d '\r' | awk 'BEGIN{ORS=RS="\n\n"}NR>1'
キャリッジリターンを許可
ただし、メッセージ(RFC5322など)とhttp応答(RFC7230などの完全なhttp / 1.1メッセージ)は、次のようにCR NL
使用する必要があります。タイトルの行末タグ。 RSには以下を含めることができます。任意に選択できるキャリッジリターンには正規表現が必要で、定数ではないため、RT(レコードターミネータ)を使用します。これはGNU awkを使用する必要があることを意味します。
$ echo "foo" | awk 'BEGIN{RS="(\r?\n){2}"}NR>1{printf "%s%s",$0,RT}'
{
"message": {
"status": "404",
"message": "Not Found"
}
}