0

我编写了一个脚本,它会为 javac 生成适当的参数来编译我的项目,以便更加精通 shell 脚本。

奇怪的是..脚本运行良好,但如果脚本使用这些参数运行 javac 它将不起作用,并且如果我在交互式 shell 中运行完全相同的命令,它会起作用。一切都以绝对路径输出,所以我在这里几乎不知所措。

示例目录结构:

src/File.java
src/File.png
src/dir/File2.java
jars/Library.jar

预期输出:

build/File.class
build/File.png
build/dir/File2.class

外壳脚本:

#! /bin/sh

cwd=$(pwd)

if [ -d "build" ]; then
    rm -rf $cwd/build/*
else
    mkdir $cwd/build
fi

find $cwd/src \( ! -path '*/.*' \) -type f ! -iname "*.java" | xargs -I{} cp --parents {} $cwd/build

cmd=$(echo javac -sourcepath $cwd/src -classpath $(find $cwd/jars -type f | awk '{ printf("\"%s\";", $0);}'  | awk '{ print substr($0, 0, length($0)); }') -d $cwd/build $(find $cwd/src \( ! -path '*/.*' \) -type f -iname "*.java"))

$cmd
echo $cmd

命令输出:

javac -sourcepath /home/test/src -classpath "/home/test/jars/Library.jar" -d /home/test/build /home/test/src/File.java /home/test/src/dir/File2.java

我的实际项目太大而无法在此处发布,但基本上会发生大量错误输出,好像类路径设置不正确(它们是库函数上的错误)。如果我从 echo 语句中复制命令,粘贴它,然后按回车,它可以完美运行。

我不明白。

有任何想法吗?

4

2 回答 2

6

通常,只要您可以剪切-n-粘贴命令并使其工作,但外壳在运行该命令时不起作用,则在某处存在引用问题。与其试图弄清楚它是什么,不如让 shell 评估字符串。换句话说,而不是:

$cmd

您希望 shell 评估 $cmd 就像您直接键入它一样:

eval $cmd
于 2012-09-10T23:03:54.070 回答
1

您在参数周围加上的引号按-classpath字面意思处理,因为它们是 的值的一部分$cmd。它们在$cmd展开后不会被删除,并且结果字符串被解析为命令行。就好像你在命令行输入了一样

$ javac -sourcepath /home/test/src -classpath \"/home/test/jars/Library.jar\" -d /home/test/build /home/test/src/File.java /home/test/src/dir/File2.java
于 2012-09-10T22:22:02.160 回答