I'm making an action game in Python. It has to support at least 2 players playing together over the Internet. I've chosen UDP since it seems to be the natural choice for low-latency games. I'm going with a client-server model and I want one player to host the game. This means one player is both hosting the game (server) and running the game (client) at the same time.
Should I be using threads for this or is there another approach? The problem is that the Python documentation says to use serve_forever but I need a non-blocking solution, ideally something I can just call every game loop.
I assume, by your reference to "the Python documentation says to use serve_forever" you are planning to use SocketServer. The module implements synchronous (forking or threading) servers, and you seem to be looking for asynchronous solutions.
For async, non-blocking solutions you might take a look to twisted http://twistedmatrix.com/trac/ (specifically twisted.internet).
Or, it you need something very specific and don't mind writing an event loop, just use poll or select for sockets and other resources...
UDP is not the "natural choice". It's an optimization for a specific type of problem (packet loss) for a specific type of data (typically position/velocity data).
You should stick with TCP until you can demonstrate that your game has a problem with it.
To integrate non-blocking networking into a game in Python, take a look at the approach taken by Game, which invokes the PyGame mainloop from Twisted. This will work equally well with TCP, UDP, or any other protocol that uses sockets.
Related
I am trying to develop a script in Python which would function like the NetDisturb utility. Some of you might ask why am I doing this if there is a ready made utility, but the thing is I want to integrate this in a web page. Using this web page I can access a particular set of interfaces which I already know or are present in the back end script and eventually degrade the performance or simply block packets.
I have succeeded a little but now I want to implement a socket connection between the two interfaces which would be connected. I am unable to have a full duplex communication using a socket connection. I am unable to decide which interface should act as master and which interface should act as slave. Because when I make one of the interface as master the listen and accept statements block further execution of the code.
Would using SOCK_DGRAM sockets instead of SOCK_STREAM help me?
You have to use non-blocking sockets. Here is an explanation how to use select to handle non-blocking sockets (for beginners I could really recommend the complete article, it is a good start). Alternatives would be a multi-threaded architecture or asynchore. If you want additionally a GUI, I can recommend pygtk for the interface and glib.io_add_watch to handle the sockets.
But in general I would recommend some high level framework like zeromq. A second high level alternative would be Twisted, but it has a non-pythonic Java-like API and is (IMO) badly documented.
I want to write an (GUI) application that listens both to keyboard events (client side generated events) and to a network port (server side generated events). I could use some high level advice on how to do this. Some additional info:
- I am using the wxPython module for the GUI
- I could set the socket in non-blocking mode, but this way I have to keep polling the socket by keeping executing the recv() command. I did this earlier and I can recall that this used considerable resources
- I could use the thread module, but since I am not familiar with it, I try to avoid this, but maybe I can't
Advice would be appreciated.
wxPython does have key events. Here are the wxPython docs page on the subject: http://www.wxpython.org/docs/api/wx.KeyEvent-class.html
wxPython doesn't wrap every single thing in wxWidgets. The developers didn't think that they needed to wrap stuff that already had great support in Python itself. Thus, see Python for its socket support
http://docs.python.org/library/socket.html
http://docs.python.org/howto/sockets.html
http://docs.python.org/library/socketserver.html
And if you want to get really heavy, look into the Twisted framework. There are several articles on using it with wxPython:
http://twistedmatrix.com/documents/current/core/howto/choosing-reactor.html
http://wiki.wxpython.org/wxPythonAndTwisted
http://code.activestate.com/recipes/181780-using-wxpython-with-twisted-python/
I am not a wx expert. Could you use wx's native event driven mechanisms? The keypress would certainly have an event. Wx has a socket class wxSocketClient() that could translate the low level socket events (data ready, closed, etc) into a wx event.
There is wxKeyEvent in Docs. Use that to catch the keys and Socket to send it via a network or do whatever you want to do! For socket see this sticky. It is C++ but it will give you a better Idea!
So i been readying for a awhile now. And it seems like asynchronous socket handling would be a better approach to dealing with what I'm trying to do.
Right now I'm working on a gaming server. At the moment socket server will do ok with about 3 clients or so. Sending data at the same exact time.
But my problem is, after that things start to get laggy. So if i do a asynchronous server in the same manner to what i'm already doing. Would it make the game data transfer more smoothly?
This is in python by the way.
Asynchronous sockets are more effective then synchronous. But if the game is lagging for 4+ clients, then your server/client system is badly written and it is not the matter of sockets imho.
I'm looking for some general information on how I should approach a problem that I think Twisted is a great fit for. (I'm new to Twisted but not Python)
I have a home automation controller that can support a single TCP socket connection, sending and receiving binary data. I'd like to use XMPP as a bridge to the socket so a user can send commands and receive events.
I got a rudimentary socket connection working with Twisted that was able to send and receive commands from one of the examples in the O'Reilly book. I also have a fully working Python XMPP bot written with the SleekXMPP library that I'm happy with. I'm just not sure how to bring these together.
The basic scenario is:
User sends message to XMPP bot, which figures out what command to send to the socket
ASCII Socket command is converted to binary and sent to socket
Socket receives command and sends binary response
Binary response converted to ASCII
XMPP bot sends response back to user.
Network events (independent from user action) can also be received by network socket and should be sent to user
It's #6 that is presenting the challenge, otherwise I'd just open/close the socket on demand when in need to write something.
The part that I'm having trouble wrapping my head around with Twisted is the best approach to make these two event loops communicate. I've seen lots of info on using Queues, deferred, threads, select, etc. I have a feeling that Twisted can handle much of the complexity if I just learn to use the tool properly.
If someone can point me in the right direction, I'll take the ball and run with it. As I mentioned, I'm happy with my XMPP bot and I'd like to use the existing code. I think my problem now comes down to creating the socket in the background, then sending and receiving data from that socket in the foreground.
By the way, I'm very happy to share back my code once it's working so someone else can benefit from the help I'm asking for.
-- Scott
One of the problems with a non-blocking IO engine is that its pretty much all-or-nothing. As soon as you introduce blocking code, you can quickly lose most of the benefits of the event-driven asynch approach. Wherever possible (as a rule of thumb), its best to have the entire app running off the same reactor.
As i see it, you have two options:
Twisted is not thread safe. That said, you can use mechanisms like deferToThread and callFromThread to interact with other threads. This is by far the most confusing and needlessly complex approach for your application design. It's particularly painful if you're new to twisted.
Use twisted.words.protocols.jabber, and implement your XMPP stuff in a non-blocking manner using the twisted reactor. That way it will happily exist alongside all your other twisted code. and allow you to cleanly interact between protocols. It will result in less code, and a robust implementation that is easy to extend, maintain, and test.
I have very little idea what I'm doing here, I've never done anything like this before, but a friend and I are writing competing chess programs and they need to be able to communicate to each other.
He'll be writing mainly in C, the bulk of mine will be in Python, and I can see a few options:
Alternately write to a temp file, or successive temp files. As the communication won't be in any way bulky this could work, but seems like an ugly work-around to me, the programs will have to keep checking for change/new files, it just seems ugly.
Find some way of manipulating pipes i.e. mine.py| ./his . This seems like a bit of a dead end.
Use sockets. But I don't know what I'd be doing, so could someone give me a pointer to some reading material? I'm not sure if there are OS-independent, language independent methods. Would there have to be some kind of supervisor server program to administrate?
Use some kind of HTML protocol, which seems like overkill. I don't mind the programs having to run on the same machine.
What do people recommend, and where can I start reading?
If you want and need truly OS independent, language independent inter process communication, sockets are probably the best option.
This will allow the two programs to communicate across machines, as well (without code changes).
For reading material, here's a Python Socket Programming How To.
Two possibilities:
Use IP sockets. There are some examples in the Python docs. (Really not that hard if you just use the basic read/write stuff.) On the other hand, sockets in C are generally not that simple to use.
Create a third application. It launches both applications using subprocess and communicates with both applications through pipes. The chess applications must only be able to read/write to stdin/stdout.
This has the additional benefit that this application could check if a move is legal. This helps you finding bugs and keeping the games fair.
You can use Protobuf as the inter-program protocol and read/write from a file each one turns.
You may read the intermediate file every n seconds.
Once you have this working, you may move to use sockets, where each program would start a server and wait for connections.
The change should be small, because the protocol would be protobuf already. So, the only place you have to change is where you either read from a socket or from a file.
In either case you'll need an interchange protocol.
edit
Ooops I misread and I thought it was C++.
Anyway, here's the C support for protobuf but is still work in progress work
http://code.google.com/p/protobuf-c/
I would say just write an xml file that contains moves for black and white. Mark in a separate file who's turn it is and make sure only the program who's turn it is will write to that file to commit their turn.
Here is a link to a proposed xml format for storing your moves that another group came up with
http://www.xml.com/pub/a/2004/08/25/tourist.html
Sockets with a client/server model...
Basically, you and your friend are creating different implementations of the client.
The local client shows a visual representation of the game and stores the state of the pieces (position, killed/not-killed) and the rules about what the pieces can/can't do (which moves can be made with which pieces and whether the board's state is in check).
The remote server stores state about the players (whose turn it is, points earned, whether the game is won or not), and a listing of moves that have occurred.
When you make a move, your client validates the move against the rules of the game, then sends a message to the server that says, I've made this move, your turn.
The other client sees that a turn has been made, pulls the last move from the server, calculates whether where the movement took place, validates the move against the game rules, and replays the action locally. After that's all done, it's now allows the user to make the next move (or not if the game is over).
The most important part of client/server gaming communication is, send as little data to and store as little state as possible on the server. That way you can play it locally, or across the world with little or no latency. As long as your client is running under the same set of rules as your opponent's client everything should work.
If you want to ensure that no one can cheat by hacking their version of the client, you can make the position and rule calculations all be done on the server and just make the clients nothing but simple playback mechanisms.
The reason why sockets are the best communication medium are:
the limitations on cross process communication are almost as difficult as cross node communication
networking is widely supported on all systems
there's little or no barrier-of-entry to using this remotely if you choose
the networking is robust, flexible, and proven
That's part of the reason why many major systems like Databases uses sockets as a networking as-well-as local communication medium.
if both applications running on same computer, use socket and serialize your objects to jsun. otherwise, use web service and jsun or xml. You can find jsun and xml parser in both languages.