如何在bash脚本中转义用curl发布的JSON变量?

How to escape a JSON variable posted with curl in bash script?

我将通过其API在bash脚本中向mandrill提交一条消息,"message"变量的内容导致API调用返回并返回一个错误:

1
An error occured: {"status":"error","code":-1,"name":"ValidationError","message":"You must specify a key value"}

$message_body变量的内容是:

1
2
3
4
5
6
7
8
9
10
11
12
Trigger: Network traffic high on 'server'
Trigger status: PROBLEM
Trigger severity: Average
Trigger URL:

Item values:

1. Network traffic inbound (server:net.if.in[eth0,bytes]): 3.54 MBytes
2. Network traffic outbound (server:net.if.out[eth0,bytes]): 77.26 KBytes
3. *UNKNOWN* (*UNKNOWN*:*UNKNOWN*): *UNKNOWN*

Original event ID: 84

我不确定字符串的哪一部分正在丢弃它,但似乎是某些原因导致了JSON在提交到mandrill的API时无效。

如果我将上述消息更改为"testing 123"之类的简单消息,则消息将成功提交。

发布的代码如下:

1
2
3
4
5
6
#!/bin/bash
...
message_body = `cat message.txt`
msg='{"async": false,"key":"'$key'","message": {"from_email":"'$from_email'","from_name":"'$from_name'","headers": {"Reply-To":"'$reply_to'" },"auto_html": false,"return_path_domain": null,"subject":"'$2'","text":"'$message_body'","to": [ {"email":"'$1'","type":"to" } ] } }'
results=$(curl -A 'Mandrill-Curl/1.0' -d"$msg" 'https://mandrillapp.com/api/1.0/messages/send.json' -s 2>&1);
echo"$results"

我该怎么做才能确保$message_body变量已经准备好并准备好作为有效的JSON提交?


我怀疑问题在于缺乏对变量的引用

1
2
msg='{"async": false,"key":"'$key'","message": {"from_email":"'$from_email'","from_name":"'$from_name'","headers": {"Reply-To":"'$reply_to'" },"auto_html": false,"return_path_domain": null,"subject":"'$2'","text":"'$message_body'","to": [ {"email":"'$1'","type":"to" } ] } }'
# ..............................^^^^ no quotes around var ...........^^^^^^^^^^^...................^^^^^^^^^^...............................^^^^^^^^^...................................................................^^..............^^^^^^^^^^^^^.........................^^

尝试这样做:对每个变量中的任何双引号进行转义。

1
2
3
4
5
6
7
8
9
10
11
escape_quotes() { echo"${1//"/\\"}"; }
msg=$(
    printf '{"async": false,"key":"%s","message": {"from_email":"%s","from_name":"%s","headers": {"Reply-To":"%s" },"auto_html": false,"return_path_domain": null,"subject":"%s","text":"%s","to": [ {"email":"%s","type":"to" } ] } }' \
       "$(escape_quotes"$key")"          \
       "$(escape_quotes"$from_email")"   \
       "$(escape_quotes"$from_name")"    \
       "$(escape_quotes"$reply_to")"     \
       "$(escape_quotes"$2")"            \
       "$(escape_quotes"$message_body")" \
       "$(escape_quotes"$1")"
)