我正在创建一个函数(下面),您可以使用该函数提供参数,目录。我测试$argv
是否是具有-d
选项的目录,但似乎不起作用,即使没有提供参数,它也总是返回true。我还尝试test -n $argv -a -d $argv
来测试$argv
是空的,但是会返回test: Missing argument at index 1
错误。我该如何测试函数是否提供了任何参数?为什么test -d $argv
不起作用,根据我的理解,当没有提供参数时它应该是假的,因为空字符串不是目录。
function fcd
if test -d $argv
open $argv
else
open $PWD
end
end
感谢您的帮助。
答案 0 :(得分:27)
count
是执行此操作的正确方法。对于检查是否存在任何参数的常见情况,您可以使用其退出状态:
function fcd
if count $argv > /dev/null
open $argv
else
open $PWD
end
end
要回答第二个问题,test -d $argv
如果$argv
为空则返回true,因为POSIX要求在test
传递一个参数时,它必须“如果$ 1则返回true(0)不为null;否则,退出false“。因此,当$ argv为空时,test -d $argv
表示test -d
必须退出true,因为-d
不为空!哎呀!
编辑添加了缺失的end
,感谢Ismail注意到
答案 1 :(得分:19)
至少在鱼2.1+中,您可以命名您的参数,然后允许更多的语义代码:
function fcd --argument-names 'filename'
if test -n "$filename"
open $filename
else
open $PWD
end
end
答案 2 :(得分:5)
$argv
是列表,因此如果该列表中有元素,您需要查看第一个元素:
if begin; test (count $argv) -gt 0; and test -d $argv[1]; end
open $argv[1]
else
open $PWD
end
答案 3 :(得分:4)
可能与此无关,但我想为此问题添加另一个视角。
我希望通过渔民小组开发的库,在更广泛的范围内拓展测试shell代码的范围。
使用mock,您可以检查是否安全地调用open命令而没有副作用。
示例:
function fcd
if count $argv > /dev/null
open $argv
else
open $PWD
end
end
mock open 0 "echo \$args"
fcd "cool" # echoes cool
mock open 0 "echo \$args"
fcd # echoes $PWD
是一个最近的库,但它可以帮助测试可能有危险的东西,例如rm
mock rm 0 "echo nothing would happen on \$args"
rm "some file" # simply echoes the message with a list of the files that would been affected
我希望它能提供更多开箱即用的观点
P.S。:对于明目张胆的宣传感到抱歉,但我认为这是一个很酷的想法,很好被shell脚本编写者采用,测试和增加shell脚本的可持续性是疯了。 :P
编辑:我最近发现了一个关于我发布的样本的错误。请不要使用rm *,因为星号不被视为参数,而是fish shell将星号扩展为找到的文件列表,命令只会模拟第一次调用,这意味着模拟会忽略第一个文件,但是所有后续文件都会被删除所以请在尝试使用示例时使用单个文件而不是通配符。答案 4 :(得分:1)
if not set -q argv[1]
echo 'none'
else
echo 'yes'
end
在man set
页上:
set ( -q | --query ) [SCOPE_OPTIONS] VARIABLE_NAMES...
o -q或--query测试是否定义了指定的变量名。不输出任何内容,但是内建退出状态是指定的变量数 没有定义。