mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2024-12-23 21:34:54 +03:00
virsh: Introduce pool-event command
Similar to 'event' and 'net-event', this prints info about incoming storage pool events.
This commit is contained in:
parent
8bab1e7c05
commit
eac167e261
@ -32,6 +32,7 @@
|
||||
#include "virfile.h"
|
||||
#include "conf/storage_conf.h"
|
||||
#include "virstring.h"
|
||||
#include "virtime.h"
|
||||
|
||||
#define VIRSH_COMMON_OPT_POOL_FULL \
|
||||
VIRSH_COMMON_OPT_POOL(N_("pool name or uuid")) \
|
||||
@ -1889,6 +1890,183 @@ cmdPoolEdit(vshControl *ctl, const vshCmd *cmd)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* "pool-event" command
|
||||
*/
|
||||
VIR_ENUM_DECL(virshPoolEvent)
|
||||
VIR_ENUM_IMPL(virshPoolEvent,
|
||||
VIR_STORAGE_POOL_EVENT_LAST,
|
||||
N_("Defined"),
|
||||
N_("Undefined"),
|
||||
N_("Started"),
|
||||
N_("Stopped"),
|
||||
N_("Refreshed"))
|
||||
|
||||
static const char *
|
||||
virshPoolEventToString(int event)
|
||||
{
|
||||
const char *str = virshPoolEventTypeToString(event);
|
||||
return str ? _(str) : _("unknown");
|
||||
}
|
||||
|
||||
struct virshPoolEventData {
|
||||
vshControl *ctl;
|
||||
bool loop;
|
||||
bool timestamp;
|
||||
int count;
|
||||
};
|
||||
typedef struct virshPoolEventData virshPoolEventData;
|
||||
|
||||
VIR_ENUM_DECL(virshPoolEventId)
|
||||
VIR_ENUM_IMPL(virshPoolEventId,
|
||||
VIR_STORAGE_POOL_EVENT_ID_LAST,
|
||||
"lifecycle")
|
||||
|
||||
static void
|
||||
vshEventLifecyclePrint(virConnectPtr conn ATTRIBUTE_UNUSED,
|
||||
virStoragePoolPtr pool,
|
||||
int event,
|
||||
int detail ATTRIBUTE_UNUSED,
|
||||
void *opaque)
|
||||
{
|
||||
virshPoolEventData *data = opaque;
|
||||
|
||||
if (!data->loop && data->count)
|
||||
return;
|
||||
|
||||
if (data->timestamp) {
|
||||
char timestamp[VIR_TIME_STRING_BUFLEN];
|
||||
|
||||
if (virTimeStringNowRaw(timestamp) < 0)
|
||||
timestamp[0] = '\0';
|
||||
|
||||
vshPrint(data->ctl, _("%s: event 'lifecycle' for storage pool %s: %s\n"),
|
||||
timestamp,
|
||||
virStoragePoolGetName(pool),
|
||||
virshPoolEventToString(event));
|
||||
} else {
|
||||
vshPrint(data->ctl, _("event 'lifecycle' for storage pool %s: %s\n"),
|
||||
virStoragePoolGetName(pool),
|
||||
virshPoolEventToString(event));
|
||||
}
|
||||
|
||||
data->count++;
|
||||
if (!data->loop)
|
||||
vshEventDone(data->ctl);
|
||||
}
|
||||
|
||||
static const vshCmdInfo info_pool_event[] = {
|
||||
{.name = "help",
|
||||
.data = N_("Storage Pool Events")
|
||||
},
|
||||
{.name = "desc",
|
||||
.data = N_("List event types, or wait for storage pool events to occur")
|
||||
},
|
||||
{.name = NULL}
|
||||
};
|
||||
|
||||
static const vshCmdOptDef opts_pool_event[] = {
|
||||
{.name = "pool",
|
||||
.type = VSH_OT_STRING,
|
||||
.help = N_("filter by storage pool name or uuid")
|
||||
},
|
||||
{.name = "event",
|
||||
.type = VSH_OT_STRING,
|
||||
.help = N_("which event type to wait for")
|
||||
},
|
||||
{.name = "loop",
|
||||
.type = VSH_OT_BOOL,
|
||||
.help = N_("loop until timeout or interrupt, rather than one-shot")
|
||||
},
|
||||
{.name = "timeout",
|
||||
.type = VSH_OT_INT,
|
||||
.help = N_("timeout seconds")
|
||||
},
|
||||
{.name = "list",
|
||||
.type = VSH_OT_BOOL,
|
||||
.help = N_("list valid event types")
|
||||
},
|
||||
{.name = "timestamp",
|
||||
.type = VSH_OT_BOOL,
|
||||
.help = N_("show timestamp for each printed event")
|
||||
},
|
||||
{.name = NULL}
|
||||
};
|
||||
|
||||
static bool
|
||||
cmdPoolEvent(vshControl *ctl, const vshCmd *cmd)
|
||||
{
|
||||
virStoragePoolPtr pool = NULL;
|
||||
bool ret = false;
|
||||
int eventId = -1;
|
||||
int timeout = 0;
|
||||
virshPoolEventData data;
|
||||
const char *eventName = NULL;
|
||||
int event;
|
||||
virshControlPtr priv = ctl->privData;
|
||||
|
||||
if (vshCommandOptBool(cmd, "list")) {
|
||||
size_t i;
|
||||
|
||||
for (i = 0; i < VIR_STORAGE_POOL_EVENT_ID_LAST; i++)
|
||||
vshPrint(ctl, "%s\n", virshPoolEventIdTypeToString(i));
|
||||
return true;
|
||||
}
|
||||
|
||||
if (vshCommandOptStringReq(ctl, cmd, "event", &eventName) < 0)
|
||||
return false;
|
||||
if (!eventName) {
|
||||
vshError(ctl, "%s", _("either --list or event type is required"));
|
||||
return false;
|
||||
}
|
||||
if ((event = virshPoolEventIdTypeFromString(eventName)) < 0) {
|
||||
vshError(ctl, _("unknown event type %s"), eventName);
|
||||
return false;
|
||||
}
|
||||
|
||||
data.ctl = ctl;
|
||||
data.loop = vshCommandOptBool(cmd, "loop");
|
||||
data.timestamp = vshCommandOptBool(cmd, "timestamp");
|
||||
data.count = 0;
|
||||
if (vshCommandOptTimeoutToMs(ctl, cmd, &timeout) < 0)
|
||||
return false;
|
||||
|
||||
if (vshCommandOptBool(cmd, "pool"))
|
||||
pool = virshCommandOptPool(ctl, cmd, "pool", NULL);
|
||||
if (vshEventStart(ctl, timeout) < 0)
|
||||
goto cleanup;
|
||||
|
||||
if ((eventId = virConnectStoragePoolEventRegisterAny(priv->conn, pool, event,
|
||||
VIR_STORAGE_POOL_EVENT_CALLBACK(vshEventLifecyclePrint),
|
||||
&data, NULL)) < 0)
|
||||
goto cleanup;
|
||||
switch (vshEventWait(ctl)) {
|
||||
case VSH_EVENT_INTERRUPT:
|
||||
vshPrint(ctl, "%s", _("event loop interrupted\n"));
|
||||
break;
|
||||
case VSH_EVENT_TIMEOUT:
|
||||
vshPrint(ctl, "%s", _("event loop timed out\n"));
|
||||
break;
|
||||
case VSH_EVENT_DONE:
|
||||
break;
|
||||
default:
|
||||
goto cleanup;
|
||||
}
|
||||
vshPrint(ctl, _("events received: %d\n"), data.count);
|
||||
if (data.count)
|
||||
ret = true;
|
||||
|
||||
cleanup:
|
||||
vshEventCleanup(ctl);
|
||||
if (eventId >= 0 &&
|
||||
virConnectStoragePoolEventDeregisterAny(priv->conn, eventId) < 0)
|
||||
ret = false;
|
||||
if (pool)
|
||||
virStoragePoolFree(pool);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
const vshCmdDef storagePoolCmds[] = {
|
||||
{.name = "find-storage-pool-sources-as",
|
||||
.handler = cmdPoolDiscoverSourcesAs,
|
||||
@ -2004,5 +2182,11 @@ const vshCmdDef storagePoolCmds[] = {
|
||||
.info = info_pool_uuid,
|
||||
.flags = 0
|
||||
},
|
||||
{.name = "pool-event",
|
||||
.handler = cmdPoolEvent,
|
||||
.opts = opts_pool_event,
|
||||
.info = info_pool_event,
|
||||
.flags = 0
|
||||
},
|
||||
{.name = NULL}
|
||||
};
|
||||
|
@ -3466,6 +3466,24 @@ Undefine the configuration for an inactive I<pool>.
|
||||
|
||||
Returns the UUID of the named I<pool>.
|
||||
|
||||
=item B<pool-event> {[I<pool>] I<event> [I<--loop>] [I<--timeout>
|
||||
I<seconds>] [I<--timestamp>] | I<--list>}
|
||||
|
||||
Wait for a class of storage pool events to occur, and print appropriate
|
||||
details of events as they happen. The events can optionally be filtered
|
||||
by I<pool>. Using I<--list> as the only argument will provide a list
|
||||
of possible I<event> values known by this client, although the connection
|
||||
might not allow registering for all these events.
|
||||
|
||||
By default, this command is one-shot, and returns success once an event
|
||||
occurs; you can send SIGINT (usually via C<Ctrl-C>) to quit immediately.
|
||||
If I<--timeout> is specified, the command gives up waiting for events
|
||||
after I<seconds> have elapsed. With I<--loop>, the command prints all
|
||||
events until a timeout or interrupt key.
|
||||
|
||||
When I<--timestamp> is used, a human-readable timestamp will be printed
|
||||
before the event.
|
||||
|
||||
=back
|
||||
|
||||
=head1 VOLUME COMMANDS
|
||||
|
Loading…
Reference in New Issue
Block a user