fix backwards compatibility in xmlrpc_wrappers.inc
[plcapi.git] / lib / xmlrpc_wrappers.inc
1 <?php
2
3 /******************************************************************************
4  *
5  * *** DEPRECATED ***
6  *
7  * This file is only used to insure backwards compatibility
8  * with the API of the library <= rev. 3
9  *****************************************************************************/
10
11 include_once(__DIR__.'/../src/Wrapper.php');
12
13 /* Expose as global functions the ones which are now class methods */
14
15 /**
16  * @see PhpXmlRpc\Wrapper::php_2_xmlrpc_type
17  * @param string $phpType
18  * @return string
19  */
20 function php_2_xmlrpc_type($phpType)
21 {
22     $wrapper = new PhpXmlRpc\Wrapper();
23     return $wrapper->php2XmlrpcType($phpType);
24 }
25
26 /**
27  * @see PhpXmlRpc\Wrapper::xmlrpc_2_php_type
28  * @param string $xmlrpcType
29  * @return string
30  */
31 function xmlrpc_2_php_type($xmlrpcType)
32 {
33     $wrapper = new PhpXmlRpc\Wrapper();
34     return $wrapper->xmlrpc2PhpType($xmlrpcType);
35 }
36
37 /**
38  * @see PhpXmlRpc\Wrapper::wrap_php_function
39  * @param callable $funcName
40  * @param string $newFuncName
41  * @param array $extraOptions
42  * @return array|false
43  */
44 function wrap_php_function($funcName, $newFuncName='', $extraOptions=array())
45 {
46     $wrapper = new PhpXmlRpc\Wrapper();
47     if (!isset($extraOptions['return_source'])  || $extraOptions['return_source'] == false) {
48         // backwards compat: return string instead of callable
49         $extraOptions['return_source'] = true;
50         $wrapped = $wrapper->wrapPhpFunction($funcName, $newFuncName, $extraOptions);
51         eval($wrapped['source']);
52     } else {
53         $wrapped = $wrapper->wrapPhpFunction($funcName, $newFuncName, $extraOptions);
54     }
55     return $wrapped;
56 }
57
58 /**
59  * NB: this function returns an array in a format which is unsuitable for direct use in the server dispatch map, unlike
60  * PhpXmlRpc\Wrapper::wrapPhpClass. This behaviour might seem like a bug, but has been kept for backwards compatibility.
61  *
62  * @see PhpXmlRpc\Wrapper::wrap_php_class
63  * @param string|object $className
64  * @param array $extraOptions
65  * @return array|false
66  */
67 function wrap_php_class($className, $extraOptions=array())
68 {
69     $wrapper = new PhpXmlRpc\Wrapper();
70     $fix = false;
71     if (!isset($extraOptions['return_source'])  || $extraOptions['return_source'] == false) {
72         // backwards compat: return string instead of callable
73         $extraOptions['return_source'] = true;
74         $fix = true;
75     }
76     $wrapped = $wrapper->wrapPhpClass($className, $extraOptions);
77     foreach($wrapped as $name => $value) {
78         if ($fix) {
79             eval($value['source']);
80         }
81         $wrapped[$name] = $value['function'];
82     }
83     return $wrapped;
84 }
85
86 /**
87  * @see PhpXmlRpc\Wrapper::wrapXmlrpcMethod
88  * @param xmlrpc_client $client
89  * @param string $methodName
90  * @param int|array $extraOptions the usage of an int as signature number is deprecated, use an option in $extraOptions
91  * @param int $timeout            deprecated, use an option in $extraOptions
92  * @param string $protocol        deprecated, use an option in $extraOptions
93  * @param string $newFuncName     deprecated, use an option in $extraOptions
94  * @return array|callable|false
95  */
96 function wrap_xmlrpc_method($client, $methodName, $extraOptions=0, $timeout=0, $protocol='', $newFuncName='')
97 {
98     if (!is_array($extraOptions))
99     {
100         $sigNum = $extraOptions;
101         $extraOptions = array(
102             'signum' => $sigNum,
103             'timeout' => $timeout,
104             'protocol' => $protocol,
105             'new_function_name' => $newFuncName
106         );
107     }
108
109     $wrapper = new PhpXmlRpc\Wrapper();
110
111     if (!isset($extraOptions['return_source'])  || $extraOptions['return_source'] == false) {
112         // backwards compat: return string instead of callable
113         $extraOptions['return_source'] = true;
114         $wrapped = $wrapper->wrapXmlrpcMethod($client, $methodName, $extraOptions);
115         eval($wrapped['source']);
116         $wrapped = $wrapped['function'];
117     } else {
118         $wrapped = $wrapper->wrapXmlrpcMethod($client, $methodName, $extraOptions);
119     }
120     return $wrapped;
121 }
122
123 /**
124  * @see PhpXmlRpc\Wrapper::wrap_xmlrpc_server
125  * @param xmlrpc_client $client
126  * @param array $extraOptions
127  * @return mixed
128  */
129 function wrap_xmlrpc_server($client, $extraOptions=array())
130 {
131     $wrapper = new PhpXmlRpc\Wrapper();
132     return $wrapper->wrapXmlrpcServer($client, $extraOptions);
133 }
134
135 /**
136  * Given the necessary info, build php code that creates a new function to invoke a remote xmlrpc method.
137  * Take care that no full checking of input parameters is done to ensure that valid php code is emitted.
138  * Only kept for backwards compatibility
139  * Note: real spaghetti code follows...
140  *
141  * @deprecated
142  */
143 function build_remote_method_wrapper_code($client, $methodName, $xmlrpcFuncName,
144      $mSig, $mDesc = '', $timeout = 0, $protocol = '', $clientCopyMode = 0, $prefix = 'xmlrpc',
145      $decodePhpObjects = false, $encodePhpObjects = false, $decodeFault = false,
146      $faultResponse = '', $namespace = '\\PhpXmlRpc\\')
147 {
148     $code = "function $xmlrpcFuncName (";
149     if ($clientCopyMode < 2) {
150         // client copy mode 0 or 1 == partial / full client copy in emitted code
151         $innerCode = build_client_wrapper_code($client, $clientCopyMode, $prefix, $namespace);
152         $innerCode .= "\$client->setDebug(\$debug);\n";
153         $this_ = '';
154     } else {
155         // client copy mode 2 == no client copy in emitted code
156         $innerCode = '';
157         $this_ = 'this->';
158     }
159     $innerCode .= "\$req = new {$namespace}Request('$methodName');\n";
160
161     if ($mDesc != '') {
162         // take care that PHP comment is not terminated unwillingly by method description
163         $mDesc = "/**\n* " . str_replace('*/', '* /', $mDesc) . "\n";
164     } else {
165         $mDesc = "/**\nFunction $xmlrpcFuncName\n";
166     }
167
168     // param parsing
169     $innerCode .= "\$encoder = new {$namespace}Encoder();\n";
170     $plist = array();
171     $pCount = count($mSig);
172     for ($i = 1; $i < $pCount; $i++) {
173         $plist[] = "\$p$i";
174         $pType = $mSig[$i];
175         if ($pType == 'i4' || $pType == 'int' || $pType == 'boolean' || $pType == 'double' ||
176             $pType == 'string' || $pType == 'dateTime.iso8601' || $pType == 'base64' || $pType == 'null'
177         ) {
178             // only build directly xmlrpc values when type is known and scalar
179             $innerCode .= "\$p$i = new {$namespace}Value(\$p$i, '$pType');\n";
180         } else {
181             if ($encodePhpObjects) {
182                 $innerCode .= "\$p$i = \$encoder->encode(\$p$i, array('encode_php_objs'));\n";
183             } else {
184                 $innerCode .= "\$p$i = \$encoder->encode(\$p$i);\n";
185             }
186         }
187         $innerCode .= "\$req->addparam(\$p$i);\n";
188         $mDesc .= '* @param ' . xmlrpc_2_php_type($pType) . " \$p$i\n";
189     }
190     if ($clientCopyMode < 2) {
191         $plist[] = '$debug=0';
192         $mDesc .= "* @param int \$debug when 1 (or 2) will enable debugging of the underlying {$prefix} call (defaults to 0)\n";
193     }
194     $plist = implode(', ', $plist);
195     $mDesc .= '* @return ' . xmlrpc_2_php_type($mSig[0]) . " (or an {$namespace}Response obj instance if call fails)\n*/\n";
196
197     $innerCode .= "\$res = \${$this_}client->send(\$req, $timeout, '$protocol');\n";
198     if ($decodeFault) {
199         if (is_string($faultResponse) && ((strpos($faultResponse, '%faultCode%') !== false) || (strpos($faultResponse, '%faultString%') !== false))) {
200             $respCode = "str_replace(array('%faultCode%', '%faultString%'), array(\$res->faultCode(), \$res->faultString()), '" . str_replace("'", "''", $faultResponse) . "')";
201         } else {
202             $respCode = var_export($faultResponse, true);
203         }
204     } else {
205         $respCode = '$res';
206     }
207     if ($decodePhpObjects) {
208         $innerCode .= "if (\$res->faultcode()) return $respCode; else return \$encoder->decode(\$res->value(), array('decode_php_objs'));";
209     } else {
210         $innerCode .= "if (\$res->faultcode()) return $respCode; else return \$encoder->decode(\$res->value());";
211     }
212
213     $code = $code . $plist . ") {\n" . $innerCode . "\n}\n";
214
215     return array('source' => $code, 'docstring' => $mDesc);
216 }
217
218 /**
219  * @deprecated
220  */
221 function build_client_wrapper_code($client, $verbatim_client_copy, $prefix='xmlrpc')
222 {
223     $code = "\$client = new {$prefix}_client('".str_replace("'", "\'", $client->path).
224         "', '" . str_replace("'", "\'", $client->server) . "', $client->port);\n";
225
226     // copy all client fields to the client that will be generated runtime
227     // (this provides for future expansion or subclassing of client obj)
228     if ($verbatim_client_copy)
229     {
230         foreach($client as $fld => $val)
231         {
232             if($fld != 'debug' && $fld != 'return_type')
233             {
234                 $val = var_export($val, true);
235                 $code .= "\$client->$fld = $val;\n";
236             }
237         }
238     }
239     // only make sure that client always returns the correct data type
240     $code .= "\$client->return_type = '{$prefix}vals';\n";
241     //$code .= "\$client->setDebug(\$debug);\n";
242     return $code;
243 }