2016-06-07 61 views
0

我們需要建立一個軟件讀取XML文件數千進口其內容爲使用的SQLAlchemy SQLite數據庫。多處理和SQLAlchemy的錯誤

請找我們的代碼的相關部分如下:

文件1:

from multiprocessing.dummy import Pool as ThreadPool 
... 
for file in os.listdir(path): 
    if file.endswith("-endpoint.xml"): 
     xmls.append([self.database, os.path.join(path, file), self.debug]) 

pool = ThreadPool(threads) 
try: 
    def multi_run_wrapper(args): 
     return collectors.import_asset(*args) 

    results = pool.map(multi_run_wrapper, xmls) 
    pool.close() 
    pool.join() 
except: 
    if self.debug: 
     traceback.print_exc(file=sys.stdout) 

文件2,第1部分:

def import_asset(db, xml, debug = False): 
    tree = ET.parse(xml) 
    root = tree.getroot() 
    signcheck = root.find('Signcheck') 
    usersArray = [] 
    running_processes = [] 
    autoruns = [] 

    machine_id = add_machine(root, xml, db, debug) 

文件2,部分2:

def add_machine(root, file_path, db, debug = False): 
    ... 
    machine = Machine(hostname=hostname, operating_system=operating_system, version=Version) 
    db.add(machine) 
    db.commit() 

文件3:

在整個代碼, 'DB' 是任何該函數的返回值是:

def open(sqlite_db_path = None): 
    engine = create_engine('sqlite:///' + sqlite_db_path) 
    session = sessionmaker() 
    session.configure(bind=engine) 
    return scoped_session(session()) 

錯誤消息:

TypeError: 'Session' object is not callable 

我們已經閱讀here scoped_session()不返回一個真正的Session()對象。但是我們還沒有能夠使用這些信息來修復我們的代碼。

預先感謝您爲您的這個障礙實物援助。

+0

爲什麼你會調用'scoped_session(會話())'?而不是像scoped_session(session)那樣傳遞對象?顯然,錯誤說,使用sessionmaker()創建的會話對象不可調用。 –

+0

'scoped_session(sessionmaker(綁定=發動機))',路過sessionmaker創建的會話工廠是代替由工廠(呼叫)創建的'Session'的。 –

回答

3

您打電話給會話工廠session,此時應該調用scoped_session(請參閱Contextual/Thread-local Sessions)。

所以應該

scoped_session(session)() 

,而不是

scoped_session(session()) 

爲了避免混淆,我會建議重新命名sessionsession_factory。所以,這樣的事情應該工作:

def open(sqlite_db_path = None): 
    engine = create_engine('sqlite:///' + sqlite_db_path) 
    session_factory = sessionmaker(bind=engine) 
    return scoped_session(session_factory)() 
2

這樣做的修復只是替換此:

def open(sqlite_db_path = None): 
    engine = create_engine('sqlite:///' + sqlite_db_path) 
    session = sessionmaker() 
    session.configure(bind=engine) 
    return scoped_session(session()) 

有了這個:

engine = create_engine('sqlite:///' + sqlite_db_path) 
session_factory = sessionmaker(bind=engine) 
return scoped_session(session_factory) 

感謝所有迴應此人線。