json: add new API json_variant_filter() for dropping fields from objects

This commit is contained in:
Lennart Poettering
2019-12-02 09:47:00 +01:00
parent e787b211a5
commit f2ff34ff2a
2 changed files with 55 additions and 0 deletions
+53
View File
@@ -1622,6 +1622,59 @@ void json_variant_dump(JsonVariant *v, JsonFormatFlags flags, FILE *f, const cha
fputc('\n', f); /* In case of SSE add a second newline */
}
int json_variant_filter(JsonVariant **v, char **to_remove) {
_cleanup_(json_variant_unrefp) JsonVariant *w = NULL;
_cleanup_free_ JsonVariant **array = NULL;
size_t i, n = 0, k = 0;
int r;
assert(v);
if (json_variant_is_blank_object(*v))
return 0;
if (!json_variant_is_object(*v))
return -EINVAL;
if (strv_isempty(to_remove))
return 0;
for (i = 0; i < json_variant_elements(*v); i += 2) {
JsonVariant *p;
p = json_variant_by_index(*v, i);
if (!json_variant_has_type(p, JSON_VARIANT_STRING))
return -EINVAL;
if (strv_contains(to_remove, json_variant_string(p))) {
if (!array) {
array = new(JsonVariant*, json_variant_elements(*v) - 2);
if (!array)
return -ENOMEM;
for (k = 0; k < i; k++)
array[k] = json_variant_by_index(*v, k);
}
n++;
} else if (array) {
array[k++] = p;
array[k++] = json_variant_by_index(*v, i + 1);
}
}
if (n == 0)
return 0;
r = json_variant_new_object(&w, array, k);
if (r < 0)
return r;
json_variant_unref(*v);
*v = TAKE_PTR(w);
return (int) n;
}
static int json_variant_copy(JsonVariant **nv, JsonVariant *v) {
JsonVariantType t;
JsonVariant *c;
+2
View File
@@ -167,6 +167,8 @@ typedef enum JsonFormatFlags {
int json_variant_format(JsonVariant *v, JsonFormatFlags flags, char **ret);
void json_variant_dump(JsonVariant *v, JsonFormatFlags flags, FILE *f, const char *prefix);
int json_variant_filter(JsonVariant **v, char **to_remove);
int json_parse(const char *string, JsonVariant **ret, unsigned *ret_line, unsigned *ret_column);
int json_parse_continue(const char **p, JsonVariant **ret, unsigned *ret_line, unsigned *ret_column);
int json_parse_file(FILE *f, const char *path, JsonVariant **ret, unsigned *ret_line, unsigned *ret_column);