Skip to content

Instantly share code, notes, and snippets.

@geraintwhite
Last active August 29, 2015 14:09
Show Gist options
  • Select an option

  • Save geraintwhite/40d4c90de0c2ac7162a3 to your computer and use it in GitHub Desktop.

Select an option

Save geraintwhite/40d4c90de0c2ac7162a3 to your computer and use it in GitHub Desktop.
Python TCP chat server and client
from threading import Thread
import socket
import sys
class Server(Thread):
def __init__(self, host='', port=1337):
super().__init__()
self.host = host
self.port = port
self.backlog = 5
self.size = 1024
self.server = None
self.threads = []
def open_socket(self):
try:
self.server = socket.socket()
self.server.bind((self.host, self.port))
self.server.listen(self.backlog)
except socket.error:
if self.server:
self.server.close()
sys.exit('Could not open socket')
print('Server running on port', self.port)
def run(self):
self.open_socket()
self.running = True
while self.running:
c = Connection(self, *self.server.accept())
c.start()
self.threads.append(c)
print('Connection from', c.addr)
self.broadcast('{} has joined the server'.format(c.addr), c)
def broadcast(self, data, client=None):
for sock in self.threads:
if sock is not client:
try:
sock.client.send(data.encode())
except:
self.threads.remove(sock)
self.broadcast('{} has left the server'
.format(sock.addr))
def terminate(self):
self.running = False
self.server.close()
for c in self.threads:
c.join()
self.join()
class Client(Thread):
def __init__(self, host, port):
super().__init__()
self.host = host
self.port = port
self.size = 1024
self.conn = None
def connect(self):
try:
self.conn = socket.socket()
self.conn.connect((self.host, self.port))
except socket.error:
if self.conn:
self.conn.close()
sys.exit('Could not connect to socket')
print('Connected to {}:{}'.format(self.host, self.port))
def run(self):
self.connect()
self.running = True
while self.running:
data = self.conn.recv(self.size).decode()
print(data)
def terminate(self):
self.running = False
self.conn.close()
self.join()
class Connection(Thread):
def __init__(self, server, client, addr):
super().__init__()
self.server = server
self.client = client
self.addr = addr
self.size = 1024
def run(self):
running = True
while running:
data = self.client.recv(self.size)
if data:
msg = '{}: "{}"'.format(self.addr, data.decode())
self.server.broadcast(msg, self)
print(msg)
else:
self.client.close()
running = False
if __name__ == '__main__':
try:
if sys.argv[1] == '-s':
s = Server()
s.start()
input()
s.terminate()
elif sys.argv[2]:
c, s = Client(sys.argv[1], int(sys.argv[2])), True
c.start()
while s:
s = input()
c.conn.send(s.encode())
c.terminate()
except IndexError:
print('Usage: python {} [-s | addr port] '.format(__file__))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment