2016-04-17 7 views
0

クライアント側からいくつかの情報を受け取るためにソケットプログラミングを使用しようとしています(ディスク使用量など)。サーバーにデータを送信し、ソケットを使用してSQL Serverに格納します。

複数のクライアントに非同期メソッドを使用してSQL Serverに書き込もうとしましたが、SQL Serverにすべての情報を格納しませんでした。クライアントとサーバー間のバイト配列による通信ストリームですが、通信中にこのバイト配列をSQL Serverに格納するにはどうすればよいですか?

+0

TCPソケットの最大データグラムサイズは約1500バイトです。より大きいメッセージは、複数のデータグラムに分割されます。したがって、データをデータベースに格納するには、クライアントからのバイト配列にブロックが含まれている必要があります。そのため、データをより小さな部分に分割できます。たとえば、クライアント100の銀行口座から受け取った場合、各銀行口座の末尾に改行文字が表示されます。その後、サーバーは各銀行口座を一度に1つずつSQL Serverに格納できます。または、一度に1つの銀行口座を送るだけで、100の銀行口座を個々の口座に分割する必要がなくなりました。 – jdweng

+0

オカン、コード例を追加してください。あなたがこれをやっていること、そして実際にあなたが望むことは、今は明らかではありません。 – cassandrad

答えて

0

遅い応答の人に申し訳ありません。

ここにコードがあります。 2つのプロジェクトがあります。そのうちの1つはサーバーで、もう1つはクライアントです。サーバープロジェクトには2つのクラスがあります。

クラス;

class Listener 
{ 
    private Socket _socket; 

    public bool Listening { get; private set; } 
    public int Port { get; private set; } 

    public Listener(int port) 
    { 
     Port = port; 
     _socket=new Socket(AddressFamily.InterNetwork,SocketType.Stream, ProtocolType.Tcp); 
    } 

    public void Start() 
    { 
     if (Listening) 
     { 
      return; 
     } 

     _socket.Bind(new IPEndPoint(0,Port)); 
     _socket.Listen(0); 
     _socket.BeginAccept(callback, null); 
     Listening = true; 
    } 

    public void Stop() 
    { 
     if (!Listening) 
     { 
      return; 
     } 

     _socket.Close(); 
     _socket.Dispose(); 
     _socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); 
    } 

    void callback(IAsyncResult ar) 
    { 
     try 
     { 
      Socket socket = this._socket.EndAccept(ar); 

      if (SocketAccepted!=null) 
      { 
       SocketAccepted(socket); 
      } 
      this._socket.BeginAccept(callback, null); 
     } 
     catch (Exception ex) 
     { 
      MessageBox.Show(ex.Message); 
     } 
    } 

    public delegate void SocketAcceptedHandler(Socket e); 

    public event SocketAcceptedHandler SocketAccepted; 
} 


class Client 
{ 
    public string ID { get; private set; } 
    public IPEndPoint EndPoint { get; private set; } 

    private Socket sck; 

    public Client(Socket accepted) 
    { 
     sck = accepted; 
     ID = Guid.NewGuid().ToString(); 
     EndPoint = (IPEndPoint)sck.RemoteEndPoint; 
     sck.BeginReceive(new byte[] {0}, 0, 0, 0, callback, null); 
    } 

    void callback(IAsyncResult ar) 
    { 
     try 
     { 
      sck.EndReceive(ar); 

      byte[] buf=new byte[8192]; 
      int rec = sck.Receive(buf, buf.Length, 0); 

      if (rec<buf.Length) 
      { 
       Array.Resize<byte>(ref buf, rec); 
      } 
      if (Received!=null) 
      { 
       Received(this, buf); 
      } 

      sck.BeginReceive(new byte[] { 0 }, 0, 0, 0, callback, null); 

     } 
     catch (Exception ex) 
     { 
      //MessageBox.Show(ex.Message); 
      sck.Close(); 

      if (Disconnected!=null) 
      { 
       Disconnected(this); 
      } 
     } 

    } 

    public void Close() 
    { 
     sck.Close(); 
     sck.Dispose(); 
    } 
    public delegate void ClientReceivedHandler(Client sender, byte[] data); 
    public delegate void ClientDiscconnectedHandler(Client sender); 

    public event ClientReceivedHandler Received; 
    public event ClientDiscconnectedHandler Disconnected; 
} 

Serverプロジェクトメインフォーム:

Server Application

public partial class Main : Form 
{ 
    private static Listener _listener; 

    public Main() 
    { 
     InitializeComponent(); 
     _listener = new Listener(8); 
     _listener.SocketAccepted += new Listener.SocketAcceptedHandler(_listenerSocketAccepted); 
     _listener.Start(); 

    } 

    private void _listenerSocketAccepted(Socket e) 
    { 
     Client client = new Client(e); 
     client.Received += new Client.ClientReceivedHandler(client_Received); 
     client.Disconnected += new Client.ClientDiscconnectedHandler(client_Disconnected); 


     Invoke((MethodInvoker)delegate 
     { 
      ListViewItem i=new ListViewItem(); 
      i.Text = client.EndPoint.ToString(); 
      i.SubItems.Add(client.ID); 
      i.SubItems.Add("XXX"); 
      i.SubItems.Add("XXX"); 
      i.Tag = client; 
      listViewClients.Items.Add(i); 

      //textBox1.Text = "New Connection : " + e.RemoteEndPoint + " Time : " + DateTime.Now; 
     }); 
    } 

    private void client_Disconnected(Client sender) 
    { 
     Invoke((MethodInvoker)delegate 
     { 
      for (int i = 0; i < listViewClients.Items.Count; i++) 
      { 
       Client client=listViewClients.Items[i].Tag as Client; 

       if (client.ID==sender.ID) 
       { 
        listViewClients.Items.RemoveAt(i); 
        break; 
       } 
      } 
     }); 
    } 

    private void client_Received(Client sender, byte[] data) 
    { 
     Invoke((MethodInvoker)delegate 
     { 
      for (int i = 0; i < listViewClients.Items.Count; i++) 
      { 
       Client client = listViewClients.Items[i].Tag as Client; 

       if (client.ID == sender.ID) 
       { 
        listViewClients.Items[i].SubItems[2].Text = Encoding.Default.GetString(data); 
        listViewClients.Items[i].SubItems[3].Text = DateTime.Now.ToString(); 
        break; 
       } 
      } 
     }); 
    } 

    private void Main_Load(object sender, EventArgs e) 
    { 

    } 
} 

クライアント側メインフォーム:

Client Application

public partial class Main : Form 
{ 
    Socket sck = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); 
    public Main() 
    { 
     InitializeComponent(); 
    } 

    private void btnConnect_Click(object sender, EventArgs e) 
    { 
     sck.Connect("127.0.0.1", 8); 
     MessageBox.Show("Connected"); 
    } 

    private void btnSend_Click(object sender, EventArgs e) 
    { 
     int s = sck.Send(Encoding.Default.GetBytes(txtMsg.Text)); 

     if (s>0) 
     { 
      MessageBox.Show("Message Sent.."); 
     } 
    } 

    private void btnClose_Click(object sender, EventArgs e) 
    { 
     sck.Close(); 
     sck.Dispose(); 
     Close(); 
    } 

    private void Main_Load(object sender, EventArgs e) 
    { 
     //lis 
    } 
} 

私は2つの質問があります。

1-どのようにクライアントから来たsqlにデータを挿入できますか?

2リストビューの項目がちらつき、btnCloseでクライアントアプリケーションを閉じるときに消えません。

+0

通常、データベースへの接続プールを開きます。メッセージが入ったら、バイトストリームを個々のデータフィールドに変換してパラメータをSQLに渡すか、そこからオブジェクトを作成することができます。 C#では、オブジェクトを使用するエンティティフレームワークを使用するか、ADO.NETを使用してparamsをSQLに渡すことができます。 ADO.NETの場合、同時リクエスト用の接続プールを作成できます。エンティティ・フレームワークにはプーリングが組み込まれています。 – Mike

関連する問題