客户端/服务器程序通信问题。 [英] Client / Server program communication issue.
问题描述
所以我被困了。
目前,以下内容只会从服务器向客户端发送消息。我无法弄清楚如何从客户端向服务器发送消息。
这需要双向沟通而不是单向沟通。
我知道它有事情要做使用Listener / Client TCP。
目前代码有点混乱。
有人可以指引我正确的方式或告诉我我做错了吗?
客户
-------------------------------------- -------------------------------------------- <无线电通信/>
So i'm Stuck.
At the moment the following will only send messages from the Server to the client. I can't figure out how to send a message from the client to the server also.
This needs to be 2 way communication not 1 way.
I know it has something to do with the Listener / Client TCP.
The code is a little messy at the moment.
Could someone please steer me the right way or show me what i'm doing wrong?
CLIENT
----------------------------------------------------------------------------------
Imports System.Threading
Imports System.IO
Imports System.Net
Imports System.Drawing.Color
Imports System.Net.Sockets
Public Class Client
Dim SvrPort As String = "12345"
Dim Listener As New TcpListener(12345)
Dim Client As New TcpClient
Dim Message As String = ""
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
SvrStatusLst.Items.Add("Server Running...")
SvrPortTxt.Text = SvrPort
'GetIPAddress()
Listener.Start()
Listenertimer.Start()
End Sub
Private Sub GetIPAddress()
Dim strHostName As String
Dim strIPAddress As String
strHostName = System.Net.Dns.GetHostName()
strIPAddress = System.Net.Dns.GetHostByName(strHostName).AddressList(0).ToString()
SvrIpTxt.Text = strIPAddress
End Sub
'Start Server stuff
'------------------------------------------------------------------------------------------------------
Private Sub Listening()
Listener.Start()
End Sub
Private Sub Clear_Status_List(sender As Object, e As EventArgs) Handles ClearStatusLst.Click
SvrStatusLst.Items.Clear()
End Sub
Private Sub Listener_Timer_Tick(sender As Object, e As EventArgs) Handles Listenertimer.Tick
If Listener.Pending = True Then
Message = ""
Client = Listener.AcceptTcpClient()
Dim Reader As New StreamReader(Client.GetStream())
While Reader.Peek > -1
Message = Message + Convert.ToChar(Reader.Read()).ToString
End While
SvrStatusLst.Items.Add(Message)
End If
End Sub
'------------------------------------------------------------------------------------------------------
'End Server stuff
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles SvrSendToClientBtn.Click
If txtName.Text = "" Or SvrToClientTxt.Text = "" Then
'Check to make sure that the user has entered
'a display name, and a client IP Address
'If Not, Show a Message Box
MessageBox.Show("All Fields must be Filled", _
"Error Sending Message", _
MessageBoxButtons.OK, MessageBoxIcon.Error)
Else
Try
Client = New TcpClient(SvrIpTxt.Text, SvrPort)
'Declare the Client as an IP Address.
'Must be in the Correct form. eg. 000.0.0.0
Dim Writer As New StreamWriter(Client.GetStream())
Writer.Write(txtName.Text & ": " & SvrToClientTxt.Text)
Writer.Flush()
'Write the Message in the stream
SvrStatusLst.Text += (txtName.Text & ": " & SvrToClientTxt.Text) + vbCrLf
SvrToClientTxt.Text = ""
Catch ex As Exception
Console.WriteLine(ex)
Dim Errorresult As String = ex.Message
MessageBox.Show(Errorresult & vbCrLf & vbCrLf & _
"Please Review Client Address", _
"Error Sending Message", _
MessageBoxButtons.OK, MessageBoxIcon.Error)
End Try
End If
End Sub
Private Sub Button1_Click_1(sender As Object, e As EventArgs) Handles Button1.Click
Listenertimer.Start()
End Sub
End Class
< br $>
服务器
------------------------------------------------- --------------------------
SERVER
---------------------------------------------------------------------------
Imports System.Threading
Imports System.IO
Imports System.Net
Imports System.Drawing.Color
Imports System.Net.Sockets
Public Class Server
Dim SvrPort As String = "12345"
Dim Listener As New TcpListener(12345)
Dim Client As New TcpClient
Dim Message As String = ""
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
SvrStatusLst.Items.Add("Server Running...")
SvrPortTxt.Text = SvrPort
'GetIPAddress()
'Listener.Start()
'ListenerTimer.Start()
End Sub
Private Sub GetIPAddress()
Dim strHostName As String
Dim strIPAddress As String
strHostName = System.Net.Dns.GetHostName()
strIPAddress = System.Net.Dns.GetHostByName(strHostName).AddressList(0).ToString()
SvrIpTxt.Text = strIPAddress
End Sub
'Start Server stuff
'------------------------------------------------------------------------------------------------------
Private Sub Listening()
Listener.Start()
End Sub
Private Sub Clear_Status_List(sender As Object, e As EventArgs) Handles ClearStatusLst.Click
SvrStatusLst.Items.Clear()
End Sub
Private Sub Listener_Timer_Tick(sender As Object, e As EventArgs) Handles ListenerTimer.Tick
If Listener.Pending = True Then
Message = ""
Client = Listener.AcceptTcpClient()
Dim Reader As New StreamReader(Client.GetStream())
While Reader.Peek > -1
Message = Message + Convert.ToChar(Reader.Read()).ToString
End While
SvrStatusLst.Items.Add(Message)
End If
End Sub
'------------------------------------------------------------------------------------------------------
'End Server stuff
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles SvrSendToClientBtn.Click
If txtName.Text = "" Or SvrIpTxt.Text = "" Then
'Check to make sure that the user has entered
'a display name, and a client IP Address
'If Not, Show a Message Box
MessageBox.Show("All Fields must be Filled", _
"Error Sending Message", _
MessageBoxButtons.OK, MessageBoxIcon.Error)
Else
Try
Client = New TcpClient(SvrIpTxt.Text, SvrPort)
'Declare the Client as an IP Address.
'Must be in the Correct form. eg. 000.0.0.0
Dim Writer As New StreamWriter(Client.GetStream())
Writer.Write(txtName.Text & ": " & SvrToClientTxt.Text)
Writer.Flush()
'Write the Message in the stream
SvrStatusLst.Text += (txtName.Text & " : balls " & SvrToClientTxt.Text) + vbCrLf
SvrToClientTxt.Text = ""
Catch ex As Exception
Console.WriteLine(ex)
Dim Errorresult As String = ex.Message
MessageBox.Show(Errorresult & vbCrLf & vbCrLf & _
"Please Review Client Address", _
"Error Sending Message", _
MessageBoxButtons.OK, MessageBoxIcon.Error)
End Try
End If
End Sub
End Class
推荐答案
数据传输方向完全没有区别。您只需要组织代码。无论你如何做,你总是在TCP上开发一些应用程序级协议: http:/ /en.wikipedia.org/wiki/Application_layer [ ^ ]。
在您的协议中,定义客户端和服务器从读取切换到写入的顺序,反之亦然。它可能取决于数据中发送的某些条件,或者可能只是轮流。
您的问题不是网络,而是指令流和同步。您正试图在计时器事件中侦听并接受新连接。这非常非常糟糕。在服务器部分,您至少需要两个独立的通信线程:一个是侦听和接受新连接,另一个是从/向网络流读/写。这些线程应该通过互锁共享数据(代表远程客户端的套接字集合)进行同步。
对于某些想法,请查看我过去的答案:
套接字编程中的业余问题 [ ^ ],
来自同一端口的多个客户端号码 [ ^ ]。
-SA
There is absolutely no difference in direction of data transfer. You need to just organize your code. No matter how you do it, you always develop some application-level protocol on top of TCP: http://en.wikipedia.org/wiki/Application_layer[^].
In your protocol, define the order in which both client and server switch from reading to writing and visa versa. It could depend on some conditions sent in data, or could be simply taking turns.
Your problem is not the networking, but instruction flow and synchronization. You are trying to listen and accept new connections in a timer event. This is very, very bad. On the server part, you need at least two separate communication threads: one listening and accepting new connections, another one reading/writing from/to network stream. These threads should be synchronized by interlocking of shared data (a collection of the sockets representing remote client).
For some ideas, please see my past answers:
an amateur question in socket programming[^],
Multple clients from same port Number[^].
—SA
这篇关于客户端/服务器程序通信问题。的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!