Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
D
drupal
Manage
Activity
Members
Labels
Plan
Wiki
Custom issue tracker
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Locked files
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Model registry
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Code review analytics
Insights
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Terms and privacy
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
project
drupal
Commits
03dd2f9c
Commit
03dd2f9c
authored
18 years ago
by
Dries Buytaert
Browse files
Options
Downloads
Patches
Plain Diff
- Patch
#66154
by jvandyck: XML-RPC fixes and documentation improvements.
parent
7bacdb43
No related branches found
Branches containing commit
No related tags found
Tags containing commit
2 merge requests
!7452
Issue #1797438. HTML5 validation is preventing form submit and not fully...
,
!789
Issue #3210310: Adjust Database API to remove deprecated Drupal 9 code in Drupal 10
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
includes/xmlrpcs.inc
+143
-116
143 additions, 116 deletions
includes/xmlrpcs.inc
with
143 additions
and
116 deletions
includes/xmlrpcs.inc
+
143
−
116
View file @
03dd2f9c
<?php
<?php
// $Id$
// $Id$
/**
* The main entry point for XML-RPC requests.
*
* @param $callbacks
* Array of external XML-RPC method names with the callbacks they map to.
*/
function
xmlrpc_server
(
$callbacks
)
{
function
xmlrpc_server
(
$callbacks
)
{
$xmlrpc_server
=
new
stdClass
();
$xmlrpc_server
=
new
stdClass
();
// Define built-in XML-RPC method names
$defaults
=
array
(
$defaults
=
array
(
'system.multicall'
=>
'xmlrpc_server_multicall'
,
'system.multicall'
=>
'xmlrpc_server_multicall'
,
array
(
array
(
'system.methodSignature'
,
'system.methodSignature'
,
'xmlrpc_server_method_signature'
,
'xmlrpc_server_method_signature'
,
array
(
'array'
,
'string'
),
array
(
'array'
,
'string'
),
'Returns an array describing the return type and required parameters of a method'
'Returns an array describing the return type and required parameters of a method
.
'
),
),
array
(
array
(
'system.getCapabilities'
,
'system.getCapabilities'
,
'xmlrpc_server_get_capabilities'
,
'xmlrpc_server_get_capabilities'
,
array
(
'struct'
),
array
(
'struct'
),
'Returns a struct describing the XML-RPC specifications supported by this server'
'Returns a struct describing the XML-RPC specifications supported by this server
.
'
),
),
array
(
array
(
'system.listMethods'
,
'system.listMethods'
,
'xmlrpc_server_list_methods'
,
'xmlrpc_server_list_methods'
,
array
(
'array'
),
array
(
'array'
),
'Returns an array of available methods on this server'
),
'Returns an array of available methods on this server
.
'
),
array
(
array
(
'system.methodHelp'
,
'system.methodHelp'
,
'xmlrpc_server_method_help'
,
'xmlrpc_server_method_help'
,
array
(
'string'
,
'string'
),
array
(
'string'
,
'string'
),
'Returns a documentation string for the specified method'
)
'Returns a documentation string for the specified method
.
'
)
);
);
// the order matters in the next line. which is the best?
// We build an array of all method names by combining the built-ins
// with those defined by modules implementing the _xmlrpc hook.
// Built-in methods are overridable.
foreach
(
array_merge
(
$defaults
,
(
array
)
$callbacks
)
as
$key
=>
$callback
)
{
foreach
(
array_merge
(
$defaults
,
(
array
)
$callbacks
)
as
$key
=>
$callback
)
{
// we could check for is_array($callback)
// we could check for is_array($callback)
if
(
is_int
(
$key
))
{
if
(
is_int
(
$key
))
{
...
@@ -50,14 +59,14 @@ function xmlrpc_server($callbacks) {
...
@@ -50,14 +59,14 @@ function xmlrpc_server($callbacks) {
}
}
$xmlrpc_server
->
message
=
xmlrpc_message
(
$data
);
$xmlrpc_server
->
message
=
xmlrpc_message
(
$data
);
if
(
!
xmlrpc_message_parse
(
$xmlrpc_server
->
message
))
{
if
(
!
xmlrpc_message_parse
(
$xmlrpc_server
->
message
))
{
xmlrpc_server_error
(
-
32700
,
t
(
'
p
arse error. not well formed'
));
xmlrpc_server_error
(
-
32700
,
t
(
'
P
arse error.
Request
not well formed
.
'
));
}
}
if
(
$xmlrpc_server
->
message
->
messagetype
!=
'methodCall'
)
{
if
(
$xmlrpc_server
->
message
->
messagetype
!=
'methodCall'
)
{
xmlrpc_server_error
(
-
32600
,
t
(
'
s
erver error.
i
nvalid
xml-rpc. not conforming to spec
. Request must be a method
_c
all'
));
xmlrpc_server_error
(
-
32600
,
t
(
'
S
erver error.
I
nvalid
XML-RPC
. Request must be a method
C
all
.
'
));
}
}
xmlrpc_server_set
(
$xmlrpc_server
);
xmlrpc_server_set
(
$xmlrpc_server
);
$result
=
xmlrpc_server_call
(
$xmlrpc_server
,
$xmlrpc_server
->
message
->
methodname
,
$xmlrpc_server
->
message
->
params
);
$result
=
xmlrpc_server_call
(
$xmlrpc_server
,
$xmlrpc_server
->
message
->
methodname
,
$xmlrpc_server
->
message
->
params
);
// Is the result an error?
if
(
$result
->
is_error
)
{
if
(
$result
->
is_error
)
{
xmlrpc_server_error
(
$result
);
xmlrpc_server_error
(
$result
);
}
}
...
@@ -80,8 +89,15 @@ function xmlrpc_server($callbacks) {
...
@@ -80,8 +89,15 @@ function xmlrpc_server($callbacks) {
xmlrpc_server_output
(
$xml
);
xmlrpc_server_output
(
$xml
);
}
}
/**
* Throw an XML-RPC error.
*
* @param $error
* an error object OR integer error code
* @param $message
* description of error, used only if integer error code was passed
*/
function
xmlrpc_server_error
(
$error
,
$message
=
false
)
{
function
xmlrpc_server_error
(
$error
,
$message
=
false
)
{
// Accepts either an error object or an error code and message
if
(
$message
&&
!
is_object
(
$error
))
{
if
(
$message
&&
!
is_object
(
$error
))
{
$error
=
xmlrpc_error
(
$error
,
$message
);
$error
=
xmlrpc_error
(
$error
,
$message
);
}
}
...
@@ -98,11 +114,12 @@ function xmlrpc_server_output($xml) {
...
@@ -98,11 +114,12 @@ function xmlrpc_server_output($xml) {
exit
;
exit
;
}
}
function
xmlrpc_server_list_methods
()
{
/**
$xmlrpc_server
=
xmlrpc_server_get
();
* Store a copy of the request temporarily.
return
array_keys
(
$xmlrpc_server
->
callbacks
);
*
}
* @param $xmlrpc_server
* Request object created by xmlrpc_server().
*/
function
xmlrpc_server_set
(
$xmlrpc_server
=
NULL
)
{
function
xmlrpc_server_set
(
$xmlrpc_server
=
NULL
)
{
static
$server
;
static
$server
;
if
(
!
isset
(
$server
))
{
if
(
!
isset
(
$server
))
{
...
@@ -111,77 +128,39 @@ function xmlrpc_server_set($xmlrpc_server = NULL) {
...
@@ -111,77 +128,39 @@ function xmlrpc_server_set($xmlrpc_server = NULL) {
return
$server
;
return
$server
;
}
}
// Retrieve the stored request.
function
xmlrpc_server_get
()
{
function
xmlrpc_server_get
()
{
return
xmlrpc_server_set
();
return
xmlrpc_server_set
();
}
}
function
xmlrpc_server_multicall
(
$methodcalls
)
{
/**
// See http://www.xmlrpc.com/discuss/msgReader$1208
* Dispatch the request and any parameters to the appropriate handler.
$return
=
array
();
*
$xmlrpc_server
=
xmlrpc_server_get
();
* @param $xmlrpc_server
foreach
(
$methodcalls
as
$call
)
{
* @param $methodname
$method
=
$call
[
'methodName'
];
* The external XML-RPC method name, e.g. 'system.methodHelp'
$params
=
$call
[
'params'
];
* @param $args
if
(
$method
==
'system.multicall'
)
{
* Array containing any parameters that were sent along with the request.
$result
=
xmlrpc_error
(
-
32600
,
t
(
'Recursive calls to system.multicall are forbidden'
));
*/
}
else
{
$result
=
xmlrpc_server_call
(
$xmlrpc_server
,
$method
,
$params
);
}
if
(
$result
->
is_error
)
{
$return
[]
=
array
(
'faultCode'
=>
$result
->
code
,
'faultString'
=>
$result
->
message
);
}
else
{
$return
[]
=
$result
;
}
}
return
$return
;
}
function
xmlrpc_server_get_capabilities
()
{
return
array
(
'xmlrpc'
=>
array
(
'specUrl'
=>
'http://www.xmlrpc.com/spec'
,
'specVersion'
=>
1
),
'faults_interop'
=>
array
(
'specUrl'
=>
'http://xmlrpc-epi.sourceforge.net/specs/rfc.fault_codes.php'
,
'specVersion'
=>
20010516
),
'system.multicall'
=>
array
(
'specUrl'
=>
'http://www.xmlrpc.com/discuss/msgReader$1208'
,
'specVersion'
=>
1
),
'introspection'
=>
array
(
'specUrl'
=>
'http://xmlrpc.usefulinc.com/doc/reserved.html'
,
'specVersion'
=>
1
)
);
}
function
xmlrpc_server_call
(
$xmlrpc_server
,
$methodname
,
$args
)
{
function
xmlrpc_server_call
(
$xmlrpc_server
,
$methodname
,
$args
)
{
// Make sure
it's
in an array
// Make sure
parameters are
in an array
if
(
$args
&&
!
is_array
(
$args
))
{
if
(
$args
&&
!
is_array
(
$args
))
{
$args
=
array
(
$args
);
$args
=
array
(
$args
);
}
}
//
Over-rides default call method, adds signature check
//
Has this method been mapped to a Drupal function by us or by modules?
if
(
!
isset
(
$xmlrpc_server
->
callbacks
[
$methodname
]))
{
if
(
!
isset
(
$xmlrpc_server
->
callbacks
[
$methodname
]))
{
return
xmlrpc_error
(
-
32601
,
t
(
'
s
erver error.
r
equested method %methodname not specified.'
,
array
(
"%methodname"
=>
$xmlrpc_server
->
message
->
methodname
)));
return
xmlrpc_error
(
-
32601
,
t
(
'
S
erver error.
R
equested method %methodname not specified.'
,
array
(
"%methodname"
=>
$xmlrpc_server
->
message
->
methodname
)));
}
}
$method
=
$xmlrpc_server
->
callbacks
[
$methodname
];
$method
=
$xmlrpc_server
->
callbacks
[
$methodname
];
$signature
=
$xmlrpc_server
->
signatures
[
$methodname
];
$signature
=
$xmlrpc_server
->
signatures
[
$methodname
];
$ok
=
true
;
// If the method has a signature, validate the request against the signature
if
(
is_array
(
$signature
))
{
if
(
is_array
(
$signature
))
{
$ok
=
true
;
$return_type
=
array_shift
(
$signature
);
$return_type
=
array_shift
(
$signature
);
// Check the number of arguments
// Check the number of arguments
if
(
count
(
$args
)
!=
count
(
$signature
))
{
if
(
count
(
$args
)
!=
count
(
$signature
))
{
return
xmlrpc_error
(
-
32602
,
t
(
'
s
erver error.
w
rong number of method parameters'
));
return
xmlrpc_error
(
-
32602
,
t
(
'
S
erver error.
W
rong number of method parameters
.
'
));
}
}
// Check the argument types
// Check the argument types
foreach
(
$signature
as
$key
=>
$type
)
{
foreach
(
$signature
as
$key
=>
$type
)
{
...
@@ -218,74 +197,122 @@ function xmlrpc_server_call($xmlrpc_server, $methodname, $args) {
...
@@ -218,74 +197,122 @@ function xmlrpc_server_call($xmlrpc_server, $methodname, $args) {
break
;
break
;
}
}
if
(
!
$ok
)
{
if
(
!
$ok
)
{
return
xmlrpc_error
(
-
32602
,
t
(
'
s
erver error.
i
nvalid method parameters'
));
return
xmlrpc_error
(
-
32602
,
t
(
'
S
erver error.
I
nvalid method parameters
.
'
));
}
}
}
}
}
}
// It passed the test - run the "real" method call
/*
if
(
!
isset
(
$xmlrpc_server
->
callbacks
[
$methodname
]))
{
return
xmlrpc_error
(
-
32601
,
t
(
'server error. requested method %methodname does not exist.'
,
array
(
"%methodname"
=>
$methodname
)));
}
$method
=
$xmlrpc_server
->
callbacks
[
$methodname
];
// Perform the callback and send the response
/*
if (count($args) == 1) {
if (count($args) == 1) {
// If only one parameter just send that instead of the whole array
// If only one parameter just send that instead of the whole array
$args = $args[0];
$args = $args[0];
}
}
*/
*/
if
(
!
function_exists
(
$method
))
{
if
(
!
function_exists
(
$method
))
{
return
xmlrpc_error
(
-
32601
,
t
(
'
s
erver error.
r
equested function %method does not exist.'
,
array
(
"%method"
=>
$method
)));
return
xmlrpc_error
(
-
32601
,
t
(
'
S
erver error.
R
equested function %method does not exist.'
,
array
(
"%method"
=>
$method
)));
}
}
// Call the function
// Call the
mapped
function
return
call_user_func_array
(
$method
,
$args
);
return
call_user_func_array
(
$method
,
$args
);
}
}
function
xmlrpc_server_method_signature
(
$xmlrpc_server
,
$methodname
)
{
function
xmlrpc_server_multicall
(
$methodcalls
)
{
// See http://www.xmlrpc.com/discuss/msgReader$1208
$return
=
array
();
$xmlrpc_server
=
xmlrpc_server_get
();
foreach
(
$methodcalls
as
$call
)
{
$ok
=
true
;
if
(
!
isset
(
$call
[
'methodName'
])
||
!
isset
(
$call
[
'params'
]))
{
$result
=
xmlrpc_error
(
3
,
t
(
'Invalid syntax for system.multicall.'
));
$ok
=
false
;
}
$method
=
$call
[
'methodName'
];
$params
=
$call
[
'params'
];
if
(
$method
==
'system.multicall'
)
{
$result
=
xmlrpc_error
(
-
32600
,
t
(
'Recursive calls to system.multicall are forbidden.'
));
}
elseif
(
$ok
)
{
$result
=
xmlrpc_server_call
(
$xmlrpc_server
,
$method
,
$params
);
}
if
(
$result
->
is_error
)
{
$return
[]
=
array
(
'faultCode'
=>
$result
->
code
,
'faultString'
=>
$result
->
message
);
}
else
{
$return
[]
=
$result
;
}
}
return
$return
;
}
/**
* XML-RPC method system.listMethods maps to this function.
*/
function
xmlrpc_server_list_methods
()
{
$xmlrpc_server
=
xmlrpc_server_get
();
return
array_keys
(
$xmlrpc_server
->
callbacks
);
}
/**
* XML-RPC method system.getCapabilities maps to this function.
* See http://groups.yahoo.com/group/xml-rpc/message/2897
*/
function
xmlrpc_server_get_capabilities
()
{
return
array
(
'xmlrpc'
=>
array
(
'specUrl'
=>
'http://www.xmlrpc.com/spec'
,
'specVersion'
=>
1
),
'faults_interop'
=>
array
(
'specUrl'
=>
'http://xmlrpc-epi.sourceforge.net/specs/rfc.fault_codes.php'
,
'specVersion'
=>
20010516
),
'system.multicall'
=>
array
(
'specUrl'
=>
'http://www.xmlrpc.com/discuss/msgReader$1208'
,
'specVersion'
=>
1
),
'introspection'
=>
array
(
'specUrl'
=>
'http://scripts.incutio.com/xmlrpc/introspection.html'
,
'specVersion'
=>
1
)
);
}
/**
* XML-RPC method system.methodSignature maps to this function.
*
* @param $methodname
* Name of method for which we return a method signature.
* @return array
* An array of types representing the method signature of the
* function that the methodname maps to. The methodSignature of
* this function is 'array', 'string' because it takes an array
* and returns a string.
*/
function
xmlrpc_server_method_signature
(
$methodname
)
{
$xmlrpc_server
=
xmlrpc_server_get
();
if
(
!
isset
(
$xmlrpc_server
->
callbacks
[
$methodname
]))
{
if
(
!
isset
(
$xmlrpc_server
->
callbacks
[
$methodname
]))
{
return
xmlrpc_error
(
-
32601
,
t
(
'
s
erver error.
r
equested method %methodname not specified.'
,
array
(
"%methodname"
=>
$methodname
)));
return
xmlrpc_error
(
-
32601
,
t
(
'
S
erver error.
R
equested method %methodname not specified.'
,
array
(
"%methodname"
=>
$methodname
)));
}
}
if
(
!
is_array
(
$xmlrpc_server
->
signature
[
$methodname
]))
{
if
(
!
is_array
(
$xmlrpc_server
->
signature
s
[
$methodname
]))
{
return
xmlrpc_error
(
-
32601
,
t
(
'
s
erver error.
r
equested method %methodname signature not specified.'
,
array
(
"%methodname"
=>
$methodname
)));
return
xmlrpc_error
(
-
32601
,
t
(
'
S
erver error.
R
equested method %methodname signature not specified.'
,
array
(
"%methodname"
=>
$methodname
)));
}
}
// We
should be returning an
array of types
// We array of types
$return
=
array
();
$return
=
array
();
foreach
(
$xmlrpc_server
->
signatures
[
$methodname
]
as
$type
)
{
foreach
(
$xmlrpc_server
->
signatures
[
$methodname
]
as
$type
)
{
switch
(
$type
)
{
$return
[]
=
$type
;
case
'string'
:
$return
[]
=
'string'
;
break
;
case
'int'
:
case
'i4'
:
$return
[]
=
42
;
break
;
case
'double'
:
$return
[]
=
3.1415
;
break
;
case
'dateTime.iso8601'
:
$return
[]
=
xmlrpc_date
(
time
());
break
;
case
'boolean'
:
$return
[]
=
true
;
break
;
case
'base64'
:
$return
[]
=
xmlrpc_base64
(
'base64'
);
break
;
case
'array'
:
$return
[]
=
array
(
'array'
);
break
;
case
'struct'
:
$return
[]
=
array
(
'struct'
=>
'struct'
);
break
;
}
}
}
return
$return
;
return
$return
;
}
}
/**
* XML-RPC method system.methodHelp maps to this function.
*
* @param $method
* Name of method for which we return a help string.
*/
function
xmlrpc_server_method_help
(
$method
)
{
function
xmlrpc_server_method_help
(
$method
)
{
$xmlrpc_server
=
xmlrpc_server_get
();
$xmlrpc_server
=
xmlrpc_server_get
();
return
$xmlrpc_server
->
help
[
$method
];
return
$xmlrpc_server
->
help
[
$method
];
}
}
\ No newline at end of file
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment