Search code examples
pythonpython-2.7tcpudptwisted

Twisted protocol that simultaneously handles TCP and UDP at once


What I want to do, thinking about my logic, is independent of the transport that I choose - I want UDP and TCP to work. Normally, if I was doing TCP or SSL -- this is a little trivial. However, with UDP (no factory) and TCP (uses factory), it becomes a little tricky?

from twisted.internet.protocol import Factory, ServerFactory, Protocol, DatagramProtocol
from twisted.internet import reactor

class SpecialServerProtocol(DatagramProtocol, Protocol):
  def datagramReceived(self, datagram, address):
    print("Received udp")
    self.transport.write(datagram, address)

  def dataReceived(self, data):
    print("Received tcp")
    self.transport.write(data)

class SpecialServerFactory(ServerFactory):
  protocol = IPBusServerProtocol

def main():
  reactor.listenTCP(8000, SpecialServerFactory())
  reactor.listenUDP(8000, SpecialServerProtocol())

  reactor.run()

if __name__ == '__main__':
  main()

This is some code I've managed to get and it seems to work as expected (I think). It's not clear to me if this is actually a good thing to do, or if I should separate out the same logic from TCP/UDP and pass it off to a series of functions independent of how they're called.


Solution

  • TCP is connection-oriented, which means you get a notification that a connection is beginning, when data arrives on it, and when it ends. UDP is not; you just get chunks of data from various peers, which may appear or disappear at any time with no notification. Therefore you cannot speak the same protocol over TCP and UDP; you need a UDP version and a TCP version.