From: Lennart Poettering Date: Thu, 20 Jun 2024 07:39:51 +0000 (+0200) Subject: json: make it easy to dispatch our enums X-Git-Tag: v257-rc1~1084^2 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=45840c2297d72a0f9e94eb3d2754b5e54c9cc0d9;p=thirdparty%2Fsystemd.git json: make it easy to dispatch our enums This does the opposite of the previous patch: it undoes the "-" → "_" mapping of enum values when we try to parse enums again. --- diff --git a/src/libsystemd/sd-json/json-util.h b/src/libsystemd/sd-json/json-util.h index 2b5ef521b6b..72c8d80bf7d 100644 --- a/src/libsystemd/sd-json/json-util.h +++ b/src/libsystemd/sd-json/json-util.h @@ -60,8 +60,16 @@ struct json_variant_foreach_state { return json_log(variant, flags, SYNTHETIC_ERRNO(EINVAL), "JSON field '%s' is not a string.", strna(n)); \ \ type cc = func(sd_json_variant_string(variant)); \ - if (cc < 0) \ - return json_log(variant, flags, SYNTHETIC_ERRNO(EINVAL), "Value of JSON field '%s' not recognized.", strna(n)); \ + if (cc < 0) { \ + /* Maybe this enum is recognizable if we replace "_" (i.e. Varlink syntax) with "-" (how we usually prefer it). */ \ + _cleanup_free_ char *z = strreplace(sd_json_variant_string(variant), "_", "-"); \ + if (!z) \ + return json_log_oom(variant, flags); \ + \ + cc = func(z); \ + if (cc < 0) \ + return json_log(variant, flags, SYNTHETIC_ERRNO(EINVAL), "Value of JSON field '%s' not recognized: %s", strna(n), sd_json_variant_string(variant)); \ + } \ \ *c = cc; \ return 0; \ diff --git a/src/test/test-json.c b/src/test/test-json.c index 5ebb5dd4a0c..aea4bbaf3ef 100644 --- a/src/test/test-json.c +++ b/src/test/test-json.c @@ -917,37 +917,40 @@ TEST(json_dispatch) { } typedef enum mytestenum { - myfoo, mybar, mybaz, _mymax, _myinvalid = -EINVAL, + myfoo, mybar, mybaz, with_some_dashes, _mymax, _myinvalid = -EINVAL, } mytestenum; static const char *mytestenum_table[_mymax] = { [myfoo] = "myfoo", [mybar] = "mybar", [mybaz] = "mybaz", + [with_some_dashes] = "with-some-dashes", }; -DEFINE_PRIVATE_STRING_TABLE_LOOKUP_FROM_STRING(mytestenum, mytestenum); +DEFINE_PRIVATE_STRING_TABLE_LOOKUP(mytestenum, mytestenum); static JSON_DISPATCH_ENUM_DEFINE(dispatch_mytestenum, mytestenum, mytestenum_from_string); TEST(json_dispatch_enum_define) { struct data { - mytestenum a, b, c, d; + mytestenum a, b, c, d, e; } data = { .a = _myinvalid, .b = _myinvalid, .c = _myinvalid, .d = mybar, + .e = _myinvalid, }; _cleanup_(sd_json_variant_unrefp) sd_json_variant *j = NULL; - assert_se(sd_json_build(&j, SD_JSON_BUILD_OBJECT( - SD_JSON_BUILD_PAIR("a", SD_JSON_BUILD_STRING("mybaz")), - SD_JSON_BUILD_PAIR("b", SD_JSON_BUILD_STRING("mybar")), - SD_JSON_BUILD_PAIR("c", SD_JSON_BUILD_STRING("myfoo")), - SD_JSON_BUILD_PAIR("d", SD_JSON_BUILD_NULL))) >= 0); + assert_se(sd_json_buildo(&j, + SD_JSON_BUILD_PAIR("a", SD_JSON_BUILD_STRING("mybaz")), + SD_JSON_BUILD_PAIR("b", SD_JSON_BUILD_STRING("mybar")), + SD_JSON_BUILD_PAIR("c", SD_JSON_BUILD_STRING("myfoo")), + SD_JSON_BUILD_PAIR("d", SD_JSON_BUILD_NULL), + SD_JSON_BUILD_PAIR("e", JSON_BUILD_STRING_UNDERSCORIFY(mytestenum_to_string(with_some_dashes)))) >= 0); assert_se(sd_json_dispatch(j, (const sd_json_dispatch_field[]) { @@ -955,6 +958,7 @@ TEST(json_dispatch_enum_define) { { "b", _SD_JSON_VARIANT_TYPE_INVALID, dispatch_mytestenum, offsetof(struct data, b), 0 }, { "c", _SD_JSON_VARIANT_TYPE_INVALID, dispatch_mytestenum, offsetof(struct data, c), 0 }, { "d", _SD_JSON_VARIANT_TYPE_INVALID, dispatch_mytestenum, offsetof(struct data, d), 0 }, + { "e", _SD_JSON_VARIANT_TYPE_INVALID, dispatch_mytestenum, offsetof(struct data, e), 0 }, {}, }, /* flags= */ 0, @@ -964,6 +968,7 @@ TEST(json_dispatch_enum_define) { assert(data.b == mybar); assert(data.c == myfoo); assert(data.d < 0); + assert(data.e == with_some_dashes); } TEST(json_dispatch_double) {