我有这个模块用于检查数字的奇偶校验:
defmodule Parity do
def start() do
continue()
end
defp continue() do
get_number()
|> parse()
|> even?()
|> print_output()
continue()
end
defp get_number() do
IO.gets("Type a number: ")
end
defp parse(input) do
String.trim(input)
|> Integer.parse
end
defp even?({ number, _ }) do
Integer.mod(number, 2) == 0
end
defp print_output(_is_even = true) do
IO.puts("This number is even!")
end
defp print_output(_is_odd) do
IO.puts("This number is odd!")
end
end
它的工作原理如下:
$ mix run -e Parity.start
Type a number: 4
This number is even!
Type a number: 3
This number is odd!
Type a number: 68
This number is even!
Type a number: 1
This number is odd!
Type a number: ...
现在我想要另一个模块,它可以为Parity
模块的标准输入写入数字。所以我需要有一些东西来执行Parity.start()
,然后为IO.gets()
函数提供数字。
我试过这样的事情:
defmodule Bot do
def start() do
Parity.start()
provide_number()
end
defp provide_number() do
random_number()
|> IO.puts
provide_number()
end
defp random_number() do
Enum.random(0..100)
end
end
它不起作用。
它只启动Parity
模块,但provide_number()
函数没有输入。
答案 0 :(得分:2)
如果你想写入stdin (比如伪造一个CLI输入),你几乎需要一种在不同系统进程之间交换信息的方法。 Porcelain做得非常好:
defmodule OtherModule do
alias Porcelain.Process, as: Proc
alias Porcelain.Result
proc = %Proc{pid: pid} =
Porcelain.spawn_shell("mix run -e Parity.start", in: :receive, out: {:send, self()})
Proc.send_input(proc, "1")
receive do
{^pid, :data, :out, data} -> IO.inspect data #=> "This number is odd!"
end
end
未经测试编写,但这应该给你一个粗略的想法。瓷器比System.cmd/3
具有更多更好的处理能力。或者,如果您不需要 stdin ,则应在own Elixir node上运行每个模块:
iex --sname parity -S mix
然后在你的OtherModule
中你可以写出类似的内容:
pid = Node.spawn_link :"parity@computer-name", fn -> ... end