NewLife.Net——開始網絡編程

網絡編程的重要性就不說了,先上源碼:https://github.com/nnhy/NewLife.Net.Tests

一個服務端,就是監聽一些端口,接收客戶端連接和數據,進行處理,然後響應。

/// <summary>定義服務端,用於管理所有網絡會話</summary>
class MyNetServer : NetServer<MyNetSession>
{
}

/// <summary>定義會話。每一個遠程連接唯一對應一個網絡會話,再次重複收發信息</summary>
class MyNetSession : NetSession<MyNetServer>
{
    /// <summary>客戶端連接</summary>
    public override void Start()
    {
        base.Start();

        // 歡迎語
        var str = String.Format("Welcome to visit {1}!  [{0}]\r\n", Remote, Environment.MachineName);
        Send(str);
    }

    /// <summary>收到客戶端數據</summary>
    /// <param name="e"></param>
    protected override void OnReceive(ReceivedEventArgs e)
    {
        WriteLog("收到:{0}", e.Packet.ToStr());

        // 把收到的數據發回去
        Send(e.Packet);
    }
}

服務端核心類是NetServer,一般來說,每個網絡服務端都會寫一個自己的類來繼承NetServer,以方便編寫自己的NetSession會話邏輯。

實在簡單的應用,也可以直接實例化NetServer,然後通過事件來處理收到的連接和數據。

這裏我們寫了個MyNetServer,沒有任何代碼,僅僅是爲了指定使用哪個網絡會話類。

網絡會話NetSession非常重要,每一個Tcp連接就對應一個會話,對Udp來說同一個遠端套接字(IP+端口)就是一個會話。

網絡會話最重要的有幾塊:

  1. Start會話開始,Tcp三次握手之後,雙方還沒有發送數據包之前,此時可以做一些準備工作,或者向客戶端發送歡迎語。Udp會話開始在第一個數據包達到時。
  2. OnReceive接收,每次收到數據包以後,都會觸發該方法,數據包位於e.Packet。Tcp默認同步處理,未完成當前數據包處理之前,不會接收本連接的下一個數據包。
  3. Send發送。發送Packet數據包給本會話連接的客戶端,擴展方法支持發送字符串或數據流。

!!!注意:粘包問題在OnReceive之前處理,下回有專門文章分析,接收數據的ReceivedEventArgs裏面還有個Message,支持編碼器對數據包進行解碼成爲消息。

 

本例程是Echo回聲程序,因此OnReceive把收到的數據包原樣發回去。

服務端用法很簡單

static NetServer _server;
static void TestServer()
{
    // 實例化服務端,指定端口,同時在Tcp/Udp/IPv4/IPv6上監聽
    var svr = new MyNetServer
    {
        Port = 1234,
        Log = XTrace.Log
    };
    svr.Start();

    _server = svr;
}

指定端口和日誌,然後就可以開始服務了。

默認在Tcp/Udp/IPv4/IPv6上監聽,客戶端愛用哪個協議來連接都行。

當然,NetServer還可以支持多個端口同時監聽,共用數據處理代碼。

 

客戶端用法更簡單

var uri = new NetUri("tcp://127.0.0.1:1234");
var client = uri.CreateRemote();
client.Log = XTrace.Log;
client.Received += (s, e) =>
{
    XTrace.WriteLine("收到:{0}", e.Packet.ToStr());
};
client.Open();

for (var i = 0; i < 5; i++)
{
    Thread.Sleep(1000);

    var str = "你好" + (i + 1);
    client.Send(str);
}

client.Dispose();

這裏的NetUri直接從字符串裏面解析協議、地址、端口,然後CreateRemote建立客戶端。這裏會自動識別Tcp/Udp。

也是指定日誌,方便我們查看工作過程。還有兩個開關 LogSend/LogReceive能輸出更詳細的數據包日誌。

Received事件裏面處理收到的數據包。

Open開始連接服務端,如果網絡不同,這裏會拋出異常。Tcp客戶端有斷線重連機制。

發送數據包也很簡單,直接Send就好,高級應用需要在發送後等待響應數據,可以用 await SendAsync。

 

因爲程序很簡單,也可以用telnet命令來測試該服務端。

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章