I wrote a simple http server with Tornado, but sometimes it raise exception below, self.session.response runs in a threadpool.
code of server:
class AuToServer(object):
module_path = os.path.split(os.path.realpath(__file__))[0] + '/../module/'
def __init__(self, prefix=DEFAULT_PREFIX, work_root=module_path, module=[], **kwargs):
self._prefix = prefix
self._thread_pool = ExecutorDelegate(20)
self._module_manager = ModuleManager(work_root)
self.initilize(module, kwargs)
def initilize(self, modules, kwargs):
self._module_manager.set_args(kwargs)
if not self._module_manager.prepare(modules):
print "initilize module fail. [%s]" % (str(modules))
raise AppInitError("initilize %s fail" % (modules))
def __call__(self, request): # request handler
session = Session(request)
if not session.parse(self._prefix):
print "parse query fail. [%s]" % (session.query)
session.response("url parse fail [%s]\n" % session.query)
return
self._thread_pool.submit(WorkerHander(self._module_manager, session))
def start(self, port=8880):
http_server = tornado.httpserver.HTTPServer(self, max_header_size=128*1024)
http_server.listen(port)
tornado.ioloop.IOLoop.instance().start()
code of WorkerHander:
class WorkerHander(BaseExecutor):
def __init__(self, module_manage, session):
self.module_manage = module_manage
self.session = session
super(WorkerHander, self).__init__(self)
def run(self):
method = self.session.get_command()
if not method:
self.session.response("invalid url [%s]\n" % (self.session.query))
return
context = self.module_manage.run(method, self.session)
try:
if context:
self.session.response(context) # raise exception
else:
self.session.response("None\n")
except Exception, error:
Logger.warning("session response fail. [%s][%s]" % (self.session.query, traceback.format_exc()))
code of session.response
def response(self, context):
if not self.request:
return False
if isinstance(context, unicode):
context = context.encode("utf8")
self.request.write(utf8("%s %d\r\n\r\n%s" % (
HTTP_HEADER,
len(context),
context)))
Logger.debug("QUERY:[cmd:%s][%s] [%s] [%s]" % (
self.command,
time.time() - self.begin_time,
self.request.remote_ip,
self.query))
self.request.finish()
return True
exception:
2016-02-29 16:29:26,852 WARNING: server.py:run:94: session response fail. [/auto?start_timestamp=1456730772&_cmd=get_index_info][Traceback (most recent call last):
File "/home/admin/autobots/lib/python2.7/site-packages/autobase-0.0.1-py2.7.egg/autobase/service/server.py", line 90, in run
self.session.response(context)
File "/home/admin/autobots/lib/python2.7/site-packages/autobase-0.0.1-py2.7.egg/autobase/service/session.py", line 43, in response
self.request.finish()
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/httputil.py", line 407, in finish
self.connection.finish()
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/http1connection.py", line 459, in finish
self._pending_write.add_done_callback(self._finish_request)
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/concurrent.py", line 243, in add_done_callback
fn(self)
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/http1connection.py", line 491, in _finish_request
self.close()
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/http1connection.py", line 297, in close
self.stream.close()
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/iostream.py", line 427, in close
self.close_fd()
File "/home/admin/autobots/lib/python2.7/site-packages/tornado-4.2-py2.7-linux-x86_64.egg/tornado/iostream.py", line 995, in close_fd
self.socket.close()
AttributeError: 'NoneType' object has no attribute 'close'
]
Do I use Tornado in a wrong way? ask for help. thanks~
Tornado is not thread-safe by design. You can use a thread pool to do your own work, but you must call all Tornado methods (including in this case self.request.write and self.request.finish) from the IOLoop thread.
Related
I am new to Locust (and Python) and am trying to load test an API. My Locust UI shows no stats whatsoever - no users hatched, no API calls, etc. I need help figuring out how to get them to show up on the UI so I can get the stats.
Here is my locust.py file:
from locust import HttpUser, SequentialTaskSet, task, constant
import finops_service.locust_files.finops_fx_load_testing as load_test
class FXTransaction(SequentialTaskSet):
def __init__(self, parent):
super().__init__(parent)
self.comp_data = dict()
self.rate_lock_response = dict()
self.transaction_response = dict()
self.fx_providerID = '57638f08-e938-48d7-accf-325b6728a9ee'
self.headers = {"Content-Type": "application/json"}
def on_start(self):
load_test.login(self),
#task
def get_company_data(self):
# Get company data
self.comp_data = load_test.get_company_data(self)
print("Company is: ", self.comp_data['company'])
print("Vendor is: ", self.comp_data['vendor'])
print("Payment Method is: ", self.comp_data['payment_method'])
print("Funding Method is: ", self.comp_data['funding_method'])
# #task
# def rate_lock(self):
print("Starting rate lock")
load_test.rate_lock(self)
print("This is the returned rate lock response:")
print(self.rate_lock_response)
# #task
# def approve_transaction(self):
# print("Starting transaction")
# load_test.approve_transaction(self)
# print("This is the returned transaction response:")
# print(self.transaction_response)
class MyUser(HttpUser):
wait_time = constant(1)
# weight = 1
host = "http://localhost:8080/PaymentService/base/"
tasks = [FXTransaction]
And here are my functions:
import json
import random
import uuid
from utils import json_util as json_util
enter code here
def login(self):
try:
with self.client.post(
"security/login",
headers={'Content-Type': 'application/json',
'Authorization': 'BASIC 0ee89b88-5c4b-4922-b1f9-c1584ab26e7e:12345'},
name=login,
timeout=55.6,
catch_response=True) as response:
if response.status_code != 200:
response.failure("Login failed")
else:
response.success()
print("Login succeeded")
self.headers.update({'if-Match': "{}".format(response.headers["ETag"])})
except ConnectionRefusedError:
print("The test could not connect to {}".format("http://localhost:8080/PaymentService/security/login"))
raise
def get_company_data(self):
comp_index = random.randrange(0, 9)
print("Random company data index is: ", comp_index)
try:
body = json.load(open("finops_service/locust_files/load_testing_data.json", 'r'))
comp_data = body['fx']['multipleCompanies_10']['company_data'][comp_index]
except ConnectionRefusedError:
print("The test could not connect to {}".format("http://localhost:8080/PaymentService/security/login"))
raise
return comp_data
def rate_lock(self):
body = json_util.get_json_object(
"/finops_service/locust_files/rate_lock_load_testing.json",
'fx'.lower(),
'valid_multiple_20'.lower()
)
body["debtorCompanyProfileId"] = self.comp_data['company']
i = 0
# there are 20 rate locks so need to update each request
while i < 20:
body["rateRequestPayments"][i]["creditorProfileId"] = self.comp_data['vendor']
body["rateRequestPayments"][i]["debtorProfileId"] = self.comp_data['company']
body["rateRequestPayments"][i]["paymentMethodId"] = self.comp_data['payment_method']
random_float_no = round(random.uniform(1.11, 999.99), 2)
body['rateRequestPayments'][i]['amount'] = random_float_no
i += 1
try:
print("RIGHT BEFORE RATE LOCK CALL")
with self.client.post("services/transaction/fx/rate/lock",
data=json.dumps(body),
headers=self.headers,
name="rate lock",
timeout=55.6,
catch_response=True) as response:
if "GENERIC_FAILURE" in response.text:
response.failure("FAIL")
print("Rate lock call failed")
else:
response.success()
print("rate lock succeeded")
print("Rate lock response is:.........", response)
print("Rate lock response TEXT is:.........", response.text)
self.rate_lock_response = response.text
except ConnectionRefusedError:
print("The test could not connect to {}".format(
"http://localhost:8080/PaymentService/services/transaction/fx/rate/lock"))
raise
When I run this, I can see that the self.client.post("services/transaction/fx/rate/lock"... is happening and either succeeding or failing. However, in the Locust UI, I show 0 users hatched (console shows I hatched 5) and 0 tasks shown.
I get this error each time I run which it looks related to my stats not showing up but I don't know why it is happening:
Traceback (most recent call last):
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/gevent/pywsgi.py", line 999, in handle_one_response
self.run_application()
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/gevent/pywsgi.py", line 945, in run_application
self.result = self.application(self.environ, self.start_response)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 2464, in __call__
return self.wsgi_app(environ, start_response)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 2450, in wsgi_app
response = self.handle_exception(e)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 1867, in handle_exception
reraise(exc_type, exc_value, tb)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/_compat.py", line 39, in reraise
raise value
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 2447, in wsgi_app
response = self.full_dispatch_request()
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 1952, in full_dispatch_request
rv = self.handle_user_exception(e)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 1821, in handle_user_exception
reraise(exc_type, exc_value, tb)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/_compat.py", line 39, in reraise
raise value
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 1950, in full_dispatch_request
rv = self.dispatch_request()
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/flask/app.py", line 1936, in dispatch_request
return self.view_functions[rule.endpoint](**req.view_args)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/locust/web.py", line 319, in wrapper
return view_func(*args, **kwargs)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/locust/util/cache.py", line 21, in wrapper
cache["result"] = func(*args, **kwargs)
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/site-packages/locust/web.py", line 208, in request_stats
"safe_name": escape(s.name, quote=False),
File "/Users/michellegautier/.pyenv/versions/3.7.4/lib/python3.7/html/__init__.py", line 19, in escape
s = s.replace("&", "&") # Must be done first!
AttributeError: 'function' object has no attribute 'replace'
2021-03-18T16:44:29Z {'REMOTE_ADDR': '::1', 'REMOTE_PORT': '49242', 'HTTP_HOST': 'localhost:8089', (hidden keys: 25)} failed with AttributeError
Can someone please help me figure out how to make my stats show up?
Thank you!!!!
The stats not showing up in Locust is because of that Exception you posted. If you resolve that and get to where your code runs without issues, you should see stats in the Locust UI.
There are a number of issues with your code.
I'm not sure if it's just an issue with pasting your code into SO, but your on_start() and get_company_data() functions (and the #task decorator) need to be indented so they're part of FXTransaction.
Also, trying to use self.client in login() or get_company_data() isn't going to work because they aren't part of a class so there's no such thing as self. You'd probably want to change self in that function to just client and then pass in self.client when you call it from the on_start() function.
But what's possibly your main issue is here:
with self.client.post(
"security/login",
headers={'Content-Type': 'application/json',
'Authorization': 'BASIC 0ee89b88-5c4b-4922-b1f9-c1584ab26e7e:12345'},
name=login,
…
name here is the name of the endpoint (URL) you're hitting. This is supposed to be a string but you're giving it your function login. So when the Locust code tries to do some thing with your name value that it wants to do, expecting it to be a string, it's going to fail because it's trying to do those on a function instead. That's what AttributeError: 'function' object has no attribute 'replace' means.
I think if you fix all of those things, Locust should work.
I would like to stay in the std lib if possible. All of my threads run, and the sockets will listen appropriately. I need to be able to gracefully close the sockets, but I can't seem to get back to them to shutdown properly.
Problem is, when I get to server_close() it blows up on me (see exception trace output below).
Thanks for looking!
import sys
import threading
import SocketServer
class EchoRequestHandler(SocketServer.BaseRequestHandler):
def __init__(self, request, client_address, server):
SocketServer.BaseRequestHandler.__init__(self, request, client_address, server)
return
def setup(self):
return SocketServer.BaseRequestHandler.setup(self)
def handle(self):
# Echo the back to the client
data = self.request.recv(1024)
return
def finish(self):
return SocketServer.BaseRequestHandler.finish(self)
class EchoServer(SocketServer.TCPServer):
def __init__(self, server_address, handler_class=EchoRequestHandler):
SocketServer.TCPServer.__init__(self, server_address, handler_class)
return
def server_activate(self):
SocketServer.TCPServer.server_activate(self)
return
def serve_forever(self):
while True:
self.handle_request()
return
def server_close(self):
return SocketServer.TCPServer.server_close(self)
def bind_sockets(port_list):
server_list = []
for port in port_list:
server = EchoServer(("", int(port)), EchoRequestHandler)
server_thread = threading.Thread(target=server.serve_forever)
server_thread.setDaemon(True)
server_thread.start()
server_list.append(server)
print "listening on port", port
return server_list
def main():
port_list = [12345,54321]
active_servers = bind_sockets(port_list)
print "Hit Q to quit or R to reload."
while 1:
key_press = sys.stdin.read(1)
if key_press == "q":
sys.exit(2)
elif key_press == "r":
#We need to close gracefully so we can go on to do other stuff.
print active_servers.__len__()
for server in active_servers:
server.server_close()
print "closed"
if __name__ == "__main__":
main()
The exception stack-trace I get is:
Exception in thread Thread-1: Traceback (most recent call last):
File "~snip~/threading.py", line 810, in __bootstrap_inner self.run()
File "~snip~/threading.py", line 763, in run self.__target(*self.__args, **self.__kwargs)
File "kill_thread.py", line 36, in serve_forever self.handle_request()
File "~snip~/SocketServer.py", line 276, in handle_request fd_sets = _eintr_retry(select.select, [self], [], [], timeout)
File "~snip~/SocketServer.py", line 155, in _eintr_retry return func(*args) error: (9, 'Bad file descriptor')
You have two problems:
you need to call shutdown()
You shouldn't override server_forever()
like this:
# don't overrule server_forever, the default implementation
# handles the shutdown()
#def serve_forever(self):
# while True:
# self.handle_request()
# return
def server_close(self):
self.shutdown()
return SocketServer.TCPServer.server_close(self)
Im trying to use alchimia for get asynchronous API for DB. Trying to make a simple request to DB, like that:
def authorization(self, data):
"""
Checking user with DB
"""
def __gotResult(user):
yield engine.execute(sqlalchemy.select([Users]).where(Users.name == user))
result = __gotResult(data['user'])
log.msg("[AUTH] User=%s trying to auth..." % data['user'])
data, result_msg = commands.AUTH(result, data)
log.msg(result_msg)
return data
And cant understand - what i doing wrong? Maybe issue in option for engine (where reactor=[])?
Source code:
import sys
from json import dumps, loads
import sqlalchemy
from twisted.internet import reactor, ssl
from twisted.python import log, logfile
from twisted.web.server import Site
from twisted.web.static import File
from autobahn.twisted.websocket import WebSocketServerFactory, WebSocketServerProtocol, listenWS
import commands
from db.tables import Users
from alchimia import TWISTED_STRATEGY
log_file = logfile.LogFile("service.log", ".")
log.startLogging(log_file)
engine = sqlalchemy.create_engine('postgresql://test:test#localhost/testdb', pool_size=20, max_overflow=0,strategy=TWISTED_STRATEGY, reactor=[])
class DFSServerProtocol(WebSocketServerProtocol):
commands = commands.commands_user
def __init__(self):
self.commands_handlers = self.__initHandlersUser()
def __initHandlersUser(self):
handlers = commands.commands_handlers_server
handlers['AUTH'] = self.authorization
handlers['READ'] = None
handlers['WRTE'] = None
handlers['DELT'] = None
handlers['RNME'] = None
handlers['SYNC'] = None
handlers['LIST'] = None
return handlers
def authorization(self, data):
"""
Checking user with DB
"""
def __gotResult(user):
yield engine.execute(sqlalchemy.select([Users]).where(Users.name == data['user']))
result = __gotResult(data['user'])
log.msg("[AUTH] User=%s trying to auth..." % data['user'])
data, result_msg = commands.AUTH(result, data)
log.msg(result_msg)
return data
def onMessage(self, payload, isBinary):
json_data = loads(payload)
json_auth = json_data['auth']
json_cmd = json_data['cmd']
if json_auth == False:
if json_cmd == 'AUTH':
json_data = self.commands_handlers['AUTH'](json_data)
# for authorized users
else:
if json_cmd in commands.commands_user.keys():
if self.commands_handlers[json_cmd] is not None:
json_data = self.commands_handlers[json_cmd](json_data)
else:
json_data['error'] = '%s command is not already realized...' % json_cmd
else:
json_data['auth'] = False
json_data['error'] = 'This command is not supported on server...'
response = dumps(json_data)
self.sendMessage(str(response))
if __name__ == '__main__':
if len(sys.argv) > 1 and sys.argv[1] == 'debug':
log.startLogging(sys.stdout)
debug = True
else:
debug = False
contextFactory = ssl.DefaultOpenSSLContextFactory('keys/server.key', 'keys/server.crt')
factory = WebSocketServerFactory("wss://localhost:9000", debug = debug, debugCodePaths = debug)
factory.protocol = DFSServerProtocol
factory.setProtocolOptions(allowHixie76 = True)
listenWS(factory, contextFactory)
webdir = File("./web/")
webdir.contentTypes['.crt'] = 'application/x-x509-ca-cert'
web = Site(webdir)
reactor.listenSSL(8080, web, contextFactory)
#reactor.listenTCP(8080, web)
reactor.run()
Traceback:
Traceback (most recent call last):
File "/usr/local/lib/python2.7/dist-packages/twisted/python/log.py", line 88, in callWithLogger
return callWithContext({"system": lp}, func, *args, **kw)
File "/usr/local/lib/python2.7/dist-packages/twisted/python/log.py", line 73, in callWithContext
return context.call({ILogContext: newCtx}, func, *args, **kw)
File "/usr/local/lib/python2.7/dist-packages/twisted/python/context.py", line 118, in callWithContext
return self.currentContext().callWithContext(ctx, func, *args, **kw)
File "/usr/local/lib/python2.7/dist-packages/twisted/python/context.py", line 81, in callWithContext
return func(*args,**kw)
--- <exception caught here> ---
File "/usr/local/lib/python2.7/dist-packages/twisted/internet/posixbase.py", line 614, in _doReadOrWrite
why = selectable.doRead()
File "/usr/local/lib/python2.7/dist-packages/twisted/internet/tcp.py", line 215, in doRead
return self._dataReceived(data)
File "/usr/local/lib/python2.7/dist-packages/twisted/internet/tcp.py", line 221, in _dataReceived
rval = self.protocol.dataReceived(data)
File "/usr/local/lib/python2.7/dist-packages/twisted/protocols/tls.py", line 419, in dataReceived
self._flushReceiveBIO()
File "/usr/local/lib/python2.7/dist-packages/twisted/protocols/tls.py", line 389, in _flushReceiveBIO
ProtocolWrapper.dataReceived(self, bytes)
File "/usr/local/lib/python2.7/dist-packages/twisted/protocols/policies.py", line 120, in dataReceived
self.wrappedProtocol.dataReceived(data)
File "/usr/local/lib/python2.7/dist-packages/autobahn/twisted/websocket.py", line 78, in dataReceived
self._dataReceived(data)
File "/usr/local/lib/python2.7/dist-packages/autobahn/websocket/protocol.py", line 1270, in _dataReceived
self.consumeData()
File "/usr/local/lib/python2.7/dist-packages/autobahn/websocket/protocol.py", line 1286, in consumeData
while self.processData() and self.state != WebSocketProtocol.STATE_CLOSED:
File "/usr/local/lib/python2.7/dist-packages/autobahn/websocket/protocol.py", line 1445, in processData
return self.processDataHybi()
File "/usr/local/lib/python2.7/dist-packages/autobahn/websocket/protocol.py", line 1758, in processDataHybi
fr = self.onFrameEnd()
File "/usr/local/lib/python2.7/dist-packages/autobahn/websocket/protocol.py", line 1887, in onFrameEnd
self._onMessageEnd()
File "/usr/local/lib/python2.7/dist-packages/autobahn/twisted/websocket.py", line 107, in _onMessageEnd
self.onMessageEnd()
File "/usr/local/lib/python2.7/dist-packages/autobahn/websocket/protocol.py", line 734, in onMessageEnd
self._onMessage(payload, self.message_is_binary)
File "/usr/local/lib/python2.7/dist-packages/autobahn/twisted/websocket.py", line 110, in _onMessage
self.onMessage(payload, isBinary)
File "server.py", line 84, in onMessage
json_data = self.commands_handlers['AUTH'](json_data)
File "server.py", line 68, in authorization
data, result_msg = commands.AUTH(result, data)
File "/home/relrin/code/Helenae/helenae/commands.py", line 68, in AUTH
if result['name'] == data['user']:
exceptions.TypeError: 'generator' object has no attribute '__getitem__'
I think you are missing an #inlineCallbacks around __gotResult() That might not help you quite enough, though; since a single statement generator wrapped with inlineCallbacks is sort of pointless. You should get used to working with explicit deferred handling anyway. Lets pull this apart:
def authorization(self, data):
"""
Checking user with DB
"""
# engine.execute already gives us a deferred, will grab on to that.
user = data['user']
result_d = engine.execute(sqlalchemy.select([Users]).where(Users.name == user))
# we don't have the result in authorization,
# we need to wrap any code that works with its result int a callback.
def result_cb(result):
data, result_msg = commands.AUTH(result, data)
return data
result_d.addCallback(result_cb)
# we want to pass the (asynchronous) result out, it's hiding in our deferred;
# so we return *that* instead; callers need to add more callbacks to it.
return result_d
If you insist; we can squish this down into an inline callbacks form:
from twisted.internet.defer import inlineCallbacks, returnValue
#inlineCallbacks
def authorization(self, data):
user = data['user']
result = yield engine.execute(sqlalchemy.select([Users]).where(Users.name == user))
data, result_msg = commands.AUTH(result, data)
yield returnValue(data)
as before, though, authorization() is asynchronous; and must be since engine.execute is async. to use it, you must attach a callback to the deferred it returns (although the caller may also yield it if it is also wrapped in inlineCallbacks
class GenericUploader(object):
def __init__(self, data, fname):
"""data is the string we want to upload"""
self.log = logging.getLogger(type(self).__name__)
self.data = data
self.data.seek(0)
self.fname = fname
def upload(self):
"""Should return true or false"""
raise NotImplementedError
class SshUploader(GenericUploader):
def __init__(self, data, fname, user, host):
GenericUploader.__init__(self, data, fname)
self.log.debug('Initializing SshUploader')
self.user = user
self.host = host
def upload(self):
import subprocess
proc = subprocess.Popen(['ssh', self.user + '#' + self.host,
'cat > %s' % self.fname],
stdin=subprocess.PIPE)
proc.communicate(self.data.getvalue())
if proc.returncode != 0:
self.log.critical('Problem writing to remote server %s#%s: %d',
self.user, self.hos, proc.returncode)
return False
else:
self.log.debug('Uploaded to ssh server %s#%s', self.user, self.host)
return True
class FtpUploader(GenericUploader):
def __init__(self, data, fname, user, host, passwd):
GenericUploader.__init__(self, data, fname)
self.log.debug('Initializing FtpUploader')
self.user = user
self.host = host
self.passwd = passwd
def upload(self):
import ftplib
try:
session = ftplib.FTP(self.host, self.user, self.passwd)
session.storbinary('STOR %s' % self.fname, self.data)
session.quit()
except:
self.log.exception('Ftp upload failed')
return False
else:
self.log.debug('Uploaded to ftp server %s#%s', self.user, self.host)
return True
class DropBoxUploader(GenericUploader):
def __init__(self, data, fname, access_token):
GenericUploader.__init__(self, data, fname)
self.access_token = access_token
def upload(self):
import config
try:
import dropbox
except ImportError:
self.log.critical('dropbox module is required![pip install dropbox]')
return False
try:
client = dropbox.client.DropboxClient(self.access_token)
# print 'linked account: ', client.account_info()
response = client.put_file(self.fname, self.data)
except dropbox.rest.ErrorResponse, e:
self.log.exception('Exception uploading to dropbox: %s', str(e))
return False
except Exception:
self.log.exception('Unknown exception while uploading to dropbox')
return False
else:
self.log.debug('Uploaded to dropbox of: %s', str(client.account_info()))
return True
The above code works perfect for SshUploader & FtpUploader.
The DropBoxUploader throws the exception:
Traceback (most recent call last):
2¦ File "/media/sf_aptata/ManhattanApi/insertors/uploaders.py", line 96, in upload
response = client.put_file(self.fname, self.data)
File "/home/xubuntu/env/local/lib/python2.7/site-packages/dropbox/client.py", line 321, in put_file
return self.rest_client.PUT(url, file_obj, headers)
File "/home/xubuntu/env/local/lib/python2.7/site-packages/dropbox/rest.py", line 264, in PUT
return cls.IMPL.PUT(*n, **kw)
File "/home/xubuntu/env/local/lib/python2.7/site-packages/dropbox/rest.py", line 210, in PUT
return self.request("PUT", url, body=body, headers=headers, raw_response=raw_response)
File "/home/xubuntu/env/local/lib/python2.7/site-packages/dropbox/rest.py", line 180, in request
r = conn.getresponse()
File "/usr/lib/python2.7/httplib.py", line 1034, in getresponse
response.begin()
File "/usr/lib/python2.7/httplib.py", line 407, in begin
version, status, reason = self._read_status()
File "/usr/lib/python2.7/httplib.py", line 371, in _read_status
raise BadStatusLine(line)
BadStatusLine: ''
self.data is a file like object ( http://docs.python.org/2/library/io.html#io.BytesIO )
Tested on :
linux, python 2.7.3, pip install dropbox [https://www.dropbox.com/developers/core/sdks/python]
any ideas?
from twisted.internet.protocol import Protocol,Factory
from twisted.internet import reactor
class ChatServer(Protocol):
def connectionMade(self):
print "A Client Has Connected"
self.factory.clients.append(self)
print"clients are ",self.factory.clients
self.transport.write('Hello,Welcome to the telnet chat to sign in type aim:YOUR NAME HERE to send a messsage type msg:YOURMESSAGE '+'\n')
def connectionLost(self,reason):
self.factory.clients.remove(self)
self.transport.write('Somebody was disconnected from the server')
def dataReceived(self,data):
#print "data is",data
a = data.split(':')
if len(a) > 1:
command = a[0]
content = a[1]
msg=""
if command =="iam":
self.name + "has joined"
elif command == "msg":
ma=sg = self.name + ":" +content
print msg
for c in self.factory.clients:
c.message(msg)
def message(self,message):
self.transport.write(message + '\n')
factory = Factory()
factory.protocol = ChatServer
factory.clients = []
reactor.listenTCP(80,factory)
print "Iphone Chat server started"
reactor.run()
The above code is running succesfully...but when i connect the client (by typing telnet localhost 80) to this chatserver and try to write message ,connection gets lost and following errors occurs :
Iphone Chat server started
A Client Has Connected
clients are [<__main__.ChatServer instance at 0x024AC0A8>]
Unhandled Error
Traceback (most recent call last):
File "C:\Python27\lib\site-packages\twisted\python\log.py", line 84, in callWithLogger
return callWithContext({"system": lp}, func, *args, **kw)
File "C:\Python27\lib\site-packages\twisted\python\log.py", line 69, in callWithContext
return context.call({ILogContext: newCtx}, func, *args, **kw)
File "C:\Python27\lib\site-packages\twisted\python\context.py", line 118, in callWithContext
return self.currentContext().callWithContext(ctx, func, *args, **kw)
File "C:\Python27\lib\site-packages\twisted\python\context.py", line 81, in callWithContext
return func(*args,**kw)
--- ---
File "C:\Python27\lib\site-packages\twisted\internet\selectreactor.py", line 150, in _doReadOrWrite
why = getattr(selectable, method)()
File "C:\Python27\lib\site-packages\twisted\internet\tcp.py", line 199, in doRead
rval = self.protocol.dataReceived(data)
File "D:\chatserverultimate.py", line 21, in dataReceived
content = a[1]
exceptions.IndexError: list index out of range
Where am I going wrong?
You indented content = a[1] line incorrectly. You need more space(s)! :)