mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-01-22 04:25:18 +00:00
util: qemu: Allow nested objects in JSON -> commandline generator
Move the iterator of objects to the recursive function so that nested objects are supported by flattening the structure with '.' delimiters.
This commit is contained in:
parent
25a272ada4
commit
cd86d6f465
@ -26,11 +26,49 @@
|
|||||||
#include "virerror.h"
|
#include "virerror.h"
|
||||||
#include "virlog.h"
|
#include "virlog.h"
|
||||||
#include "virqemu.h"
|
#include "virqemu.h"
|
||||||
|
#include "virstring.h"
|
||||||
|
#include "viralloc.h"
|
||||||
|
|
||||||
#define VIR_FROM_THIS VIR_FROM_NONE
|
#define VIR_FROM_THIS VIR_FROM_NONE
|
||||||
|
|
||||||
VIR_LOG_INIT("util.qemu");
|
VIR_LOG_INIT("util.qemu");
|
||||||
|
|
||||||
|
struct virQEMUCommandLineJSONIteratorData {
|
||||||
|
const char *prefix;
|
||||||
|
virBufferPtr buf;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
static int
|
||||||
|
virQEMUBuildCommandLineJSONRecurse(const char *key,
|
||||||
|
const virJSONValue *value,
|
||||||
|
virBufferPtr buf,
|
||||||
|
bool nested);
|
||||||
|
|
||||||
|
/* internal iterator to handle nested object formatting */
|
||||||
|
static int
|
||||||
|
virQEMUBuildCommandLineJSONIterate(const char *key,
|
||||||
|
const virJSONValue *value,
|
||||||
|
void *opaque)
|
||||||
|
{
|
||||||
|
struct virQEMUCommandLineJSONIteratorData *data = opaque;
|
||||||
|
char *tmpkey = NULL;
|
||||||
|
int ret = -1;
|
||||||
|
|
||||||
|
if (data->prefix) {
|
||||||
|
if (virAsprintf(&tmpkey, "%s.%s", data->prefix, key) < 0)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
ret = virQEMUBuildCommandLineJSONRecurse(tmpkey, value, data->buf, false);
|
||||||
|
|
||||||
|
VIR_FREE(tmpkey);
|
||||||
|
} else {
|
||||||
|
ret = virQEMUBuildCommandLineJSONRecurse(key, value, data->buf, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static int
|
static int
|
||||||
virQEMUBuildCommandLineJSONRecurse(const char *key,
|
virQEMUBuildCommandLineJSONRecurse(const char *key,
|
||||||
@ -38,12 +76,19 @@ virQEMUBuildCommandLineJSONRecurse(const char *key,
|
|||||||
virBufferPtr buf,
|
virBufferPtr buf,
|
||||||
bool nested)
|
bool nested)
|
||||||
{
|
{
|
||||||
|
struct virQEMUCommandLineJSONIteratorData data = { key, buf };
|
||||||
virJSONValuePtr elem;
|
virJSONValuePtr elem;
|
||||||
virBitmapPtr bitmap = NULL;
|
virBitmapPtr bitmap = NULL;
|
||||||
ssize_t pos = -1;
|
ssize_t pos = -1;
|
||||||
ssize_t end;
|
ssize_t end;
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
|
if (!key && value->type != VIR_JSON_TYPE_OBJECT) {
|
||||||
|
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
|
||||||
|
_("only JSON objects can be top level"));
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
switch ((virJSONType) value->type) {
|
switch ((virJSONType) value->type) {
|
||||||
case VIR_JSON_TYPE_STRING:
|
case VIR_JSON_TYPE_STRING:
|
||||||
virBufferAsprintf(buf, ",%s=", key);
|
virBufferAsprintf(buf, ",%s=", key);
|
||||||
@ -96,10 +141,15 @@ virQEMUBuildCommandLineJSONRecurse(const char *key,
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case VIR_JSON_TYPE_OBJECT:
|
case VIR_JSON_TYPE_OBJECT:
|
||||||
|
if (virJSONValueObjectForeachKeyValue(value,
|
||||||
|
virQEMUBuildCommandLineJSONIterate,
|
||||||
|
&data) < 0)
|
||||||
|
return -1;
|
||||||
|
break;
|
||||||
|
|
||||||
case VIR_JSON_TYPE_NULL:
|
case VIR_JSON_TYPE_NULL:
|
||||||
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
|
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
|
||||||
_("NULL and OBJECT JSON types can't be converted to "
|
_("NULL JSON type can't be converted to commandline"));
|
||||||
"commandline string"));
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -108,15 +158,6 @@ virQEMUBuildCommandLineJSONRecurse(const char *key,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static int
|
|
||||||
virQEMUBuildCommandLineJSONIterate(const char *key,
|
|
||||||
const virJSONValue *value,
|
|
||||||
void *opaque)
|
|
||||||
{
|
|
||||||
return virQEMUBuildCommandLineJSONRecurse(key, value, opaque, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* virQEMUBuildCommandLineJSON:
|
* virQEMUBuildCommandLineJSON:
|
||||||
* @value: json object containing the value
|
* @value: json object containing the value
|
||||||
@ -131,12 +172,7 @@ int
|
|||||||
virQEMUBuildCommandLineJSON(const virJSONValue *value,
|
virQEMUBuildCommandLineJSON(const virJSONValue *value,
|
||||||
virBufferPtr buf)
|
virBufferPtr buf)
|
||||||
{
|
{
|
||||||
if (virJSONValueObjectForeachKeyValue(value,
|
return virQEMUBuildCommandLineJSONRecurse(NULL, value, buf, false);
|
||||||
virQEMUBuildCommandLineJSONIterate,
|
|
||||||
buf) < 0)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -117,6 +117,14 @@ mymain(void)
|
|||||||
"array=bleah,array=qwerty,array=1");
|
"array=bleah,array=qwerty,array=1");
|
||||||
DO_TEST_COMMAND_OBJECT_FROM_JSON("{\"boolean\":true,\"hyphen-name\":1234,\"some_string\":\"bleah\"}",
|
DO_TEST_COMMAND_OBJECT_FROM_JSON("{\"boolean\":true,\"hyphen-name\":1234,\"some_string\":\"bleah\"}",
|
||||||
"boolean=yes,hyphen-name=1234,some_string=bleah");
|
"boolean=yes,hyphen-name=1234,some_string=bleah");
|
||||||
|
DO_TEST_COMMAND_OBJECT_FROM_JSON("{\"nest\": {\"boolean\":true,"
|
||||||
|
"\"hyphen-name\":1234,"
|
||||||
|
"\"some_string\":\"bleah\","
|
||||||
|
"\"bleah\":\"bl,eah\""
|
||||||
|
"}"
|
||||||
|
"}",
|
||||||
|
"nest.boolean=yes,nest.hyphen-name=1234,"
|
||||||
|
"nest.some_string=bleah,nest.bleah=bl,,eah");
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user