48
48
# User code must use the exceptions defined in ``openerp.exceptions`` (not
49
49
# create directly ``xmlrpclib.Fault`` objects).
50
50
XML_RPC_FAULT_CODE_APPLICATION_ERROR = 1
51
+ # Unused, deferred errors are indistinguishable from normal application
52
+ # errors. We keep them so we can use the word 'indistinguishable' twice
53
+ # in the same comment.
51
54
XML_RPC_FAULT_CODE_DEFERRED_APPLICATION_ERROR = 2
52
55
XML_RPC_FAULT_CODE_ACCESS_DENIED = 3
53
56
XML_RPC_FAULT_CODE_ACCESS_ERROR = 4
54
57
XML_RPC_FAULT_CODE_WARNING = 5
55
58
56
- def xmlrpc_return (start_response , service , method , params ):
59
+ def xmlrpc_return (start_response , service , method , params , legacy_exceptions = False ):
57
60
"""
58
61
Helper to call a service's method with some params, using a wsgi-supplied
59
62
``start_response`` callback.
@@ -70,6 +73,20 @@ def xmlrpc_return(start_response, service, method, params):
70
73
try :
71
74
result = openerp .netsvc .dispatch_rpc (service , method , params )
72
75
response = xmlrpclib .dumps ((result ,), methodresponse = 1 , allow_none = False , encoding = None )
76
+ except Exception , e :
77
+ if legacy_exceptions :
78
+ response = xmlrpc_handle_exception_legacy (e )
79
+ else :
80
+ response = xmlrpc_handle_exception (e )
81
+ start_response ("200 OK" , [('Content-Type' ,'text/xml' ), ('Content-Length' , str (len (response )))])
82
+ return [response ]
83
+
84
+ def xmlrpc_handle_exception (e ):
85
+ try :
86
+ raise e
87
+ except openerp .osv .osv .except_osv , e : # legacy
88
+ fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_WARNING , openerp .tools .ustr (e .value ))
89
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
73
90
except openerp .exceptions .Warning , e :
74
91
fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_WARNING , str (e ))
75
92
response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
@@ -84,17 +101,47 @@ def xmlrpc_return(start_response, service, method, params):
84
101
# Which one is the best ?
85
102
formatted_info = "" .join (traceback .format_exception (* info ))
86
103
#formatted_info = openerp.tools.exception_to_unicode(e) + '\n' + info
87
- fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_DEFERRED_APPLICATION_ERROR , formatted_info )
104
+ fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_APPLICATION_ERROR , formatted_info )
105
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
106
+ except Exception , e :
107
+ if hasattr (e , 'message' ) and e .message == 'AccessDenied' : # legacy
108
+ fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_ACCESS_DENIED , str (e ))
109
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
110
+ else :
111
+ info = sys .exc_info ()
112
+ # Which one is the best ?
113
+ formatted_info = "" .join (traceback .format_exception (* info ))
114
+ #formatted_info = openerp.tools.exception_to_unicode(e) + '\n' + info
115
+ fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_APPLICATION_ERROR , formatted_info )
116
+ response = xmlrpclib .dumps (fault , allow_none = None , encoding = None )
117
+ return response
118
+
119
+ def xmlrpc_handle_exception_legacy (e ):
120
+ try :
121
+ raise e
122
+ except openerp .osv .osv .except_osv , e :
123
+ fault = xmlrpclib .Fault ('warning -- ' + e .name + '\n \n ' + e .value , '' )
124
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
125
+ except openerp .exceptions .Warning , e :
126
+ fault = xmlrpclib .Fault ('warning -- Warning\n \n ' + str (e ), '' )
127
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
128
+ except openerp .exceptions .AccessError , e :
129
+ fault = xmlrpclib .Fault ('warning -- AccessError\n \n ' + str (e ), '' )
130
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
131
+ except openerp .exceptions .AccessDenied , e :
132
+ fault = xmlrpclib .Fault ('AccessDenied' , str (e ))
133
+ response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
134
+ except openerp .exceptions .DeferredException , e :
135
+ info = e .traceback
136
+ formatted_info = "" .join (traceback .format_exception (* info ))
137
+ fault = xmlrpclib .Fault (openerp .tools .ustr (e .message ), formatted_info )
88
138
response = xmlrpclib .dumps (fault , allow_none = False , encoding = None )
89
139
except Exception , e :
90
140
info = sys .exc_info ()
91
- # Which one is the best ?
92
141
formatted_info = "" .join (traceback .format_exception (* info ))
93
- #formatted_info = openerp.tools.exception_to_unicode(e) + '\n' + info
94
- fault = xmlrpclib .Fault (XML_RPC_FAULT_CODE_APPLICATION_ERROR , formatted_info )
142
+ fault = xmlrpclib .Fault (openerp .tools .exception_to_unicode (e ), formatted_info )
95
143
response = xmlrpclib .dumps (fault , allow_none = None , encoding = None )
96
- start_response ("200 OK" , [('Content-Type' ,'text/xml' ), ('Content-Length' , str (len (response )))])
97
- return [response ]
144
+ return response
98
145
99
146
def wsgi_xmlrpc (environ , start_response ):
100
147
""" The main OpenERP WSGI handler."""
@@ -138,7 +185,7 @@ def legacy_wsgi_xmlrpc(environ, start_response):
138
185
path = environ ['PATH_INFO' ][len ('/xmlrpc/' ):] # expected to be one of db, object, ...
139
186
140
187
params , method = xmlrpclib .loads (data )
141
- return xmlrpc_return (start_response , path , method , params )
188
+ return xmlrpc_return (start_response , path , method , params , True )
142
189
143
190
def wsgi_jsonrpc (environ , start_response ):
144
191
pass
0 commit comments