I am trying to create a simple form of client-server application, using python. So I got started with sockets, and facing some errors I searched a bit and saw that no two sockets can be listening to the same port at the same time. Is that true? And if so, the only way to handle multiple requests towards the server, as regards the sockets, is to have a single socket do the listening and take turns at the incoming requests?
When you call accept(), it returns a new socket for the connection, the original socket is still listening for new connections.
– Barmar
Related
I tried to use python's zmq lib. And now I have two questions:
Is there a way to check socket connection state?
I'd like to know if connection is established after call connect
I want to one-to-one communication model.
I tried to use PAIR zmq socket type.
In that case if one client is already connected, server will not receive any messages from secondary connected client.
But I'd like to get info in the second client that there is another client and server is busy.
You'd get an error if connect fails.
But I guess the real question is how often do you want to check this? once at startup, before each message, or periodically, using some heartbeat?
That does not make sense, as you can not send info without connecting first.
However, some socket types might give some more info.
But the best way would be to use multiple sockets: one for such status information, and another one for sending data.
ZMQ is made to use multiple sockets.
I captured packets using Wireshark while my computer is connecting to random web site for my assignment using TCP. Normally, there should be 3 initial packets (SYN, SYN-ACK, ACK) for 3-way handshake before the data transfer starts.
In my case, there are 9 connections, 3 different 3-way handshake; each was done with a different port of my computer. After each of them are accepted, the data transfer continues with only one of the ports.
I couldn't understand the reason behind this. Thanks!
It is common that browsers open multiple connections to a site. Reason for this is that with HTTP/1 a single TCP connection can only handle a single request-response at a time, i.e. multiple requests after each other and not in parallel. To handle multiple requests in parallel a browser needs to have multiple TCP connections open. Since connection setup takes some time browsers might open multiple connections to the server just to have some already established if new requests need to be send.
Is it possible to create a socket connection (from either Python or a nc based listener), and then 'join' it from another Python process, sending data from the same socket to the same remote, and vice versa?
It is possible for a Python process to create a listening socket, bind() it to a port, and listen()s for incoming TCP connections on that port, and then at some point after that, another Python process can connect() to that port, at which point the first process can accept() the incoming TCP connection and the two processes can send data to each other over it. So if that is what you are asking about, the Python socket module has the APIs you are looking for.
If OTOH you are asking about splicing a third party in as a middleman between two existing processes that are already communicating with each other over TCP, that is not possible without some serious low-level hackery, since TCP was designed as a 1-to-1 communications mechanism only.
I have a number of clients who need to connect to a server and maintain the connection for some time (around 4 hours). I don't want to specify a different connection port for each client (as there are potentially many of them) I would like them just to be able to connect to the server on a specific predetermined port e.g., 10800 and have the server accept and maintain the connection but still be able to receive other connections from new clients. Is there a way to do this in Python or do I need to re-think the architecture.
EXTRA CREDIT: A Python snippet of the server code doing this would be amazing!
I don't want to specify a different connection port for each client (as there are potentially many of them)
You don't need that.
I would like them just to be able to connect to the server on a specific predetermined port e.g., 10800 and have the server accept and maintain the connection but still be able to receive other connections from new clients
That's how TCP already works.
Just create a socket listening to port 10800 and accept connections from it.
Use select.select() to detect events on multiple sockets, like incoming connections, incoming data, outgoing buffer capacity and connection errors. You can use this on multiple listening sockets and on established connections from a single thread. Using a websearch, you can surely find example code.
I want to create a simple video streaming (actually, image streaming) server that can manage different protocols (TCP Push/Pull, UDP Push/Pull/Multicast).
I managed to get TCP Push/Pull working with the SocketServer.TCPServer class and ThreadinMixIn for processing each connected client in a different thread.
But now that I'm working on the UDP protocol, I just realized that ThreadinMixIn creates a thread per call of handle() per client query (as there's nothing such as a "connection" in UDP).
The problem is I need to process a sequence of queries by the same client, for all the clients. How could I manage that ?
The only way I see I could handle that is to have a list of (client adresses, processing thread) and send each query to the matching thread (or create a new one if the client haven't sent any thread yet). Is there an easier way to do that ?
Thanks !
P.S : I can't use any external or too "high-level" library for this as it's a school subject meant to understand how sockets work.
Take a look at Twisted. This will remove the need to do any thread dispatch from your application. You still have to match up packets to a particular session in order to handle them, but this isn't difficult (use a port per client and dispatch based on the port, or require packets in a session to always come from the same address and use the peer address, or use one of the existing protocols that solves this problem such as SIP).