commit c945aba23f5cca6a9b10b017032c604bde7a758b Author: Ray Slakinski Date: Fri May 18 13:37:49 2012 -0400 first commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..2acade4 --- /dev/null +++ b/.gitignore @@ -0,0 +1,11 @@ +.DS_Store +*.*~ +*.py[co] +*.pid +*.log +*.swp +*.swo +*~ +django_cache +.idea +.cache diff --git a/README b/README new file mode 100644 index 0000000..ed51561 --- /dev/null +++ b/README @@ -0,0 +1,9 @@ +This is a sample Thrift application using Python for both the server and client code. + +This sample was based off the work found here http://tkang.blogspot.ca/2010/07/thrift-server-client-in-python.html then expanded upon to first make it functional out of the box(the posted version on the blog had a couple of minor bugs) and to make it a tad more complex to show off some of thrifts features better, but remain a simple application for beginers to get their feet wet with + +Requirements: + +Thrift +thrift (the python package) +Python (I'm using 2.7.1) diff --git a/client.py b/client.py new file mode 100644 index 0000000..afe1443 --- /dev/null +++ b/client.py @@ -0,0 +1,27 @@ +from helloworld import HelloWorld +from helloworld.ttypes import * +from helloworld.constants import * + +from thrift import Thrift +from thrift.transport import TSocket, TTransport +from thrift.protocol import TBinaryProtocol + + +try: + transport = TSocket.TSocket('localhost', 9090) + transport = TTransport.TBufferedTransport(transport) + protocol = TBinaryProtocol.TBinaryProtocol(transport) + client = HelloWorld.Client(protocol) + + transport.open() + + resp = client.ping() + print resp + + msg = Message(name='Ray', lang='jp') + resp = client.sayHello(msg) + print resp + + transport.close() +except Thrift.TException, tx: + print tx.message diff --git a/helloworld.thrift b/helloworld.thrift new file mode 100644 index 0000000..3f341b4 --- /dev/null +++ b/helloworld.thrift @@ -0,0 +1,14 @@ +const string HELLO_IN_ENGLISH = "hello!" +const string HELLO_IN_KOREAN = "an-nyoung-ha-se-yo" +const string HELLO_IN_FRENCH = "bonjour!" +const string HELLO_IN_JAPANESE = "konichiwa!" + +struct Message { + 1: string name, + 2: optional string lang = "en" +} + +service HelloWorld { + string ping(), + string sayHello(1:Message msg) +} diff --git a/helloworld/HelloWorld-remote b/helloworld/HelloWorld-remote new file mode 100755 index 0000000..98e9757 --- /dev/null +++ b/helloworld/HelloWorld-remote @@ -0,0 +1,95 @@ +#!/usr/bin/env python +# +# Autogenerated by Thrift Compiler (0.8.0) +# +# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING +# +# options string: py:new_style +# + +import sys +import pprint +from urlparse import urlparse +from thrift.transport import TTransport +from thrift.transport import TSocket +from thrift.transport import THttpClient +from thrift.protocol import TBinaryProtocol + +import HelloWorld +from ttypes import * + +if len(sys.argv) <= 1 or sys.argv[1] == '--help': + print '' + print 'Usage: ' + sys.argv[0] + ' [-h host[:port]] [-u url] [-f[ramed]] function [arg1 [arg2...]]' + print '' + print 'Functions:' + print ' string ping()' + print ' string sayHello(Message msg)' + print '' + sys.exit(0) + +pp = pprint.PrettyPrinter(indent = 2) +host = 'localhost' +port = 9090 +uri = '' +framed = False +http = False +argi = 1 + +if sys.argv[argi] == '-h': + parts = sys.argv[argi+1].split(':') + host = parts[0] + if len(parts) > 1: + port = int(parts[1]) + argi += 2 + +if sys.argv[argi] == '-u': + url = urlparse(sys.argv[argi+1]) + parts = url[1].split(':') + host = parts[0] + if len(parts) > 1: + port = int(parts[1]) + else: + port = 80 + uri = url[2] + if url[4]: + uri += '?%s' % url[4] + http = True + argi += 2 + +if sys.argv[argi] == '-f' or sys.argv[argi] == '-framed': + framed = True + argi += 1 + +cmd = sys.argv[argi] +args = sys.argv[argi+1:] + +if http: + transport = THttpClient.THttpClient(host, port, uri) +else: + socket = TSocket.TSocket(host, port) + if framed: + transport = TTransport.TFramedTransport(socket) + else: + transport = TTransport.TBufferedTransport(socket) +protocol = TBinaryProtocol.TBinaryProtocol(transport) +client = HelloWorld.Client(protocol) +transport.open() + +if cmd == 'ping': + if len(args) != 0: + print 'ping requires 0 args' + sys.exit(1) + pp.pprint(client.ping()) + +elif cmd == 'sayHello': + if len(args) != 1: + print 'sayHello requires 1 args' + sys.exit(1) + pp.pprint(client.sayHello(eval(args[0]),)) + +else: + print 'Unrecognized method %s' % cmd + sys.exit(1) + +transport.close() diff --git a/helloworld/HelloWorld.py b/helloworld/HelloWorld.py new file mode 100644 index 0000000..cdcb16b --- /dev/null +++ b/helloworld/HelloWorld.py @@ -0,0 +1,361 @@ +# +# Autogenerated by Thrift Compiler (0.8.0) +# +# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING +# +# options string: py:new_style +# + +from thrift.Thrift import TType, TMessageType, TException +from ttypes import * +from thrift.Thrift import TProcessor +from thrift.transport import TTransport +from thrift.protocol import TBinaryProtocol, TProtocol +try: + from thrift.protocol import fastbinary +except: + fastbinary = None + + +class Iface(object): + def ping(self, ): + pass + + def sayHello(self, msg): + """ + Parameters: + - msg + """ + pass + + +class Client(Iface): + def __init__(self, iprot, oprot=None): + self._iprot = self._oprot = iprot + if oprot is not None: + self._oprot = oprot + self._seqid = 0 + + def ping(self, ): + self.send_ping() + return self.recv_ping() + + def send_ping(self, ): + self._oprot.writeMessageBegin('ping', TMessageType.CALL, self._seqid) + args = ping_args() + args.write(self._oprot) + self._oprot.writeMessageEnd() + self._oprot.trans.flush() + + def recv_ping(self, ): + (fname, mtype, rseqid) = self._iprot.readMessageBegin() + if mtype == TMessageType.EXCEPTION: + x = TApplicationException() + x.read(self._iprot) + self._iprot.readMessageEnd() + raise x + result = ping_result() + result.read(self._iprot) + self._iprot.readMessageEnd() + if result.success is not None: + return result.success + raise TApplicationException(TApplicationException.MISSING_RESULT, "ping failed: unknown result"); + + def sayHello(self, msg): + """ + Parameters: + - msg + """ + self.send_sayHello(msg) + return self.recv_sayHello() + + def send_sayHello(self, msg): + self._oprot.writeMessageBegin('sayHello', TMessageType.CALL, self._seqid) + args = sayHello_args() + args.msg = msg + args.write(self._oprot) + self._oprot.writeMessageEnd() + self._oprot.trans.flush() + + def recv_sayHello(self, ): + (fname, mtype, rseqid) = self._iprot.readMessageBegin() + if mtype == TMessageType.EXCEPTION: + x = TApplicationException() + x.read(self._iprot) + self._iprot.readMessageEnd() + raise x + result = sayHello_result() + result.read(self._iprot) + self._iprot.readMessageEnd() + if result.success is not None: + return result.success + raise TApplicationException(TApplicationException.MISSING_RESULT, "sayHello failed: unknown result"); + + +class Processor(Iface, TProcessor): + def __init__(self, handler): + self._handler = handler + self._processMap = {} + self._processMap["ping"] = Processor.process_ping + self._processMap["sayHello"] = Processor.process_sayHello + + def process(self, iprot, oprot): + (name, type, seqid) = iprot.readMessageBegin() + if name not in self._processMap: + iprot.skip(TType.STRUCT) + iprot.readMessageEnd() + x = TApplicationException(TApplicationException.UNKNOWN_METHOD, 'Unknown function %s' % (name)) + oprot.writeMessageBegin(name, TMessageType.EXCEPTION, seqid) + x.write(oprot) + oprot.writeMessageEnd() + oprot.trans.flush() + return + else: + self._processMap[name](self, seqid, iprot, oprot) + return True + + def process_ping(self, seqid, iprot, oprot): + args = ping_args() + args.read(iprot) + iprot.readMessageEnd() + result = ping_result() + result.success = self._handler.ping() + oprot.writeMessageBegin("ping", TMessageType.REPLY, seqid) + result.write(oprot) + oprot.writeMessageEnd() + oprot.trans.flush() + + def process_sayHello(self, seqid, iprot, oprot): + args = sayHello_args() + args.read(iprot) + iprot.readMessageEnd() + result = sayHello_result() + result.success = self._handler.sayHello(args.msg) + oprot.writeMessageBegin("sayHello", TMessageType.REPLY, seqid) + result.write(oprot) + oprot.writeMessageEnd() + oprot.trans.flush() + + +# HELPER FUNCTIONS AND STRUCTURES + +class ping_args(object): + + thrift_spec = ( + ) + + def read(self, iprot): + if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None: + fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec)) + return + iprot.readStructBegin() + while True: + (fname, ftype, fid) = iprot.readFieldBegin() + if ftype == TType.STOP: + break + else: + iprot.skip(ftype) + iprot.readFieldEnd() + iprot.readStructEnd() + + def write(self, oprot): + if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None: + oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec))) + return + oprot.writeStructBegin('ping_args') + oprot.writeFieldStop() + oprot.writeStructEnd() + + def validate(self): + return + + + def __repr__(self): + L = ['%s=%r' % (key, value) + for key, value in self.__dict__.iteritems()] + return '%s(%s)' % (self.__class__.__name__, ', '.join(L)) + + def __eq__(self, other): + return isinstance(other, self.__class__) and self.__dict__ == other.__dict__ + + def __ne__(self, other): + return not (self == other) + +class ping_result(object): + """ + Attributes: + - success + """ + + thrift_spec = ( + (0, TType.STRING, 'success', None, None, ), # 0 + ) + + def __init__(self, success=None,): + self.success = success + + def read(self, iprot): + if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None: + fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec)) + return + iprot.readStructBegin() + while True: + (fname, ftype, fid) = iprot.readFieldBegin() + if ftype == TType.STOP: + break + if fid == 0: + if ftype == TType.STRING: + self.success = iprot.readString(); + else: + iprot.skip(ftype) + else: + iprot.skip(ftype) + iprot.readFieldEnd() + iprot.readStructEnd() + + def write(self, oprot): + if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None: + oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec))) + return + oprot.writeStructBegin('ping_result') + if self.success is not None: + oprot.writeFieldBegin('success', TType.STRING, 0) + oprot.writeString(self.success) + oprot.writeFieldEnd() + oprot.writeFieldStop() + oprot.writeStructEnd() + + def validate(self): + return + + + def __repr__(self): + L = ['%s=%r' % (key, value) + for key, value in self.__dict__.iteritems()] + return '%s(%s)' % (self.__class__.__name__, ', '.join(L)) + + def __eq__(self, other): + return isinstance(other, self.__class__) and self.__dict__ == other.__dict__ + + def __ne__(self, other): + return not (self == other) + +class sayHello_args(object): + """ + Attributes: + - msg + """ + + thrift_spec = ( + None, # 0 + (1, TType.STRUCT, 'msg', (Message, Message.thrift_spec), None, ), # 1 + ) + + def __init__(self, msg=None,): + self.msg = msg + + def read(self, iprot): + if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None: + fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec)) + return + iprot.readStructBegin() + while True: + (fname, ftype, fid) = iprot.readFieldBegin() + if ftype == TType.STOP: + break + if fid == 1: + if ftype == TType.STRUCT: + self.msg = Message() + self.msg.read(iprot) + else: + iprot.skip(ftype) + else: + iprot.skip(ftype) + iprot.readFieldEnd() + iprot.readStructEnd() + + def write(self, oprot): + if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None: + oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec))) + return + oprot.writeStructBegin('sayHello_args') + if self.msg is not None: + oprot.writeFieldBegin('msg', TType.STRUCT, 1) + self.msg.write(oprot) + oprot.writeFieldEnd() + oprot.writeFieldStop() + oprot.writeStructEnd() + + def validate(self): + return + + + def __repr__(self): + L = ['%s=%r' % (key, value) + for key, value in self.__dict__.iteritems()] + return '%s(%s)' % (self.__class__.__name__, ', '.join(L)) + + def __eq__(self, other): + return isinstance(other, self.__class__) and self.__dict__ == other.__dict__ + + def __ne__(self, other): + return not (self == other) + +class sayHello_result(object): + """ + Attributes: + - success + """ + + thrift_spec = ( + (0, TType.STRING, 'success', None, None, ), # 0 + ) + + def __init__(self, success=None,): + self.success = success + + def read(self, iprot): + if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None: + fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec)) + return + iprot.readStructBegin() + while True: + (fname, ftype, fid) = iprot.readFieldBegin() + if ftype == TType.STOP: + break + if fid == 0: + if ftype == TType.STRING: + self.success = iprot.readString(); + else: + iprot.skip(ftype) + else: + iprot.skip(ftype) + iprot.readFieldEnd() + iprot.readStructEnd() + + def write(self, oprot): + if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None: + oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec))) + return + oprot.writeStructBegin('sayHello_result') + if self.success is not None: + oprot.writeFieldBegin('success', TType.STRING, 0) + oprot.writeString(self.success) + oprot.writeFieldEnd() + oprot.writeFieldStop() + oprot.writeStructEnd() + + def validate(self): + return + + + def __repr__(self): + L = ['%s=%r' % (key, value) + for key, value in self.__dict__.iteritems()] + return '%s(%s)' % (self.__class__.__name__, ', '.join(L)) + + def __eq__(self, other): + return isinstance(other, self.__class__) and self.__dict__ == other.__dict__ + + def __ne__(self, other): + return not (self == other) diff --git a/helloworld/__init__.py b/helloworld/__init__.py new file mode 100644 index 0000000..45da5fe --- /dev/null +++ b/helloworld/__init__.py @@ -0,0 +1 @@ +__all__ = ['ttypes', 'constants', 'HelloWorld'] diff --git a/helloworld/constants.py b/helloworld/constants.py new file mode 100644 index 0000000..2af2b8c --- /dev/null +++ b/helloworld/constants.py @@ -0,0 +1,15 @@ +# +# Autogenerated by Thrift Compiler (0.8.0) +# +# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING +# +# options string: py:new_style +# + +from thrift.Thrift import TType, TMessageType, TException +from ttypes import * + +HELLO_IN_ENGLISH = "hello!" +HELLO_IN_KOREAN = "an-nyoung-ha-se-yo" +HELLO_IN_FRENCH = "bonjour!" +HELLO_IN_JAPANESE = "konichiwa!" diff --git a/helloworld/ttypes.py b/helloworld/ttypes.py new file mode 100644 index 0000000..2aa71c6 --- /dev/null +++ b/helloworld/ttypes.py @@ -0,0 +1,90 @@ +# +# Autogenerated by Thrift Compiler (0.8.0) +# +# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING +# +# options string: py:new_style +# + +from thrift.Thrift import TType, TMessageType, TException + +from thrift.transport import TTransport +from thrift.protocol import TBinaryProtocol, TProtocol +try: + from thrift.protocol import fastbinary +except: + fastbinary = None + + + +class Message(object): + """ + Attributes: + - name + - lang + """ + + thrift_spec = ( + None, # 0 + (1, TType.STRING, 'name', None, None, ), # 1 + (2, TType.STRING, 'lang', None, "en", ), # 2 + ) + + def __init__(self, name=None, lang=thrift_spec[2][4],): + self.name = name + self.lang = lang + + def read(self, iprot): + if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None: + fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec)) + return + iprot.readStructBegin() + while True: + (fname, ftype, fid) = iprot.readFieldBegin() + if ftype == TType.STOP: + break + if fid == 1: + if ftype == TType.STRING: + self.name = iprot.readString(); + else: + iprot.skip(ftype) + elif fid == 2: + if ftype == TType.STRING: + self.lang = iprot.readString(); + else: + iprot.skip(ftype) + else: + iprot.skip(ftype) + iprot.readFieldEnd() + iprot.readStructEnd() + + def write(self, oprot): + if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None: + oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec))) + return + oprot.writeStructBegin('Message') + if self.name is not None: + oprot.writeFieldBegin('name', TType.STRING, 1) + oprot.writeString(self.name) + oprot.writeFieldEnd() + if self.lang is not None: + oprot.writeFieldBegin('lang', TType.STRING, 2) + oprot.writeString(self.lang) + oprot.writeFieldEnd() + oprot.writeFieldStop() + oprot.writeStructEnd() + + def validate(self): + return + + + def __repr__(self): + L = ['%s=%r' % (key, value) + for key, value in self.__dict__.iteritems()] + return '%s(%s)' % (self.__class__.__name__, ', '.join(L)) + + def __eq__(self, other): + return isinstance(other, self.__class__) and self.__dict__ == other.__dict__ + + def __ne__(self, other): + return not (self == other) diff --git a/server.py b/server.py new file mode 100644 index 0000000..bd6b9c8 --- /dev/null +++ b/server.py @@ -0,0 +1,39 @@ +from helloworld import HelloWorld +from helloworld.ttypes import * +from helloworld.constants import * + +from thrift.transport import TSocket +from thrift.transport import TTransport +from thrift.protocol import TBinaryProtocol +from thrift.server import TServer + + +class HelloWorldHandler: + def __init__(self): + self.log = {} + + def ping(self): + return "pong" + + def sayHello(self, msg): + if msg.lang in ('kp', 'kr'): + hello = HELLO_IN_KOREAN + elif msg.lang == 'fr': + hello = HELLO_IN_FRENCH + elif msg.lang == 'jp': + hello = HELLO_IN_JAPANESE + else: + hello = HELLO_IN_ENGLISH + return '%s %s' % (hello, msg.name) + +handler = HelloWorldHandler() +processor = HelloWorld.Processor(handler) +transport = TSocket.TServerSocket('localhost', port=9090) +tfactory = TTransport.TBufferedTransportFactory() +pfactory = TBinaryProtocol.TBinaryProtocolFactory() + +server = TServer.TSimpleServer(processor, transport, tfactory, pfactory) + +print 'Starting server...' +server.serve() +print('done!')