diff options
author | Thomas Haller <thaller@redhat.com> | 2019-04-12 16:08:54 +0200 |
---|---|---|
committer | Thomas Haller <thaller@redhat.com> | 2019-04-15 20:50:50 +0200 |
commit | 68bd018a88b4696608ce141d2d0d8576bd148ce8 (patch) | |
tree | 3e1590edee993742667de92f48b83a852a9cbeff /clients | |
parent | 87d16e935c91fb36727332dacd27e334f1db972c (diff) | |
download | NetworkManager-68bd018a88b4696608ce141d2d0d8576bd148ce8.tar.gz |
cli: prefer matching connections by "uuid" instead of "id"
Scripts should refer to connections by UUID. That means, whenever a
UUID matches, that is really what the user wants. The specifier "uuid"
must have precedence over "id" (and all others). That means, we must
search all connections.
For example:
$ UUIDS=($(nmcli -g TYPE,UUID connection show | sed -n 's/802-11-wireless://p'))
$ nmcli -f connection.id,connection.uuid connection show "${UUIDS[@]}"
in this case we must preferrably match by UUID, regardless of whether
a "connection.id" exists.
Note that if you have:
$ nmcli connection show | grep fdf7b2d2-2858-3938-9b14-7f1b514a9a00
b fdf7b2d2-2858-3938-9b14-7f1b514a9a00 ethernet --
fdf7b2d2-2858-3938-9b14-7f1b514a9a00 ab9f3891-3420-335e-89da-f14c1b94c540 ethernet --
then certain commands will still select all matching connections:
$ nmcli -f connection.id,connection.uuid --mode multiline connection show fdf7b2d2-2858-3938-9b14-7f1b514a9a00
connection.id: fdf7b2d2-2858-3938-9b14-7f1b514a9a00
connection.uuid: ab9f3891-3420-335e-89da-f14c1b94c540
connection.id: b
connection.uuid: fdf7b2d2-2858-3938-9b14-7f1b514a9a00
This only makes a difference for commands that must pick only one profile:
$ nmcli connection modify fdf7b2d2-2858-3938-9b14-7f1b514a9a00 con-name new-name
Diffstat (limited to 'clients')
-rw-r--r-- | clients/cli/common.c | 78 |
1 files changed, 51 insertions, 27 deletions
diff --git a/clients/cli/common.c b/clients/cli/common.c index cb75e345f6..d94dbd0ba0 100644 --- a/clients/cli/common.c +++ b/clients/cli/common.c @@ -425,35 +425,37 @@ nmc_find_connection (const GPtrArray *connections, GPtrArray **out_result, gboolean complete) { - NMConnection *connection; + NMConnection *best_candidate_uuid = NULL; NMConnection *best_candidate = NULL; + gs_unref_ptrarray GPtrArray *result_allocated = NULL; GPtrArray *result = out_result ? *out_result : NULL; + const guint result_inital_len = result ? result->len : 0u; guint i, j; nm_assert (connections); nm_assert (filter_val); for (i = 0; i < connections->len; i++) { - const char *v, *v_num; + gboolean match_by_uuid = FALSE; + NMConnection *connection; + const char *v; + const char *v_num; connection = NM_CONNECTION (connections->pdata[i]); - /* When filter_type is NULL, compare connection ID (filter_val) - * against all types. Otherwise, only compare against the specific - * type. If 'path' filter type is specified, comparison against - * numeric index (in addition to the whole path) is allowed. - */ - if (NM_IN_STRSET (filter_type, NULL, "id")) { - v = nm_connection_get_id (connection); - if (complete) + if (NM_IN_STRSET (filter_type, NULL, "uuid")) { + v = nm_connection_get_uuid (connection); + if (complete && (filter_type || *filter_val)) nmc_complete_strings (filter_val, v); - if (nm_streq0 (filter_val, v)) + if (nm_streq0 (filter_val, v)) { + match_by_uuid = TRUE; goto found; + } } - if (NM_IN_STRSET (filter_type, NULL, "uuid")) { - v = nm_connection_get_uuid (connection); - if (complete && (filter_type || *filter_val)) + if (NM_IN_STRSET (filter_type, NULL, "id")) { + v = nm_connection_get_id (connection); + if (complete) nmc_complete_strings (filter_val, v); if (nm_streq0 (filter_val, v)) goto found; @@ -478,23 +480,45 @@ nmc_find_connection (const GPtrArray *connections, } continue; + found: - if (!out_result) - return connection; - if (!best_candidate) - best_candidate = connection; - if (!result) - result = g_ptr_array_new_with_free_func (g_object_unref); - for (j = 0; j < result->len; j++) { - if (connection == result->pdata[j]) - break; + if (match_by_uuid) { + if ( !complete + && !out_result) + return connection; + best_candidate_uuid = connection; + } else { + if (!best_candidate) + best_candidate = connection; + } + if (out_result) { + gboolean already_tracked = FALSE; + + if (!result) { + result_allocated = g_ptr_array_new_with_free_func (g_object_unref); + result = result_allocated; + } else { + for (j = 0; j < result->len; j++) { + if (connection == result->pdata[j]) { + already_tracked = TRUE; + break; + } + } + } + if (!already_tracked) { + if (match_by_uuid) { + /* the profile is matched exactly (by UUID). We prepend it + * to the list of all found profiles. */ + g_ptr_array_insert (result, result_inital_len, g_object_ref (connection)); + } else + g_ptr_array_add (result, g_object_ref (connection)); + } } - if (j == result->len) - g_ptr_array_add (result, g_object_ref (connection)); } - NM_SET_OUT (out_result, result); - return best_candidate; + if (result_allocated) + *out_result = g_steal_pointer (&result_allocated); + return best_candidate_uuid ?: best_candidate; } NMActiveConnection * |