2013-02-25 61 views
2

我正在運行massconnect.py模塊以模擬打開許多並行web套接字連接,但是當我嘗試在一段時間後打開15000個連接(在massconnect json中指定)時,出現以下錯誤消息:Massconnect丟失屬性套接字

Unhandled Error 
Traceback (most recent call last): 
    File "C:\Python27\lib\site-packages\twisted\python\log.py", line 88, in callWithLogger 
    return callWithContext({"system": lp}, func, *args, **kw) 
    File "C:\Python27\lib\site-packages\twisted\python\log.py", line 73, 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) 
--- <exception caught here> --- 
    File "C:\Python27\lib\site-packages\twisted\internet\iocpreactor\reactor.py", line 120, in _callEventCallback 
    evt.callback(rc, bytes, evt) 
    File "C:\Python27\lib\site-packages\twisted\internet\iocpreactor\tcp.py", line 285, in cbConnect 
    self.socket.setsockopt(
exceptions.AttributeError: 'Client' object has no attribute 'socket' 

網絡套接字連接的打開被中斷,我得到這個異常。

我改編了我的massconnect.py模塊以確認應用程序的網絡套接字身份驗證。我正在測試,以便每次分配一個客戶端時,它都會發送一個唯一的身份驗證消息。

我已經在註冊表中將MaxUserPort設置爲65534.我認爲這個問題可能會導致內存不足,但是在用不同的機器檢查後,我意識到這不是原因。

這可能是一個已知的蟒蛇/扭曲的問題?

@Glyph:

這裏是massconnect.py源碼:

''' 
Created on Jan 29, 2013 

@author: boro.petrovic 
''' 
############################################################################### 
## 
## Copyright 2011,2012 Tavendo GmbH 
## 
## Licensed under the Apache License, Version 2.0 (the "License"); 
## you may not use this file except in compliance with the License. 
## You may obtain a copy of the License at 
## 
##  http://www.apache.org/licenses/LICENSE-2.0 
## 
## Unless required by applicable law or agreed to in writing, software 
## distributed under the License is distributed on an "AS IS" BASIS, 
## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
## See the License for the specific language governing permissions and 
## limitations under the License. 
## 
############################################################################### 

import sys 
import time 
from twisted.internet import reactor 
from twisted.internet import error 
from twisted.internet.defer import Deferred, returnValue, inlineCallbacks 
from twisted.internet.interfaces import IReactorTime 
from autobahn.websocket import connectWS 
from autobahn.websocket import WebSocketClientFactory, WebSocketClientProtocol 
import time 

f='start' 

class MassConnectProtocol(WebSocketClientProtocol): 

    def sendHello(self, message): 
     #self.sendMessage("Hello from Python!") 
     self.sendMessage(payload=message) 
     #reactor.callLater(2, self.sendHello(message='test')) 

    def onOpen(self): 
     global f 
     wstoken = f.readline().rstrip() 
     message = 'messagecontent'+wstoken 
     self.factory.test.onConnected() 
     self.sendHello(message) 
     self.wstoken = wstoken 

    def onMessage(self, msg, binary): 
     print "Got message from wstoken " + self.wstoken + " :" + msg 

class MassConnectFactory(WebSocketClientFactory): 

    def clientConnectionFailed(self, connector, reason): 
     if self.test.onFailed(): 
      reactor.callLater(float(self.retrydelay)/1000., connector.connect) 

    def clientConnectionLost(self, connector, reason): 
     if self.test.onLost(): 
      reactor.callLater(float(self.retrydelay)/1000., connector.connect) 

class MassConnect: 

    def __init__(self, name, uri, connections, batchsize, batchdelay, retrydelay): 
     self.name = name 
     self.uri = uri 
     self.batchsize = batchsize 
     self.batchdelay = batchdelay 
     self.retrydelay = retrydelay 
     self.failed = 0 
     self.lost = 0 
     self.targetCnt = connections 
     self.currentCnt = 0 
     self.actual = 0 

    def run(self): 
     self.d = Deferred() 
     self.started = time.clock() 
     self.connectBunch() 
     return self.d 

    def onFailed(self): 
     self.failed += 1 
     return True 

    def onLost(self): 
     self.lost += 1 
     return True 

    def onConnected(self): 
     #sprint "connect" 
     self.actual += 1 
     if self.actual % self.batchsize == 0: 
      sys.stdout.write(".") 
     if self.actual == self.targetCnt: 
      self.ended = time.clock() 
      duration = self.ended - self.started 
      print " connected %d clients to %s at %s in %s seconds (retries %d = failed %d + lost %d)" % (self.currentCnt, self.name, self.uri, duration, self.failed + self.lost, self.failed, self.lost) 
      try: 
       reactor.run() 
      except twisted.internet.error.ReactorAlreadyRunning: 
       pass 

      result = {'name': self.name, 
        'uri': self.uri, 
        'connections': self.targetCnt, 
        'retries': self.failed + self.lost, 
        'lost': self.lost, 
        'failed': self.failed, 
        'duration': duration} 
      self.d.callback(result) 

    def connectBunch(self): 

     if self.currentCnt + self.batchsize < self.targetCnt: 
      c = self.batchsize 
      redo = True 
     else: 
      c = self.targetCnt - self.currentCnt 
      redo = False 
     for i in xrange(0, c): 
      factory = MassConnectFactory(self.uri, origin=None, protocols=[("myprotocol")]) 
      factory.test = self 
      factory.retrydelay = self.retrydelay 
      factory.protocol = MassConnectProtocol 
      factory.setProtocolOptions(version=13) 
      factory.setSessionParameters(url="myurl", origin=None, protocols=["myprotocol"]) 
      connectWS(factory) 
      self.currentCnt += 1 
     if redo: 
      reactor.callLater(float(self.batchdelay)/1000., self.connectBunch) 

class MassConnectTest: 

    def __init__(self, spec): 
     global f 
     f = open("C:/tokens.txt", "r") 
     self.spec = spec 

    @inlineCallbacks 
    def run(self): 
     global f 
     res = [] 
     for s in self.spec['servers']: 
      t = MassConnect(s['name'], 
          s['uri'], 
          self.spec['options']['connections'], 
          self.spec['options']['batchsize'], 
          self.spec['options']['batchdelay'], 
          self.spec['options']['retrydelay']) 
      r = yield t.run() 
      res.append(r) 
     returnValue(res) 
     f.close() 

在腳本我替換虛設串機密數據。

從token.txt文件我正在閱讀身份驗證令牌每個15000用戶我通過網絡套接字連接到測試下的應用程序。 這樣我模擬許多不同用戶的連接,併爲他們每個人我有主動獨立的網絡套接字連接。

不幸的是,我沒有達到建立所有15000個連接的程度,因爲在運行腳本時(連接)我得到了未處理的錯誤消息。

+0

請包含'massconnect.py'的來源。 – Glyph 2013-02-25 23:01:12

+0

@Glyph,我很抱歉打擾你,但你想看看我的[問題](http://stackoverflow.com/questions/33318976/how-to-use-massconnect-py-properly)? – maciekm 2015-10-25 13:23:05

回答

0

如果您將massconnect.py減少到SSCCE將是有幫助的。但是,如果問題僅在數千個併發連接級別出現,則可能是文件描述符用完了(對於此問題,Twisted的錯誤消息並不好)。

有關在操作系統中更改此參數的一些信息,請參閱this question