问题
Normally in Erlang programmers use !
symbol to send message to receive in concurrent programming but how do we do it in yaws? Say I am trying to do this>
<erl>
out(Arg) -> loop("bad").
loop(X)->
receive
good -> {html, "Good"};
bad -> {html, "bad"}
end.
</erl>
This program keeps waiting for a message, How do I send message to it?
回答1:
If you want to have one process send a message to another, it's clear you need two processes. When Yaws receives a HTTP request, by default it dispatches the request into one of its processes in its Erlang process pool. When you're using a .yaws
file as in your example, that process invokes your out/1
function. But that's just one process, so you need another.
There are numerous ways to start a second process. One simple way is to spawn_link
a process to run whatever logic will send the message to loop/1
:
<erl>
out(_Arg) ->
process_flag(trap_exit, true),
Self = self(),
Pid = spawn_link(fun() -> my_business_logic(Self) end),
loop(Pid).
loop(Pid) ->
receive
{Pid, good} -> {html, "Good"};
{Pid, bad} -> {html, "Bad"};
{'EXIT', Pid, Reason} ->
[{status, 500},
{html, "internal server error"}]
end.
my_business_logic(Parent) ->
%% run your logic here, then send a message
Parent ! {self(), good}.
</erl>
Note that we put the child process Pid
in the message to identify that it's originating from the expected process. Note also that we link to the child process and trap exits so that if the child dies unexpectedly, we can catch the EXIT
and report the error properly.
But this might not be a good approach. If the logic process should run independently of any HTTP request, you could start a pool of them when your Erlang system starts, and have the out/1
function send one a message to ask it to carry out a request on its behalf. It all depends on what those processes are doing, how they relate to incoming requests, and whether having a pool of them is adequate for the request load you're expecting.
Using a .yaws
file is handy for some applications but they can be limiting. An alternative is to build an Erlang system containing Yaws and your own application, and use the Yaws appmod feature to have Yaws dispatch requests into your own processes running your own Erlang modules. Explaining all that here isn't practical, so please consult the Yaws documentation or the Yaws book, or ask for help from the Yaws mailing list.
来源:https://stackoverflow.com/questions/37635491/how-to-send-message-to-receive-in-yaws-erlang