I've tried to communicate with the guest agent on a qemu instance through the libvirt golang API. However, it always reject my connections with
2022-12-02T00:10:43.799+0100 DPANIC test/main.go:335 Failed to connect to guest {"error": "virError(Code=86, Domain=10, Message='Guest agent is not responding: QEMU guest agent is not connected')"}
Even if the qemu instance is fully booted and the guest agent is available through the commandline
sudo virsh qemu-agent-command test-vm '{"execute":"guest-info"}'
Is this a bug in the implementation or do I have to register the agent somewhere in the go code? I wasn't able to find references in the documentation.
<channel type='unix'>
<source mode='bind' path='/var/lib/libvirt/qemu/channel/target/domain-6-test-vm/org.qemu.guest_agent.0'/>
<target type='virtio' name='org.qemu.guest_agent.0' state='connected'/>
<alias name='channel0'/>
<address type='virtio-serial' controller='0' bus='0' port='1'/>
</channel>
Thanks!
Not sure what was the cause in the end. I had a loop and was accessing, or to be more specific try to access, the agent. I changed it to use a timeout of 500ms and not it works.
type qemuStatusResponse struct {
Return struct {
Exitcode int `json:"exitcode,omitempty"`
OutData string `json:"out-data,omitempty"`
Exited bool `json:"exited,omitempty"`
ErrData string `json:"err-data,omitempty"`
} `json:"return,omitempty"`
}
func (l *LibvirtInstance) waitForCompletion(ctx context.Context, pid int, domain *libvirt.Domain) (response *qemuStatusResponse, err error) {
response = &qemuStatusResponse{}
ticker := time.NewTicker(500 * time.Millisecond)
defer ticker.Stop()
for {
select {
case <-ticker.C:
result, err := domain.QemuAgentCommand(
fmt.Sprintf(`
{
"execute": "guest-exec-status",
"arguments": {
"pid": %d
}
}`, pid),
libvirt.DOMAIN_QEMU_AGENT_COMMAND_BLOCK, 0)
if err != nil {
return nil, err
}
if err := json.Unmarshal([]byte(result), response); err != nil {
return nil, err
}
if response.Return.Exited {
return response, nil
}
case <-ctx.Done():
return nil, ctx.Err()
}
}
}
Furhtermore I had some stability issues (i.e., when executing multiple concurrent requests to the connection it was sometimes broken). I found some article in the web suggesting adding the user to the kvm
group. This worked for me.