Using OTP

Michael McDaniel erlang@REDACTED
Sat Jan 14 18:41:24 CET 2006


I found a nice example by Lennart Ohman which helped me.
Well, I first read OTP Design Principles over and over (and other
documents), and worked with "plain Erlang" for many smaller
programs (using bits and pieces of OTP but not the powerful
supervisor).  Then my mind was ready to understand, I think, and
Lennart Ohman's example was very useful to me.

Here is link to thread with example:

http://www.erlang.org/ml-archive/erlang-questions/200510/msg00137.html

google is your friend.


~Michael
P.S. Many other examples and documentations helped me to understand;
it is that my mind was (finally) ready to accept when I found the
above example that gave me the final push into OTP principles.


On Sat, Jan 14, 2006 at 01:44:09PM -0300, Pupeno wrote:
> Hello,
> I've been trying for days to start working in a project of mine in Erlang not 
> being able to see how it should be coded according to OTP.
> I've read the OTP Designs and principles, but that didn't really told me all I 
> needed.
> What I am doing is a library to make servers[1], it is supposed to make 
> abstractions over protocols like DNS, SMTP, POP3, etc leaving you only to 
> worry about data handling.
> I'll show you what I want with a trivial example: the echo protocol[2].
> Someone wants to write a echo server, so it would write this:
> 
> -module(echo).
> -export([start/0, init/1, echo/1]).
> -behaviour(gen_echo).
> 
> start() ->
>     gen_echo:start(?MODULE, [], []).
> 
> init(_Args) ->
>     {10007, 10007}.
> 
> echo(Data) ->
>     string:concat("You said: ", Data).
> 
> where start/0 would start the server, init/1 replies with the TCP and UDP 
> ports to use (false or something like that in any of them would mean "don't 
> use that transport, tcp or udp").
> The function echo/1 is the real worker here. In the DNS example (one in which 
> I worked on HaServers[1]), it would be query/1 and it would get a big record 
> containing the data sent by the client. echo/1 replies another string which 
> will be sent to the ip client (either by tcp, or udp, the good thing is that 
> echo/1 doesn't worry about that). As you can see, this is a non-compliant 
> echo server where the smart developer is doing some experimentation. In the 
> DNS example, query/1 would return a record containing the a packet to be sent 
> back.
> Another callback function possible for DNS would be transfer/N, which is 
> triggered for transferring actions. Other protocols (smtp, pop3, imap4, which 
> are my priorities after dns, in that order) would have other set of 
> callbacks.
> 
> Now, my gen_echo.erl looks like this:
> 
> -module(gen_echo).
> -export([behaviour_info/1]).
> -export([start/3]).
> -export([tcpLoop/2, tcpHandler/1]).
> 
> behaviour_info(callbacks) ->
>     [{echo, 1}];
> behaviour_info(_Args) ->
>     undefined.
> 
> start(Mod, Args, Options) ->
>     {TCPPort, _UDPPort} = Mod:init(Args),
>     {_, TCPLSocket} = gen_tcp:listen(TCPPort, [{active, once}, {packet, 0}]),
>     spawn(?MODULE, tcpLoop, [Mod, TCPLSocket]).
> 
> tcpLoop(Mod, TCPLSocket) ->
>     {_, Socket} = gen_tcp:accept(TCPLSocket),
>     TcpHandler = spawn(?MODULE, tcpHandler, [Mod]),
>     gen_tcp:controlling_process(Socket, TcpHandler),
>     tcpLoop(Mod, TCPLSocket).
> 
> tcpHandler(Mod) ->
>     receive
> 	{tcp, Socket, Data} ->
> 	    gen_tcp:send(Socket, Mod:echo(Data)),
> 	    inet:setopts(Socket, [{active, once}]),
> 	    tcpHandler(Mod);
> 	{tcp_closed, Socket} ->
> 	    io:format("~w closed.~n", [Socket]);
> 	Unknown ->
> 	    io:format("Received unknow message ~w.~n", [Unknown])
>     end.
> 
> I want to rewrite this as Erlangish and OTPish as possible, what do you 
> recommend ? what should I do ? Some questions I have are:
> - Should gen_echo, gen_PROTOCOL, be a gen_server ? or another gen_X ?
> - Should gen_echo, gen_PROTOCOL, use gen (gen:start, etc, I see that 
> gen_server uses it) ?
> - Should I write supervisors ?
> - Should all this be an application (ErServers, the temporary name for this 
> will only be a library, it shouldn't provide any runable program except a 
> couple of examples, any developed server should be packaged and developed 
> separately) ?
> Any other tips and hints are welcome, I feel very lost here.
> -- 
> Pupeno <pupeno@REDACTED> (http://pupeno.com)
> Vendemos: Kit del guitarrista: http://pupeno.com/vendo/#kit
> 
> [1] For those of you that understand Haskell, I started working on Haskell and 
> the result was HaServers http://software.pupeno.com/HaServers/
> 
> [2] RFC862.
> 
> PS: All this will be free software.



More information about the erlang-questions mailing list