Chinaunix首页 | 论坛 | 博客
  • 博客访问: 5119680
  • 博文数量: 921
  • 博客积分: 16037
  • 博客等级: 上将
  • 技术积分: 8469
  • 用 户 组: 普通用户
  • 注册时间: 2006-04-05 02:08
文章分类

全部博文(921)

文章存档

2020年(1)

2019年(3)

2018年(3)

2017年(6)

2016年(47)

2015年(72)

2014年(25)

2013年(72)

2012年(125)

2011年(182)

2010年(42)

2009年(14)

2008年(85)

2007年(89)

2006年(155)

分类:

2012-09-27 10:52:57

1,chat_server.erl

  1. -module(chat_server).
  2. -export([start/1]).

  3. -define(TCP_OPTIONS, [list, {packet, 0}, {active, false}, {reuseaddr, true}]).

  4. start(Port) ->
  5.   Pid = spawn(fun() -> manage_clients([]) end),
  6.   register(client_manager, Pid),
  7.   {ok, LSocket} = gen_tcp:listen(Port, ?TCP_OPTIONS),
  8.   do_accept(LSocket).

  9. do_accept(LSocket) ->
  10.   {ok, Socket} = gen_tcp:accept(LSocket),
  11.   spawn(fun() -> handle_client(Socket) end),
  12.   client_manager ! {connect, Socket},
  13.   do_accept(LSocket).

  14. handle_client(Socket) ->
  15.   case gen_tcp:recv(Socket, 0) of
  16.     {ok, Data} ->
  17.       client_manager ! {data, Data},
  18.       handle_client(Socket);
  19.     {error, closed} ->
  20.       client_manager ! {disconnect, Socket}
  21.   end.

  22. manage_clients(Sockets) ->
  23.   receive
  24.     {connect, Socket} ->
  25.       io:fwrite("Socket connected: ~w~n", [Socket]),
  26.       NewSockets = [Socket | Sockets];
  27.     {disconnect, Socket} ->
  28.       io:fwrite("Socket disconnected: ~w~n", [Socket]),
  29.       NewSockets = lists:delete(Socket, Sockets);
  30.     {data, Data} ->
  31.       send_data(Sockets, Data),
  32.       NewSockets = Sockets
  33.   end,
  34.   manage_clients(NewSockets).

  35. send_data(Sockets, Data) ->
  36.   SendData = fun(Socket) ->
  37.     gen_tcp:send(Socket, Data)
  38.   end,
  39.   lists:foreach(SendData, Sockets).

server监听Socket连接,并群发消息到所有的client

2,chat_send_client.erl

  1. -module(chat_send_client).
  2. -export([start/2]).

  3. start(IP, Port) ->
  4.   {ok, Socket} = gen_tcp:connect(IP, Port, [binary, {packet, 4}]),
  5.   talk(Socket).

  6. talk(Socket) ->
  7.   Msg = io:get_line('Input you msg:'),
  8.   ok = gen_tcp:send(Socket, term_to_binary(Msg)),
  9.   talk(Socket).

send_client用来启动一个client发消息的进程

3,chat_recv_client.erl

  1. -module(chat_recv_client).
  2. -export([start/2]).

  3. start(IP, Port) ->
  4.   {ok, Socket} = gen_tcp:connect(IP, Port, [binary, {packet, 4}]),
  5.   recv_msg(Socket).

  6. recv_msg(Socket) ->
  7.   receive
  8.     {tcp, Socket, Bin} ->
  9.       Msg = binary_to_term(Bin),
  10.       io:format("Received msg: ~p~n", [Msg]),
  11.       recv_msg(Socket)
  12.   end.


recv_client用来在client端实时显示所有登录聊天室的client发送的消息

4,启动server

  1. Eshell> chat_server:start(9999).


5,启动send和recv两个client进程

  1. $$ client1
  2. Eshell> chat_send_client:start("localhost", 9999).
  3. Eshell> chat_recv_client:start("localhost", 9999).
  4. $$ client2
  5. Eshell> chat_send_client:start("localhost", 9999).
  6. Eshell> chat_recv_client:start("localhost", 9999).

6,交互过程

  1. %% client1/send
  2. Input you msg:我囧
  3. %% client2/send
  4. Input you msg:你囧啥?
  5. %% client1、2/recv
  6. Received msg: "我囧\n"
  7. Received msg: "你囧啥?\n"

原文链接:



阅读(1773) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~