zoukankan      html  css  js  c++  java
  • [转载]在C#中使用异步Socket编程实现TCP网络服务的C/S的通讯构架(二)使用方法

    一.TcpSvr的使用方法
    A.测试程序:
    using System;
    using Ibms.Net.TcpCSFramework;
    using System.Collections;
    using System.Net.Sockets;

    namespace Ibms.Test
    {
     /// <summary>
     /// 测试TcpSvr的类
     /// </summary>
     public class TestTcpSvr
     {
      
      public TestTcpSvr()
      {
       
      }

      
      public static  void Main()
      {
       try
       {

        Console.WriteLine("Begin to Test TcpSvr class...");

        TestTcpSvr tts = new TestTcpSvr();

        //TcpSvr svr = new TcpSvr(9050,4);//默认使用Encoding.Default编码方式
        TcpSvr svr = new TcpSvr(9050,4,new Coder(Coder.EncodingMothord.UTF8));

        svr.Resovlver = new DatagramResolver("##");

        //定义服务器的4个事件

        //服务器满
        svr.ServerFull += new NetEvent(tts.ServerFull);

        //新客户端连接
        svr.ClientConn += new NetEvent(tts.ClientConn);

        //客户端关闭
        svr.ClientClose += new NetEvent(tts.ClientClose);

        //接收到数据
        svr.RecvData += new NetEvent(tts.RecvData);
        
        //命令控制循环
        while(true)
        {
         Console.Write(">");

         string cmd=Console.ReadLine();

         //退出测试程序
         if(cmd.ToLower() == "exit")
         {
          break;
         }

         //停止服务器程序
         if(cmd.ToLower() == "stop")
         {
          svr.Stop();
          
          Console.WriteLine("Server is Stop.");

          continue;
         }

         //运行服务器程序
         if(cmd.ToLower() == "start")
         {
          svr.Start();

          Console.WriteLine("Server is listen...{0}",
           svr.ServerSocket.LocalEndPoint.ToString());

          continue;
         }

         //察看服务器在线客户端数目和容量
         if(cmd.ToLower() == "count")
         {
          Console.WriteLine("Current count of Client is {0}/{1}",
           svr.SessionCount,svr.Capacity);
          continue;
         }

         //发送数据到客户端格式:send [Session] [stringData]
         if(cmd.ToLower().IndexOf("send") !=-1)
         {
          cmd = cmd.ToLower();

          string[] para = cmd.Split(' ');

          if(para.Length ==3)
          {
           
           Session client = (Session)svr.SessionTable[ new SessionId( int.Parse
            (para[1]))];

           if(client !=null)
           {
            svr.Send(client, para[2]);
           }
           else
           {
            Console.WriteLine("The Session is Null");
           }
           
          }
          else
          {
           Console.WriteLine("Error Command");
          }

          continue;
         }

         //从服务器上踢掉一个客户端
         if(cmd.ToLower().IndexOf("kick") !=-1)
         {
          cmd = cmd.ToLower();

          string[] para = cmd.Split(' ');
          
          if(para.Length ==2)
          {
           Session client = (Session)svr.SessionTable[ new SessionId( int.Parse
            (para[1]))];

           if(client !=null)
           {
            svr.CloseSession(client);
           }
           else
           {
            Console.WriteLine("The Session is Null");
           }
          }
          else
          {
           Console.WriteLine("Error command");
          }
          
          continue;

         }

         //列出服务器上所有的客户端信息
         if(cmd.ToLower() == "list")
         {
          int i=0;

          foreach( Session Client in svr.SessionTable.Values)
          {
           if(Client !=null)
           {
            i++;
            string info = string.Format("{0} Client:{1} connected server Session:{2}. Socket Handle:{3}",
             i,
             Client.ClientSocket.RemoteEndPoint.ToString(),
             Client.ID,
             Client.ClientSocket.Handle);

            Console.WriteLine( info );
           }
           else
           {
            i++;

            string info = string.Format("{0} null Client", i);
            Console.WriteLine(info);

           }
          }

          continue;
          
         }

         Console.WriteLine("Unkown Command");


        }//end of while

        Console.WriteLine("End service");
       }
       catch(Exception ex)
       {
        Console.WriteLine(ex.ToString());
       }

      }

      void ClientConn(object sender, NetEventArgs e)
      {
       string info = string.Format("A Client:{0} connect server Session:{1}. Socket Handle:{2}",
        e.Client.ClientSocket.RemoteEndPoint.ToString(),
        e.Client.ID,e.Client.ClientSocket.Handle);

       Console.WriteLine( info );

       Console.Write(">");
      }
      
      void ServerFull(object sender, NetEventArgs e)
      {
       string info = string.Format("Server is full.the Client:{0} is refused",
        e.Client.ClientSocket.RemoteEndPoint.ToString());

       //Must do it
       //服务器满了,必须关闭新来的客户端连接
       e.Client.Close();

       Console.WriteLine(info);

       Console.Write(">");

      }

      void ClientClose(object sender, NetEventArgs e)
      {
       string info ;

       if( e.Client.TypeOfExit == Session.ExitType.ExceptionExit)
       {
        info= string.Format("A Client Session:{0} Exception Closed.",
         e.Client.ID);
       }
       else
       {
        info= string.Format("A Client Session:{0} Normal Closed.",
         e.Client.ID);
       }

       Console.WriteLine( info );

       Console.Write(">");
      }

      void RecvData(object sender, NetEventArgs e)
      {
       string info = string.Format("recv data:{0} from:{1}.",e.Client.Datagram, e.Client);

       Console.WriteLine( info );
       TcpSvr svr = (TcpSvr) sender;

       //测试把收到的数据返回给客户端
       svr.Send(e.Client, e.Client.Datagram);

       Console.Write(">");
       
      }

     }
    }

    B.说明:
    使用命令来操作服务器
    exit  退出
    start 开始服务
    kick 关闭客户端
    send 发送数据
    list 列出所有客户端的状态
    count 客户端计数

    先启动服务运行start,等待客户端连接。
    然后可以使用list,count察看当前的连接状况


    每个事件都有相应函数,客户就在事件处理函数中处理自己的业务逻辑
    可以通过继承特化自己的服务器应用,基本的框架不变

    二.TcpCli的使用方法
    A.测试程序:
    using System;
    using Ibms.Net.TcpCSFramework;

    namespace Ibms.Test
    {
     /// <summary>
     /// TestTcpClient 的摘要说明。
     /// </summary>
     public class TestTcpClient
     {
      public TestTcpClient()
      {
       //
       // TODO: 在此处添加构造函数逻辑
       //
      }
      public static void Test()
      {
       Console.WriteLine("Begin to Test TcpCli Class..");

       TestTcpClient test = new TestTcpClient();

       TcpCli cli = new TcpCli( new Coder(Coder.EncodingMothord.UTF8));

       cli.Resovlver = new DatagramResolver("##");

       cli.ReceivedDatagram += new NetEvent(test.RecvData);

       cli.DisConnectedServer += new NetEvent(test.ClientClose);

       cli.ConnectedServer += new NetEvent(test.ClientConn);
       
       try
       {
        //命令控制循环
        while(true)
        {
         Console.Write(">");

         string cmd=Console.ReadLine();

         if(cmd.ToLower() == "exit")
         {
          break;
         }

         if(cmd.ToLower() == "close")
         {
          cli.Close();
          

          continue;
         }

         if(cmd.ToLower().IndexOf("conn")!=-1)
         {
          cmd = cmd.ToLower();

          string[] para = cmd.Split(' ');

          if(para.Length ==3)
          {
          
           cli.Connect(para[1],int.Parse(para[2]));
          }
          else
          {
           Console.WriteLine("Error Command");
          }

          continue;
         }

         if(cmd.ToLower().IndexOf("send") !=-1)
         {
         
          
          cmd = cmd.ToLower();

          string[] para = cmd.Split(' ');

          if(para.Length ==2)
          {
          
           cli.Send(para[1]);

          
          }
          else
          {
           Console.WriteLine("Error Command");
          }

          continue;
         }

        
         Console.WriteLine("Unkown Command");


        }//end of while

        Console.WriteLine("End service");
       }
       catch(Exception ex)
       {
        Console.WriteLine(ex.ToString());
       }


      }

      void ClientConn(object sender, NetEventArgs e)
      {
       string info = string.Format("A Client:{0} connect server :{1}",e.Client,
        e.Client.ClientSocket.RemoteEndPoint.ToString());

       Console.WriteLine( info );

       Console.Write(">");
      }
      
      void ClientClose(object sender, NetEventArgs e)
      {
       string info ;

       if( e.Client.TypeOfExit == Session.ExitType.ExceptionExit)
       {
        info= string.Format("A Client Session:{0} Exception Closed.",
         e.Client.ID);
       }
       else
       {
        info= string.Format("A Client Session:{0} Normal Closed.",
         e.Client.ID);
       }

       Console.WriteLine( info );

       Console.Write(">");
      }

      void RecvData(object sender, NetEventArgs e)
      {
       string info = string.Format("recv data:{0} from:{1}.",e.Client.Datagram, e.Client);

       Console.WriteLine( info );
       
       Console.Write(">");
       
      }
     }
    }

    B.说明:
    先建立连接,Conn 192.9.207.214 9050
    然后可以Send 数据
    最后关闭连接Close

    三.编码器
    如果你要加密你的报文,需要一个你自己的Coder
    从Coder类继承一个如MyCoder类,然后重载编码和解码函数。
    使用方法:

    TcpCli cli = new TcpCli( new MyCoder());

    就可以在客户端使用该编码器了。
    四.报文解析器
    与编码器同样的实现方法。

  • 相关阅读:
    flex居中
    flex
    js将接口返回的数据序列化
    用javascript替换URL中的参数值
    object遍历删除空值
    node代理服务器
    随机生成id
    正则之特殊字符
    H5项目常见问题及注意事项
    node编译C++,比如安装node-gyp失败的问题
  • 原文地址:https://www.cnblogs.com/fx2008/p/2269997.html
Copyright © 2011-2022 走看看