[已解决] 使用Golang创建XML-RPC客户端
[已解决] 使用Golang创建XML-RPC客户端 你好,
我来自 Perl 世界,对 Go 语言还比较陌生。为了积累经验并熟悉相关技巧,我正尝试用 Go 重新实现一些之前用 Perl 编写的功能。
其中一个脚本是 XML-RPC 客户端(使用 Perl 的 Frontier::Client 模块)。由于 Perl 没有内置此功能,我从 Go 生态的选项中选择了 github.com/kolo/xmlrpc。
现在我在尝试身份验证时遇到了困难,相关文档较为简略,导致我无法自行解决。我需要发送用户名和密码,并期望获取会话密钥。以下是我目前的尝试:
client, _ := xmlpc.NewClient("http://localhost/rpc/api", nil)
type Credentials struct {
Username, Password string
}
var creds = Credentials{"admin","admin1"}
client.Call("auth.login", &creds, &sessionkey)
通过 tcpdump 观察,我发现用户名和密码字段是在 <struct> 标签内传输的,但这不符合服务器的预期,因此我未能获得会话密钥。
如有任何指导将不胜感激。
此致,Lordy
更多关于[已解决] 使用Golang创建XML-RPC客户端的实战教程也可以访问 https://www.itying.com/category-94-b0.html
通过查看其他使用相同模块的源代码,我自己找到了解决方案:
package client
import (
"errors"
"fmt"
log "github.com/Sirupsen/logrus"
"github.com/nilshell/xmlrpc"
)
type XenAPIClient struct {
Session interface{}
Host string
Url string
Username string
Password string
RPC *xmlrpc.Client
}
type APIResult struct {
Status string
该文件已被截断。显示完整内容
其中的Login函数满足了我的需求,我将代码修改为:
creds := make([]interface{}, 2)
creds[0] = "admin"
creds[1] = "admin1"
client.Call("auth.login", creds, &sessionkey)
现在我得到了有效的sessionkey,可以继续进行了!
更多关于[已解决] 使用Golang创建XML-RPC客户端的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
在 XML-RPC 中,auth.login 方法通常期望参数作为单独的成员(members)传递,而不是封装在一个结构体中。根据你的描述,服务器可能期望参数按顺序传递,而不是作为命名结构体字段。
以下是修改后的代码示例:
package main
import (
"fmt"
"log"
"github.com/kolo/xmlrpc"
)
func main() {
client, err := xmlrpc.NewClient("http://localhost/rpc/api", nil)
if err != nil {
log.Fatal("客户端创建失败:", err)
}
var sessionKey string
err = client.Call("auth.login", []interface{}{"admin", "admin1"}, &sessionKey)
if err != nil {
log.Fatal("调用失败:", err)
}
fmt.Printf("会话密钥: %s\n", sessionKey)
}
关键修改点:
- 使用
[]interface{}{"admin", "admin1"}作为参数,将用户名和密码作为有序参数列表传递 - 移除了自定义的
Credentials结构体 - 添加了完整的错误处理
XML-RPC 请求将生成类似这样的结构:
<methodCall>
<methodName>auth.login</methodName>
<params>
<param>
<value><string>admin</string></value>
</param>
<param>
<value><string>admin1</string></value>
</param>
</params>
</methodCall>
如果服务器需要其他参数格式,比如需要将凭据包装在结构体中但使用不同的字段名,可以这样调整:
args := struct {
Username string `xmlrpc:"username"`
Password string `xmlrpc:"password"`
}{
Username: "admin",
Password: "admin1",
}
err = client.Call("auth.login", []interface{}{args}, &sessionKey)
这会在 <struct> 中使用指定的字段名生成 XML。根据服务器的具体 API 要求选择合适的参数格式。

