Syspass API Bash 脚本上的非变量识别

Non variable recognition on Syspass API Bash Script

当我在 curl 上输入带有 json 索引的变量时,它采用变量的字符串值,如果我将双引号转义,它returns 我是一个语法错误,因为在 json 请求中,您必须使用双引号输入数据。 示例:

#!/bin/bash

token="x"
tokenPass="x"
name="prueba"
url="https://prueba.prueba.prueba"
user="prueba"
pass="prueba"
notes="prueba"

curl -k -H "Content-Type:Application/json" -d '{"jsonrpc": "2.0", "method": "account/create", "params": { "authToken": "$token", "tokenPass": "$tokenPass", "name": "$name" , "categoryId": "7", "clientId": "9","login":"$user","url": "$url" ,"pass": "$pass","notes": "$notes"}, "id": 1}' -o- https://syspass.prueba.es/api.php

如果我手动输入数据,则 curl json 请求有效,但使用变量,当我创建帐户时,帐户被命名为字符串值关于变量,我的意思是,如果变量名为 $name ,则创建的帐户名称为 $name。有什么帮助吗? 我还尝试输入变量:“${variable}”并且两者都有效

试试这个:

curl -k -H "Content-Type:Application/json" -d '{"jsonrpc": "2.0", "method": "account/create", "params": { "authToken": "'${token}'", "tokenPass": "'${tokenPass}'", "name": "'${name}'" , "categoryId": "7", "clientId": "9","login":"'${user}'","url": "'${url}'" ,"pass": "'${pass}'","notes": "'${notes}'"}, "id": 1}' -o- https://syspass.prueba.es/api.php

一点解释: 单引号 ' 之间的文本不会被 bash 解释,这就是不会插入变量的原因。你必须把绳子弄断...... 另一个建议是您应该在变量周围使用花括号:When do we need curly braces around shell variables?

我这里针对变量token进行说明。其他变量可以用同样的方式处理。

假设变量 token 包含字符串 foo bar baz,那么您希望 curl 作为它的第 5 个接收参数以下字符串:

{"jsonrpc": "2.0", "method": "account/create", "params": { "authToken": "foo bar baz", "tokenPass":... rest omitted for brevity}

既然要变成单参数,就得把空洞字符串用某种方式引用起来,而且因为这个字符串包含很多双引号,用单引号包裹起来更方便。但是,这会阻止参数扩展。要做到这一点,变量必须在单引号之外。但是,它们也必须在双引号内,以免在变量包含空格时成为分词的受害者。这会产生以下解决方案:

curl .... '{"jsonrpc": "2.0", "method": "account/create", "params": { "authToken": "'"$token"'", "tokenPass": ... rest omitted for brevity}'

注意 $token 前面的 "'":第一个双引号将成为扩展 "foo bar baz" 的一部分。它必须是文字,因为 curl 想要看到它。下一个单引号终止初始单引号。下一个双引号告诉 shell 扩展 $token,但不尝试分词。

如果扩展的参数很多,结果表达式很难调试和维护。另一种方法是设置一个 HERE 文档:

# Set up Parameter 5 for curl
read p5 <<END
{"jsonrpc": "2.0", "method": "account/create", "params": { "authToken": "$token", "tokenPass":... rest omitted for brevity}
END

然后用作

curl .... -d "$p5"
 

这需要设置参数的单独步骤,但最终可读性更高,而且您也不必担心分词。

我会使用 jq 来生成 JSON 字符串(主要是为了为您处理引号,JSON 字符串并不简单),以及可读性(以及下一个维护者的理智)添加一些换行符和缩进:

data=$(
    jq  -n \
        --arg token "$token" \
        --arg tokenPass "$tokenPass" \
        --arg name "$name" \
        --arg url "$url" \
        --arg user "$user" \
        --arg pass "$pass" \
        --arg notes "$notes" \
        '{
            jsonrpc: "2.0",
            method: "account/create",
            params: { 
                authToken: $token,
                tokenPass: $tokenPass,
                name: $name,
                categoryId: "7",
                clientId: "9",
                login: $user,
                url: $url ,
                pass: $pass,
                notes: $notes
            },
            id: 1
        }'
)

curl -k \
     -H "Content-Type:Application/json" \
     -d "$data" \
     -o- \
     https://syspass.prueba.es/api.php