Closed graugans closed 10 months ago
Hi @graugans, I haven't seen a case like this but i think it should be possible to implement. I'll take a look at this
This little guy behaves like this: https://www.ifm.com/us/en/product/O3D200 In case you have an idea or example, how this could be handled I can try it by myself.
Do you have an example of how the payload looks like on the wire? XML-RPC should only have one parameter in the response.
An XML-RPC response can only contain one parameter, despite the use of the enclosing params element. That parameter, may, of course, be an array or a struct, so it is possible to return multiple values.
However what im trying to understand - does it respond with a struct + flexible amount of fields OR does it respond with multiple parameters directly?
I will try to grab some communication examples tomorrow I guess this will provide more details.
I've given it a quick stab based on the scarce information i have right now. You can give 0.5.0-RC1 a try when you have a moment, i will make a proper release if this works or after some fixes.
Sorry for the delay, this was a busy day. A successful call captured in Wireshark looks like this:
POST /RPC1/ HTTP/1.1
Host: 10.121.123.14:8080
Accept-Encoding: gzip
Content-Type: text/xml
User-Agent: Python-xmlrpc/3.12
Content-Length: 109
<?xml version='1.0'?>
<methodCall>
<methodName>MDAXMLConnectCP</methodName>
<params>
</params>
</methodCall>
HTTP/1.1 200 OK
Server: XMLRPC++ 0.7
Content-Type: text/xml
Content-length: 222
<?xml version="1.0" encoding="UTF-8"?>
<methodResponse><params><param>
<value><array><data><value><i4>0</i4></value><value>4099</value><value>O3D217AC</value></data></array></value>
</param></params></methodResponse>
When the device returns an error it looks like this:
POST /RPC1/ HTTP/1.1
Host: 10.121.123.14:8080
Accept-Encoding: gzip
Content-Type: text/xml
User-Agent: Python-xmlrpc/3.12
Content-Length: 109
<?xml version='1.0'?>
<methodCall>
<methodName>MDAXMLConnectCP</methodName>
<params>
</params>
</methodCall>
HTTP/1.1 200 OK
Server: XMLRPC++ 0.7
Content-Type: text/xml
Content-length: 183
<?xml version="1.0" encoding="UTF-8"?>
<methodResponse><params><param>
<value><array><data><value><i4>-102</i4></value></data></array></value>
</param></params></methodResponse>
I have captured this with a small Python example.
I hopefully find some time on Thursday to give your branch a try
Okay so your response contains a single array value, so that should just work by specifying that your response is expected to be an array. This would not require any modifications.
type MyResponse struct {
Response []any
}
However I've noticed that your system does NOT wrap all values in data types. First parameter is correctly wrapped into
Today the library will return nil on them... I will look into changing implementation to have the flag that would default unknown types to string (or attempt at least) but that will likely come at certain tradeoffs.. Will get back to you on this.
Yeah, the device is not behaving in an optimal way. Anyway according to the specification here: http://xmlrpc.com/spec.md the default is string
If no type is indicated, the type is string.
Thats a good catch! then I don't need an extra flag for that. I will adjust the behavior, as this is clearly then a bug on my side.
This should be resolved in v0.4.1. You can check the test-case i added with your data sample (slightly modified) for example how to do the data mapping for this type of responses.
Sorry for the late feedback, with https://github.com/alexejk/go-xmlrpc/releases/tag/v0.4.1 and the any
type Array it works like a charm. Thanks for your support and great library.
First of all thank you very much for your great work. I have an weird XML-RPC server implementation which does response with a different amount of values in case of an internal error occurred, hence the message
Is there an option to omit the struct value in case it is empty? Maybe something like this:
In case of a successful operation the returned data from the device is
{0,"4711","AA"}
and in case of an error only{-100}
is returned.