是否有一个Erlang操作系统:cmd等效,它采用字符串列表而不是单个命令?

时间:2010-02-09 17:29:53

标签: erlang

我可以在Retval = subprocess:call(["cmd", "arg1", "arg2", "arg3"])处找到Erlang电话吗?

如果我正在构建一个复杂的命令来执行,使用os:cmd / 1可以很容易地逃避错误。与Python的subprocess.call()方法相比,我传入一个字符串列表并知道它是逐字传递给子进程的,没有任何损坏。

感谢。

3 个答案:

答案 0 :(得分:7)

现在你可以做open_port({spawn_executable, Command}, [{args, [A1, ..., An]}]),但是在os模块中还没有方便的包装器。您可以使用os:cmd/1的代码并将其调整为使用spawn_executable。有关详细信息,请查看erlang:open_port/2的文档。

答案 1 :(得分:7)

这就是我的想法。

-module(mycmd).
-export([cmd/2]).

cmd(Cmd, Args) ->
    Tag = make_ref(), 
    {Pid, Ref} = erlang:spawn_monitor(fun() ->
            Rv = cmd_sync(Cmd, Args),
            exit({Tag, Rv})
        end),
    receive
        {'DOWN', Ref, process, Pid, {Tag, Data}} -> Data;
        {'DOWN', Ref, process, Pid, Reason} -> exit(Reason)
    end.

cmd_sync(Cmd, Args) ->
    P = open_port({spawn_executable, os:find_executable(Cmd)}, [
            binary, use_stdio, stream, eof, {args, Args}]),
    cmd_receive(P, []).

cmd_receive(Port, Acc) ->
    receive
        {Port, {data, Data}} -> cmd_receive(Port, [Data|Acc]);
        {Port, eof}          -> {ok, lists:reverse(Acc)}
    end.

答案 2 :(得分:0)

你不能只做os:cmd(string:join(["cmd", "arg1", "arg2"], " "))吗?