This library implements xml-rpc client and server functionality using Drakma, CXML and Hunchentoot.
Get it via git:
git clone http://github.com/antifuchs/cxml-rpc
Then adjust your ASDF to find cxml-rpc.asd. After that,
(asdf:oos 'asdf:load-op :cxml-rpc)
Acting as an XML-RPC client is pretty easy: Just call the functions on the endpoints you need. The function's first return value is the value returned by the server, and the second return value is its type.
* (xrpc:call "http://betty.userland.com/RPC2" "examples.getStateName" '(:integer 41))
"South Dakota"
:STRING
Since the mapping of CL types to XML-RPC types is not easily DWIM-able, you need to pass args with explicit type hints. CXML-RPC maps these types (as keywords):
:boolean
- generalized boolean:integer
- 4-octet integers:double
- floating-point doubles:string
- strings:time
- universal times as CL integers:base64
- strings, file streams or vectors containing (unsigned-byte 8) elements.:struct
- alists:array
- sequencesYou can run multiple XML RPC handlers in your hunchentoot instance: These are identified by a handler tag that you can choose. This tag is not exposed to the outside world, so you can run multiple sites (or endpoints) with a different set of xml-rpc methods in the same lisp image.
(push
(hunchentoot:create-prefix-dispatcher "/RPC2"
(cxml:cxml-rpc-method-handler 'some-tag))
hunchentoot:*dispatch-table*)
This tells hunchentoot to dispatch xml-rpc calls on /RPC2 to dispatch xml-rpc methods. This handler will serve only methods that are defined with the group tag some-tag.
Define-xrpc-method is what you use to create a function that can be called from xml-rpc. Its arguments are:
CXML-RPC allows introspection via the system.getCapabilities, system.listMethods, system.methodHelp, and system.methodSignature.
(define-xrpc-method (add some-tag) (a b) (:integer :integer :integer)
"Add two numbers"
(+ a b))