提交 c5007017 编写于 作者: D Daniel P. Berrange

Add domain event for metadata changes

When changing the metadata via virDomainSetMetadata, we now
emit an event to notify the app of changes. This is useful
when co-ordinating different applications read/write of
custom metadata.
Signed-off-by: NDaniel P. Berrange <berrange@redhat.com>
上级 f1e48297
......@@ -1223,6 +1223,50 @@ remoteRelayDomainEventDeviceRemovalFailed(virConnectPtr conn,
}
static int
remoteRelayDomainEventMetadataChange(virConnectPtr conn,
virDomainPtr dom,
int type,
const char *nsuri,
void *opaque)
{
daemonClientEventCallbackPtr callback = opaque;
remote_domain_event_callback_metadata_change_msg data;
char **nsurip;
if (callback->callbackID < 0 ||
!remoteRelayDomainEventCheckACL(callback->client, conn, dom))
return -1;
VIR_DEBUG("Relaying domain metadata change %s %d %d %s, callback %d",
dom->name, dom->id, type, NULLSTR(nsuri), callback->callbackID);
/* build return data */
memset(&data, 0, sizeof(data));
data.type = type;
if (nsuri) {
if (VIR_ALLOC(nsurip) < 0)
return -1;
if (VIR_STRDUP(*nsurip, nsuri) < 0) {
VIR_FREE(nsurip);
return -1;
}
data.nsuri = nsurip;
}
make_nonnull_domain(&data.dom, dom);
data.callbackID = callback->callbackID;
remoteDispatchObjectEventSend(callback->client, remoteProgram,
REMOTE_PROC_DOMAIN_EVENT_CALLBACK_METADATA_CHANGE,
(xdrproc_t)xdr_remote_domain_event_callback_metadata_change_msg,
&data);
return 0;
}
static virConnectDomainEventGenericCallback domainEventCallbacks[] = {
VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventLifecycle),
......@@ -1248,6 +1292,7 @@ static virConnectDomainEventGenericCallback domainEventCallbacks[] = {
VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventMigrationIteration),
VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventJobCompleted),
VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventDeviceRemovalFailed),
VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventMetadataChange),
};
verify(ARRAY_CARDINALITY(domainEventCallbacks) == VIR_DOMAIN_EVENT_ID_LAST);
......
......@@ -917,6 +917,40 @@ myDomainEventDeviceRemovalFailedCallback(virConnectPtr conn ATTRIBUTE_UNUSED,
}
static const char *
metadataTypeToStr(int status)
{
switch ((virDomainMetadataType) status) {
case VIR_DOMAIN_METADATA_DESCRIPTION:
return "description";
case VIR_DOMAIN_METADATA_TITLE:
return "title";
case VIR_DOMAIN_METADATA_ELEMENT:
return "element";
case VIR_DOMAIN_METADATA_LAST:
break;
}
return "unknown";
}
static int
myDomainEventMetadataChangeCallback(virConnectPtr conn ATTRIBUTE_UNUSED,
virDomainPtr dom,
int type,
const char *nsuri,
void *opaque ATTRIBUTE_UNUSED)
{
const char *typestr = metadataTypeToStr(type);
printf("%s EVENT: Domain %s(%d) metadata type: %s (%s)\n",
__func__, virDomainGetName(dom), virDomainGetID(dom), typestr, nsuri ? nsuri : "n/a");
return 0;
}
static void
myFreeFunc(void *opaque)
......@@ -971,6 +1005,7 @@ struct domainEventData domainEvents[] = {
DOMAIN_EVENT(VIR_DOMAIN_EVENT_ID_MIGRATION_ITERATION, myDomainEventMigrationIterationCallback),
DOMAIN_EVENT(VIR_DOMAIN_EVENT_ID_JOB_COMPLETED, myDomainEventJobCompletedCallback),
DOMAIN_EVENT(VIR_DOMAIN_EVENT_ID_DEVICE_REMOVAL_FAILED, myDomainEventDeviceRemovalFailedCallback),
DOMAIN_EVENT(VIR_DOMAIN_EVENT_ID_METADATA_CHANGE, myDomainEventMetadataChangeCallback),
};
struct storagePoolEventData {
......
......@@ -3770,6 +3770,25 @@ typedef void (*virConnectDomainEventDeviceRemovalFailedCallback)(virConnectPtr c
const char *devAlias,
void *opaque);
/**
* virConnectDomainEventMetadataChangeCallback:
* @conn: connection object
* @dom: domain on which the event occurred
* @type: a value from virDomainMetadataTypea
* @nsuri: XML namespace URI
* @opaque: application specified data
*
* This callback is triggered when the domain XML metadata is changed
*
* The callback signature to use when registering for an event of type
* VIR_DOMAIN_EVENT_ID_METADATA_CHANGE with virConnectDomainEventRegisterAny().
*/
typedef void (*virConnectDomainEventMetadataChangeCallback)(virConnectPtr conn,
virDomainPtr dom,
int type,
const char *nsuri,
void *opaque);
/**
* virConnectDomainEventMigrationIterationCallback:
......@@ -4195,6 +4214,7 @@ typedef enum {
VIR_DOMAIN_EVENT_ID_MIGRATION_ITERATION = 20, /* virConnectDomainEventMigrationIterationCallback */
VIR_DOMAIN_EVENT_ID_JOB_COMPLETED = 21, /* virConnectDomainEventJobCompletedCallback */
VIR_DOMAIN_EVENT_ID_DEVICE_REMOVAL_FAILED = 22, /* virConnectDomainEventDeviceRemovalFailedCallback */
VIR_DOMAIN_EVENT_ID_METADATA_CHANGE = 23, /* virConnectDomainEventMetadataChangeCallback */
# ifdef VIR_ENUM_SENTINELS
VIR_DOMAIN_EVENT_ID_LAST
......
......@@ -1124,6 +1124,13 @@ bhyveDomainSetMetadata(virDomainPtr dom,
privconn->xmlopt, BHYVE_STATE_DIR,
BHYVE_CONFIG_DIR, flags);
if (ret == 0) {
virObjectEventPtr ev = NULL;
ev = virDomainEventMetadataChangeNewFromObj(vm, type, uri);
virObjectEventStateQueue(privconn->domainEventState, ev);
}
cleanup:
virObjectUnref(caps);
virObjectUnlock(vm);
......
......@@ -59,6 +59,7 @@ static virClassPtr virDomainEventDeviceAddedClass;
static virClassPtr virDomainEventMigrationIterationClass;
static virClassPtr virDomainEventJobCompletedClass;
static virClassPtr virDomainEventDeviceRemovalFailedClass;
static virClassPtr virDomainEventMetadataChangeClass;
static void virDomainEventDispose(void *obj);
static void virDomainEventLifecycleDispose(void *obj);
......@@ -79,6 +80,7 @@ static void virDomainEventDeviceAddedDispose(void *obj);
static void virDomainEventMigrationIterationDispose(void *obj);
static void virDomainEventJobCompletedDispose(void *obj);
static void virDomainEventDeviceRemovalFailedDispose(void *obj);
static void virDomainEventMetadataChangeDispose(void *obj);
static void
virDomainEventDispatchDefaultFunc(virConnectPtr conn,
......@@ -266,6 +268,15 @@ struct _virDomainEventDeviceRemovalFailed {
typedef struct _virDomainEventDeviceRemovalFailed virDomainEventDeviceRemovalFailed;
typedef virDomainEventDeviceRemovalFailed *virDomainEventDeviceRemovalFailedPtr;
struct _virDomainEventMetadataCange {
virDomainEvent parent;
int type;
char *nsuri;
};
typedef struct _virDomainEventMetadataCange virDomainEventMetadataChange;
typedef virDomainEventMetadataChange *virDomainEventMetadataChangePtr;
static int
......@@ -385,6 +396,12 @@ virDomainEventsOnceInit(void)
sizeof(virDomainEventDeviceRemovalFailed),
virDomainEventDeviceRemovalFailedDispose)))
return -1;
if (!(virDomainEventMetadataChangeClass =
virClassNew(virDomainEventClass,
"virDomainEventMetadataChange",
sizeof(virDomainEventMetadataChange),
virDomainEventMetadataChangeDispose)))
return -1;
return 0;
}
......@@ -573,6 +590,16 @@ virDomainEventJobCompletedDispose(void *obj)
}
static void
virDomainEventMetadataChangeDispose(void *obj)
{
virDomainEventMetadataChangePtr event = obj;
VIR_DEBUG("obj=%p", event);
VIR_FREE(event->nsuri);
}
static void *
virDomainEventNew(virClassPtr klass,
int eventID,
......@@ -1600,6 +1627,53 @@ virDomainEventTunableNewFromDom(virDomainPtr dom,
}
static virObjectEventPtr
virDomainEventMetadataChangeNew(int id,
const char *name,
unsigned char *uuid,
int type,
const char *nsuri)
{
virDomainEventMetadataChangePtr ev;
if (virDomainEventsInitialize() < 0)
return NULL;
if (!(ev = virDomainEventNew(virDomainEventMetadataChangeClass,
VIR_DOMAIN_EVENT_ID_METADATA_CHANGE,
id, name, uuid)))
return NULL;
ev->type = type;
if (nsuri && VIR_STRDUP(ev->nsuri, nsuri) < 0)
goto error;
return (virObjectEventPtr)ev;
error:
virObjectUnref(ev);
return NULL;
}
virObjectEventPtr
virDomainEventMetadataChangeNewFromObj(virDomainObjPtr obj,
int type,
const char *nsuri)
{
return virDomainEventMetadataChangeNew(obj->def->id, obj->def->name,
obj->def->uuid, type, nsuri);
}
virObjectEventPtr
virDomainEventMetadataChangeNewFromDom(virDomainPtr dom,
int type,
const char *nsuri)
{
return virDomainEventMetadataChangeNew(dom->id, dom->name, dom->uuid,
type, nsuri);
}
static void
virDomainEventDispatchDefaultFunc(virConnectPtr conn,
virObjectEventPtr event,
......@@ -1857,6 +1931,18 @@ virDomainEventDispatchDefaultFunc(virConnectPtr conn,
goto cleanup;
}
case VIR_DOMAIN_EVENT_ID_METADATA_CHANGE:
{
virDomainEventMetadataChangePtr metadataChangeEvent;
metadataChangeEvent = (virDomainEventMetadataChangePtr)event;
((virConnectDomainEventMetadataChangeCallback)cb)(conn, dom,
metadataChangeEvent->type,
metadataChangeEvent->nsuri,
cbopaque);
goto cleanup;
}
case VIR_DOMAIN_EVENT_ID_LAST:
break;
}
......
......@@ -234,6 +234,16 @@ virDomainEventJobCompletedNewFromDom(virDomainPtr dom,
virTypedParameterPtr params,
int nparams);
virObjectEventPtr
virDomainEventMetadataChangeNewFromObj(virDomainObjPtr obj,
int type,
const char *nsuri);
virObjectEventPtr
virDomainEventMetadataChangeNewFromDom(virDomainPtr dom,
int type,
const char *nsuri);
int
virDomainEventStateRegister(virConnectPtr conn,
virObjectEventStatePtr state,
......
......@@ -558,6 +558,8 @@ virDomainEventLifecycleNew;
virDomainEventLifecycleNewFromDef;
virDomainEventLifecycleNewFromDom;
virDomainEventLifecycleNewFromObj;
virDomainEventMetadataChangeNewFromDom;
virDomainEventMetadataChangeNewFromObj;
virDomainEventMigrationIterationNewFromDom;
virDomainEventMigrationIterationNewFromObj;
virDomainEventPMSuspendDiskNewFromDom;
......
......@@ -5379,6 +5379,12 @@ lxcDomainSetMetadata(virDomainPtr dom,
driver->xmlopt, cfg->stateDir,
cfg->configDir, flags);
if (ret == 0) {
virObjectEventPtr ev = NULL;
ev = virDomainEventMetadataChangeNewFromObj(vm, type, uri);
virObjectEventStateQueue(driver->domainEventState, ev);
}
virLXCDomainObjEndJob(driver, vm);
cleanup:
......
......@@ -18072,6 +18072,12 @@ qemuDomainSetMetadata(virDomainPtr dom,
driver->xmlopt, cfg->stateDir,
cfg->configDir, flags);
if (ret == 0) {
virObjectEventPtr ev = NULL;
ev = virDomainEventMetadataChangeNewFromObj(vm, type, uri);
qemuDomainEventQueue(driver, ev);
}
qemuDomainObjEndJob(driver, vm);
cleanup:
......
......@@ -354,6 +354,11 @@ remoteDomainBuildEventCallbackJobCompleted(virNetClientProgramPtr prog,
virNetClientPtr client,
void *evdata, void *opaque);
static void
remoteDomainBuildEventCallbackMetadataChange(virNetClientProgramPtr prog,
virNetClientPtr client,
void *evdata, void *opaque);
static void
remoteNetworkBuildEventLifecycle(virNetClientProgramPtr prog ATTRIBUTE_UNUSED,
virNetClientPtr client ATTRIBUTE_UNUSED,
......@@ -558,6 +563,10 @@ static virNetClientProgramEvent remoteEvents[] = {
remoteDomainBuildEventCallbackDeviceRemovalFailed,
sizeof(remote_domain_event_callback_device_removal_failed_msg),
(xdrproc_t)xdr_remote_domain_event_callback_device_removal_failed_msg },
{ REMOTE_PROC_DOMAIN_EVENT_CALLBACK_METADATA_CHANGE,
remoteDomainBuildEventCallbackMetadataChange,
sizeof(remote_domain_event_callback_metadata_change_msg),
(xdrproc_t)xdr_remote_domain_event_callback_metadata_change_msg },
{ REMOTE_PROC_STORAGE_POOL_EVENT_LIFECYCLE,
remoteStoragePoolBuildEventLifecycle,
sizeof(remote_storage_pool_event_lifecycle_msg),
......@@ -5248,6 +5257,28 @@ remoteDomainBuildEventCallbackJobCompleted(virNetClientProgramPtr prog ATTRIBUTE
}
static void
remoteDomainBuildEventCallbackMetadataChange(virNetClientProgramPtr prog ATTRIBUTE_UNUSED,
virNetClientPtr client ATTRIBUTE_UNUSED,
void *evdata, void *opaque)
{
virConnectPtr conn = opaque;
remote_domain_event_callback_metadata_change_msg *msg = evdata;
struct private_data *priv = conn->privateData;
virDomainPtr dom;
virObjectEventPtr event = NULL;
if (!(dom = get_nonnull_domain(conn, msg->dom)))
return;
event = virDomainEventMetadataChangeNewFromDom(dom, msg->type, msg->nsuri ? *msg->nsuri : NULL);
virObjectUnref(dom);
remoteEventQueue(priv, event, msg->callbackID);
}
static void
remoteNetworkBuildEventLifecycle(virNetClientProgramPtr prog ATTRIBUTE_UNUSED,
virNetClientPtr client ATTRIBUTE_UNUSED,
......
......@@ -3353,6 +3353,13 @@ struct remote_domain_set_guest_vcpus_args {
};
struct remote_domain_event_callback_metadata_change_msg {
int callbackID;
remote_nonnull_domain dom;
int type;
remote_string nsuri;
};
/*----- Protocol. -----*/
/* Define the program number, protocol version and procedure numbers here. */
......@@ -5952,5 +5959,11 @@ enum remote_procedure {
* @priority: high
* @acl: storage_vol:read
*/
REMOTE_PROC_STORAGE_VOL_GET_INFO_FLAGS = 378
REMOTE_PROC_STORAGE_VOL_GET_INFO_FLAGS = 378,
/**
* @generate: both
* @acl: none
*/
REMOTE_PROC_DOMAIN_EVENT_CALLBACK_METADATA_CHANGE = 379
};
......@@ -2800,6 +2800,12 @@ struct remote_domain_set_guest_vcpus_args {
int state;
u_int flags;
};
struct remote_domain_event_callback_metadata_change_msg {
int callbackID;
remote_nonnull_domain dom;
int type;
remote_string nsuri
};
enum remote_procedure {
REMOTE_PROC_CONNECT_OPEN = 1,
REMOTE_PROC_CONNECT_CLOSE = 2,
......@@ -3179,4 +3185,5 @@ enum remote_procedure {
REMOTE_PROC_NODE_DEVICE_EVENT_LIFECYCLE = 376,
REMOTE_PROC_NODE_DEVICE_EVENT_UPDATE = 377,
REMOTE_PROC_STORAGE_VOL_GET_INFO_FLAGS = 378,
REMOTE_PROC_DOMAIN_EVENT_CALLBACK_METADATA_CHANGE = 379,
};
......@@ -2721,6 +2721,12 @@ static int testDomainSetMetadata(virDomainPtr dom,
privconn->caps, privconn->xmlopt,
NULL, NULL, flags);
if (ret == 0) {
virObjectEventPtr ev = NULL;
ev = virDomainEventMetadataChangeNewFromObj(privdom, type, uri);
testObjectEventQueue(privconn, ev);
}
virDomainObjEndAPI(&privdom);
return ret;
}
......
......@@ -12750,6 +12750,29 @@ virshEventDeviceRemovalFailedPrint(virConnectPtr conn ATTRIBUTE_UNUSED,
virshEventPrint(opaque, &buf);
}
VIR_ENUM_DECL(virshEventMetadataChangeType)
VIR_ENUM_IMPL(virshEventMetadataChangeType,
VIR_DOMAIN_METADATA_LAST,
N_("description"),
N_("title"),
N_("element"))
static void
virshEventMetadataChangePrint(virConnectPtr conn ATTRIBUTE_UNUSED,
virDomainPtr dom,
int type,
const char *nsuri,
void *opaque)
{
virBuffer buf = VIR_BUFFER_INITIALIZER;
virBufferAsprintf(&buf, _("event 'metdata-change' for domain %s: %s %s\n"),
virDomainGetName(dom),
UNKNOWNSTR(virshEventMetadataChangeTypeTypeToString(type)),
NULLSTR(nsuri));
virshEventPrint(opaque, &buf);
}
static vshEventCallback vshEventCallbacks[] = {
{ "lifecycle",
......@@ -12796,6 +12819,8 @@ static vshEventCallback vshEventCallbacks[] = {
VIR_DOMAIN_EVENT_CALLBACK(virshEventJobCompletedPrint), },
{ "device-removal-failed",
VIR_DOMAIN_EVENT_CALLBACK(virshEventDeviceRemovalFailedPrint), },
{ "metadata-change",
VIR_DOMAIN_EVENT_CALLBACK(virshEventMetadataChangePrint), },
};
verify(VIR_DOMAIN_EVENT_ID_LAST == ARRAY_CARDINALITY(vshEventCallbacks));
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册