使用 bash 脚本从 plist 中提取字符串,也许是 sed?

发布于 2024-09-14 21:56:06 字数 710 浏览 5 评论 0原文

所以这是我的问题。 如何使用 bash 脚本将这些字符串提取到 3 个变量中?

所以出于这个:

<key>GameDir</key> <string>C:/Program Files/</string> <key>GameEXE</key> <string>C:/Program Files/any.exe</string> <key>GameFlags</key> <string>-anyflag</string>

我想要:

GameDir=C:/Program Files/
GameEXE=C:/Program Files/any.exe
GameFlags=-anyflag

示例脚本:

echo GameDir
echo GameEXE
echo GameFlags

示例输出:

C:/Program Files/
C:/Program Files/any.exe
-anyflag

键的顺序没有改变,只有字符串本身。 我使用的是 OS X,因此它需要是一个在 OS X 上开箱即用的命令。 也许这可以与 sed 一起使用吗?

谢谢 德拉库利克斯

So here is my problem.
How can I extract those strings into 3 variables with a bash script?

So out of this:

<key>GameDir</key> <string>C:/Program Files/</string> <key>GameEXE</key> <string>C:/Program Files/any.exe</string> <key>GameFlags</key> <string>-anyflag</string>

I want:

GameDir=C:/Program Files/
GameEXE=C:/Program Files/any.exe
GameFlags=-anyflag

Example Script:

echo GameDir
echo GameEXE
echo GameFlags

Example Output:

C:/Program Files/
C:/Program Files/any.exe
-anyflag

The order of the keys is not changing, only the strings itself.
I am using OS X, so it needs to be a command that works out-of-the-box on OS X.
Maybe this could work with sed?

Thanks
Drakulix

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

2024-09-21 21:56:06

您可以使用 /usr/libexec/PlistBuddy 来实现此目的,它似乎至少从 10.5 开始就包含在 OS X 中(手册页)。示例:

file="$HOME/yourfile"
/usr/libexec/PlistBuddy -c "Print" "$file"

您可以像这样分配您感兴趣的变量:

for var in GameDir GameEXE GameFlags ; do
    val=$( /usr/libexec/PlistBuddy -c "Print $var" "$file" )
    eval "export $var='$val'"
    echo "$var = $val"
done

它似乎比 bash/sed/awk 正则表达式更具可读性,并且由于它是特定于 plist 的工具,我认为它对于提取值来说是可靠的。请注意,按键区分大小写。

You could use /usr/libexec/PlistBuddy for this, which seems to be included in OS X since at least 10.5 (man page). Example:

file="$HOME/yourfile"
/usr/libexec/PlistBuddy -c "Print" "$file"

And you could assign the vars you're interested in like this:

for var in GameDir GameEXE GameFlags ; do
    val=$( /usr/libexec/PlistBuddy -c "Print $var" "$file" )
    eval "export $var='$val'"
    echo "$var = $val"
done

It seems more readable than bash/sed/awk regexes, and since it is a plist-specific tool, I presume it is reliable for extracting values. Just be aware that the keys are case-sensitive.

别在捏我脸啦 2024-09-21 21:56:06

假设 Bash 版本 >= 3.2

string='<key>GameDir</key> <string>C:/Program Files/</string> <key>GameEXE</key> <string>C:/Program Files/any.exe</string> <key>GameFlags</key> <string>-anyflag</string>'

string=$(<file)

pattern='<key>([^<]*)</key>[[:blank:]]*<string>([^<]*)</string>[[:blank:]]*'
pattern=$pattern$pattern$pattern
[[ $string =~ $pattern ]]    # extract the matches into ${BASH_REMATCH[@]}
for ((i=1; i<${#BASH_REMATCH[@]}; i+=2))
do
    declare ${BASH_REMATCH[i]}="${BASH_REMATCH[i+1]}"    # make the assignments
done
echo $GameDir    # these were missing dollar signs in your question
echo $GameEXE
echo $GameFlags

Assuming Bash version >= 3.2

string='<key>GameDir</key> <string>C:/Program Files/</string> <key>GameEXE</key> <string>C:/Program Files/any.exe</string> <key>GameFlags</key> <string>-anyflag</string>'

or

string=$(<file)

and

pattern='<key>([^<]*)</key>[[:blank:]]*<string>([^<]*)</string>[[:blank:]]*'
pattern=$pattern$pattern$pattern
[[ $string =~ $pattern ]]    # extract the matches into ${BASH_REMATCH[@]}
for ((i=1; i<${#BASH_REMATCH[@]}; i+=2))
do
    declare ${BASH_REMATCH[i]}="${BASH_REMATCH[i+1]}"    # make the assignments
done
echo $GameDir    # these were missing dollar signs in your question
echo $GameEXE
echo $GameFlags
十年不长 2024-09-21 21:56:06

您可以使用 awk,这适用于多行和多个键、字符串值。

$ cat file
<key>GameDir</key> <string>C:/Program Files/
   </string>
<key>GameEXE</key>
  <string>C:/Program Files/any.exe
 </string> <key>GameFlags</key> <string>-anyflag</string>

$ awk -vRS="</string>" '/<key>/{gsub(/<key>|<string>|\n| +/,"") ; sub("</key>","=") ;print}' file
GameDir=C:/ProgramFiles/
GameEXE=C:/ProgramFiles/any.exe
GameFlags=-anyflag

使用 eval 创建变量

$ eval $(awk -vRS="</string>" '/<key>/{gsub(/<key>|<string>|\n| +/,"") ; sub("</key>","=") ;print}' file )
$ echo $GameDir
C:/ProgramFiles/

you can use awk, this works for multiline and multiple key, string values.

$ cat file
<key>GameDir</key> <string>C:/Program Files/
   </string>
<key>GameEXE</key>
  <string>C:/Program Files/any.exe
 </string> <key>GameFlags</key> <string>-anyflag</string>

$ awk -vRS="</string>" '/<key>/{gsub(/<key>|<string>|\n| +/,"") ; sub("</key>","=") ;print}' file
GameDir=C:/ProgramFiles/
GameEXE=C:/ProgramFiles/any.exe
GameFlags=-anyflag

Use eval to create the variables

$ eval $(awk -vRS="</string>" '/<key>/{gsub(/<key>|<string>|\n| +/,"") ; sub("</key>","=") ;print}' file )
$ echo $GameDir
C:/ProgramFiles/
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文