This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: multiprocess fails to re-raise exception which has mandatory arguments
Type: behavior Stage:
Components: Interpreter Core Versions: Python 2.7
process
Status: closed Resolution: duplicate
Dependencies: Superseder: Cannot unpickle classes derived from 'Exception'
View: 17296
Assigned To: Nosy List: Bala.FA, sbt
Priority: normal Keywords:

Created on 2012-07-24 15:17 by Bala.FA, last changed 2022-04-11 14:57 by admin. This issue is now closed.

Messages (2)
msg166299 - (view) Author: Bala FA (Bala.FA) Date: 2012-07-24 15:17
I use multiprocess in one of my project.  When an exception which
requires mandatory argument is raised by a server process, is not
re-raised properly to client process.  I get an error something like
below

Traceback (most recent call last):
  File "prod.py", line 69, in <module>
    main()
  File "prod.py", line 61, in main
    print myobj.fun3()
  File "<string>", line 2, in fun3
  File "/usr/lib64/python2.7/multiprocessing/managers.py", line 759,
in _callmethod
    kind, result = conn.recv()
TypeError: ('__init__() takes exactly 2 arguments (1 given)', <class
'__main__.MyException2'>, ())

However, if an exception which has optional argument is raised by
server process, is re-raised properly to client process.

Below is a reproducer.

#!/usr/bin/python

import sys
import os
import time
import subprocess
from multiprocessing.managers import BaseManager

class MyManager(BaseManager):
    pass

class MyException1(Exception):
    def __init__(self, msg=''):
        self.msg = msg

    def __str__(self):
        return self.msg

class MyException2(Exception):
    def __init__(self, msg):
        self.msg = msg

    def __str__(self):
        return self.msg

class MyClass(object):
    def fun1(self):
        return 'this is fun1'

    def fun2(self):
        raise MyException1('fun2 raised')

    def fun3(self):
        raise MyException2('fun3 raised')

def runManager():
    manager = MyManager(address=('', 50000), authkey='abc')
    manager.register('instance', callable=MyClass)
    server = manager.get_server()
    print "manager is running"
    server.serve_forever()

def startManager():
    p = subprocess.Popen(['python', __file__, 'manager'])
    time.sleep(1)
    return p

def main():
    p = startManager()
    manager = MyManager(address=('', 50000), authkey='abc')
    manager.register('instance')
    print "connecting to manager"
    manager.connect()
    myobj = manager.instance()
    print myobj.fun1()
    try:
        print myobj.fun2()
    except MyException1, e:
        print e
    try:
        print myobj.fun3()
    except MyException2, e:
        print e
    finally:
        p.kill()

if __name__ == '__main__':
    if len(sys.argv) == 1:
        main()
    else:
        runManager()

I use python 2.7.3 on fedora 17 on x86_64 (rpm version is
python-2.7.3-6.fc17.x86_64)
msg202615 - (view) Author: Richard Oudkerk (sbt) * (Python committer) Date: 2013-11-11 11:39
This was fixed for 3.3 in #1692335.

The issue of backporting to 2.7 is discussed in #17296.
History
Date User Action Args
2022-04-11 14:57:33adminsetgithub: 59645
2013-11-11 11:39:25sbtsetstatus: open -> closed
superseder: Cannot unpickle classes derived from 'Exception'
messages: + msg202615

type: crash -> behavior
resolution: duplicate
2013-10-14 14:20:57georg.brandlsetnosy: + sbt
2012-07-24 15:17:51Bala.FAcreate