From e3247b8b20d17c33faa7d1716738e7f7b7dbbb08 Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Wed, 6 Dec 2023 09:53:30 -0400 Subject: [PATCH 1/3] Disallow brokers from returning users without groups The brokers used to be able to provide the userinfo without any group associated to it. This creates difficulties when trying to manage the user presence in the local groups. Now, the broker must provide at least one group for the user and the first group must be a remote one (with UGID). --- internal/brokers/broker.go | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/internal/brokers/broker.go b/internal/brokers/broker.go index 84890dbb4..b2f83ff0f 100644 --- a/internal/brokers/broker.go +++ b/internal/brokers/broker.go @@ -336,6 +336,14 @@ func validateUserInfoAndGenerateIDs(brokerName string, rawMsg json.RawMessage) ( } uInfo.UID = generateID(brokerName + uInfo.UUID) + // User must be a part of at least one group. + if len(uInfo.Groups) == 0 { + return users.UserInfo{}, fmt.Errorf("empty groups") + } + // The default group for the user is the default and it must have a UGID. + if uInfo.Groups[0].UGID == "" { + return users.UserInfo{}, fmt.Errorf("default group has empty UGID") + } // Validate UGIDs and generate GIDs for _, g := range uInfo.Groups { if g.Name == "" { From c73272625706629d296d6a93a82dcfec17e26729 Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Thu, 7 Dec 2023 08:30:53 -0400 Subject: [PATCH 2/3] Update cache to prevent adding/updating users without group This follows the changes to the userinfo returned by IsAuthenticated. We have validation for the return before getting to the cache, but it's best to have multiple layers of protection. --- internal/cache/getusers.go | 2 +- internal/cache/update.go | 30 ++++++------------------------ 2 files changed, 7 insertions(+), 25 deletions(-) diff --git a/internal/cache/getusers.go b/internal/cache/getusers.go index bed1982e0..63e9a38f9 100644 --- a/internal/cache/getusers.go +++ b/internal/cache/getusers.go @@ -13,7 +13,7 @@ type UserPasswdShadow struct { Name string UID int GID int - Gecos string + Gecos string // Gecos is an optional field. It can be empty. Dir string Shell string diff --git a/internal/cache/update.go b/internal/cache/update.go index 1820a6d71..cc816cd80 100644 --- a/internal/cache/update.go +++ b/internal/cache/update.go @@ -16,15 +16,17 @@ import ( // UpdateFromUserInfo inserts or updates user and group buckets from the user information. func (c *Cache) UpdateFromUserInfo(u users.UserInfo) error { // create bucket contents dynamically - gid := -1 - if len(u.Groups) > 0 && u.Groups[0].GID != nil { - gid = *u.Groups[0].GID + if len(u.Groups) == 0 { + return fmt.Errorf("no group provided for user %s (%v)", u.Name, u.UID) + } + if u.Groups[0].GID == nil { + return fmt.Errorf("no gid provided for default group %q", u.Groups[0].Name) } userDB := userDB{ UserPasswdShadow: UserPasswdShadow{ Name: u.Name, UID: u.UID, - GID: gid, + GID: *u.Groups[0].GID, Gecos: u.Gecos, Dir: u.Dir, Shell: u.Shell, @@ -66,26 +68,6 @@ func (c *Cache) UpdateFromUserInfo(u users.UserInfo) error { return err } - // No groups were specified for this request. - if userDB.GID == -1 { - if len(previousGroupsForCurrentUser.GIDs) == 0 { - return fmt.Errorf("no group provided for user %v (%v) and no previous record found", userDB.Name, userDB.UID) - } - - for _, gid := range previousGroupsForCurrentUser.GIDs { - g, err := getFromBucket[groupDB](buckets[groupByIDBucketName], gid) - if err != nil { - c.requestClearDatabase() - return err - } - groupContents = append(groupContents, groupDB{ - Name: g.Name, - GID: g.GID, - }) - } - userDB.GID = groupContents[0].GID - } - /* 1. Handle user update */ updateUser(buckets, userDB) From 9d8fa24af517da8e2945ba199e5ed76e69f0d38a Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Wed, 6 Dec 2023 09:55:23 -0400 Subject: [PATCH 3/3] Update tests to cover new behaviors --- internal/brokers/broker_test.go | 13 ++--- ...roker_returns_userinfo_with_empty_username | 2 +- ...userinfo_with_first_group_with_empty_ugid} | 2 +- ...hen_broker_returns_userinfo_with_no_groups | 12 +++++ ...n_broker_returns_userinfo_with_empty_gecos | 4 ++ .../golden/no_ugid_means_local_group | 4 -- internal/cache/db_test.go | 51 +++++++++++++------ ...sert_new_user_without_optional_gecos_field | 13 +++++ ...eates_entries_even_without_restating_group | 13 ----- ...ep_existing_groups_without_specifying_them | 13 ----- ...y_removing_optional_gecos_field_if_not_set | 13 +++++ internal/testutils/broker.go | 13 ++++- 12 files changed, 97 insertions(+), 56 deletions(-) rename internal/brokers/testdata/TestIsAuthenticated/golden/{error_when_broker_returns_userinfo_with_empty_ugid => error_when_broker_returns_userinfo_with_first_group_with_empty_ugid} (87%) create mode 100644 internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_no_groups create mode 100644 internal/brokers/testdata/TestIsAuthenticated/golden/no_error_when_broker_returns_userinfo_with_empty_gecos delete mode 100644 internal/brokers/testdata/TestIsAuthenticated/golden/no_ugid_means_local_group create mode 100644 internal/cache/testdata/TestUpdateFromUserInfo/golden/insert_new_user_without_optional_gecos_field delete mode 100644 internal/cache/testdata/TestUpdateFromUserInfo/golden/invalid_value_entry_in_groupbyname_recreates_entries_even_without_restating_group delete mode 100644 internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_and_keep_existing_groups_without_specifying_them create mode 100644 internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_by_removing_optional_gecos_field_if_not_set diff --git a/internal/brokers/broker_test.go b/internal/brokers/broker_test.go index 52b839ab3..a4276399e 100644 --- a/internal/brokers/broker_test.go +++ b/internal/brokers/broker_test.go @@ -214,12 +214,11 @@ func TestIsAuthenticated(t *testing.T) { cancelFirstCall bool }{ - "Successfully authenticate": {sessionID: "success"}, - "Successfully authenticate after cancelling first call": {sessionID: "IA_second_call", secondCall: true}, - "Denies authentication when broker times out": {sessionID: "IA_timeout"}, - "No error when auth.Next and no data": {sessionID: "IA_next"}, - - "No UGID means local group": {sessionID: "IA_info_missing_ugid"}, + "Successfully authenticate": {sessionID: "success"}, + "Successfully authenticate after cancelling first call": {sessionID: "IA_second_call", secondCall: true}, + "Denies authentication when broker times out": {sessionID: "IA_timeout"}, + "No error when auth.Next and no data": {sessionID: "IA_next"}, + "No error when broker returns userinfo with empty gecos": {sessionID: "IA_info_missing_gecos"}, // broker errors "Error when authenticating": {sessionID: "IA_error"}, @@ -228,7 +227,9 @@ func TestIsAuthenticated(t *testing.T) { "Error when broker returns invalid access": {sessionID: "IA_invalid_access"}, "Error when broker returns invalid userinfo": {sessionID: "IA_invalid_userinfo"}, "Error when broker returns userinfo with empty username": {sessionID: "IA_info_missing_user_name"}, + "Error when broker returns userinfo with no groups": {sessionID: "IA_info_missing_groups"}, "Error when broker returns userinfo with empty group name": {sessionID: "IA_info_missing_group_name"}, + "Error when broker returns userinfo with first group with empty UGID": {sessionID: "IA_info_missing_ugid"}, "Error when broker returns userinfo with empty UUID": {sessionID: "IA_info_missing_uuid"}, "Error when broker returns userinfo with invalid homedir": {sessionID: "IA_info_invalid_home"}, "Error when broker returns userinfo with invalid shell": {sessionID: "IA_info_invalid_shell"}, diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_username b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_username index 8fb97a44f..eb226d2f9 100644 --- a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_username +++ b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_username @@ -4,7 +4,7 @@ FIRST CALL: err: invalid user information provided by the broker ({ "name": "", "uuid": "uuid-IA_info_missing_user_name", - "gecos": "gecos for ", + "gecos": "gecos for IA_info_missing_user_name", "dir": "/home/IA_info_missing_user_name", "shell": "/bin/sh/IA_info_missing_user_name", "avatar": "avatar for ", diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_ugid b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_first_group_with_empty_ugid similarity index 87% rename from internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_ugid rename to internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_first_group_with_empty_ugid index 67dfc282d..3f4d6fc5b 100644 --- a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_empty_ugid +++ b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_first_group_with_empty_ugid @@ -9,4 +9,4 @@ FIRST CALL: "shell": "/bin/sh/IA_info_missing_ugid", "avatar": "avatar for IA_info_missing_ugid", "groups": [ {"name": "group-IA_info_missing_ugid", "ugid": ""} ] - }): group "group-IA_info_missing_ugid" has empty UGID + }): default group has empty UGID diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_no_groups b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_no_groups new file mode 100644 index 000000000..5c820a3ee --- /dev/null +++ b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_broker_returns_userinfo_with_no_groups @@ -0,0 +1,12 @@ +FIRST CALL: + access: + data: + err: invalid user information provided by the broker ({ + "name": "IA_info_missing_groups", + "uuid": "uuid-IA_info_missing_groups", + "gecos": "gecos for IA_info_missing_groups", + "dir": "/home/IA_info_missing_groups", + "shell": "/bin/sh/IA_info_missing_groups", + "avatar": "avatar for IA_info_missing_groups", + "groups": [ ] + }): empty groups diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/no_error_when_broker_returns_userinfo_with_empty_gecos b/internal/brokers/testdata/TestIsAuthenticated/golden/no_error_when_broker_returns_userinfo_with_empty_gecos new file mode 100644 index 000000000..dac27b877 --- /dev/null +++ b/internal/brokers/testdata/TestIsAuthenticated/golden/no_error_when_broker_returns_userinfo_with_empty_gecos @@ -0,0 +1,4 @@ +FIRST CALL: + access: granted + data: {"Name":"IA_info_missing_gecos","UID":67151,"Gecos":"","Dir":"/home/IA_info_missing_gecos","Shell":"/bin/sh/IA_info_missing_gecos","Groups":[{"Name":"group-IA_info_missing_gecos","GID":66857}]} + err: diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/no_ugid_means_local_group b/internal/brokers/testdata/TestIsAuthenticated/golden/no_ugid_means_local_group deleted file mode 100644 index 108692036..000000000 --- a/internal/brokers/testdata/TestIsAuthenticated/golden/no_ugid_means_local_group +++ /dev/null @@ -1,4 +0,0 @@ -FIRST CALL: - access: granted - data: {"Name":"IA_info_missing_ugid","UID":96915,"Gecos":"gecos for IA_info_missing_ugid","Dir":"/home/IA_info_missing_ugid","Shell":"/bin/sh/IA_info_missing_ugid","Groups":[{"Name":"group-IA_info_missing_ugid","GID":null}]} - err: diff --git a/internal/cache/db_test.go b/internal/cache/db_test.go index 44f27f977..b1c17c34c 100644 --- a/internal/cache/db_test.go +++ b/internal/cache/db_test.go @@ -179,6 +179,25 @@ func TestUpdateFromUserInfo(t *testing.T) { {Name: "newgroup1", GID: ptrValue(11111)}, }, }, + "user1-with-only-local-group": { + Name: "user1", + UID: 1111, + Gecos: "User1 gecos\nOn multiple lines", + Dir: "/home/user1", + Shell: "/bin/bash", + Groups: []users.GroupInfo{ + {Name: "local-group"}, + }, + }, + "user1-without-gecos": { + Name: "user1", + UID: 1111, + Dir: "/home/user1", + Shell: "/bin/bash", + Groups: []users.GroupInfo{ + {Name: "group1", GID: ptrValue(11111)}, + }, + }, "user1-without-groups": { Name: "user1", UID: 1111, @@ -249,18 +268,19 @@ func TestUpdateFromUserInfo(t *testing.T) { wantErr bool }{ // New user - "Insert new user": {userCase: "user1"}, - "Update last login time for user": {userCase: "user1", dbFile: "one_user_and_group"}, + "Insert new user": {userCase: "user1"}, + "Update last login time for user": {userCase: "user1", dbFile: "one_user_and_group"}, + "Insert new user without optional gecos field": {userCase: "user1-without-gecos"}, // User and Group renames - "Update user by changing attributes": {userCase: "user1-new-attributes", dbFile: "one_user_and_group"}, - "Update group by changing attributes": {userCase: "group1-new-attributes", dbFile: "one_user_and_group"}, + "Update user by changing attributes": {userCase: "user1-new-attributes", dbFile: "one_user_and_group"}, + "Update user by removing optional gecos field if not set": {userCase: "user1-without-gecos", dbFile: "one_user_and_group"}, + "Update group by changing attributes": {userCase: "group1-new-attributes", dbFile: "one_user_and_group"}, // Group updates - "Update user and keep existing groups without specifying them": {userCase: "user1-without-groups", dbFile: "one_user_and_group"}, - "Update user by adding a new group": {userCase: "user1-with-new-group", dbFile: "one_user_and_group"}, - "Update user by adding a new default group": {userCase: "user1-with-new-default-group", dbFile: "one_user_and_group"}, - "Remove group from user": {userCase: "user1-with-only-new-group", dbFile: "one_user_and_group"}, + "Update user by adding a new group": {userCase: "user1-with-new-group", dbFile: "one_user_and_group"}, + "Update user by adding a new default group": {userCase: "user1-with-new-default-group", dbFile: "one_user_and_group"}, + "Remove group from user": {userCase: "user1-with-only-new-group", dbFile: "one_user_and_group"}, // Multi users handling "Update only user even if we have multiple of them": {userCase: "user1", dbFile: "multiple_users_and_groups"}, @@ -271,17 +291,16 @@ func TestUpdateFromUserInfo(t *testing.T) { "Local groups are filtered": {userCase: "user1-with-local-group"}, // Allowed inconsistent cases - "Invalid value entry in groupByID but user restating group recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_groupByID"}, - "Invalid value entry in userByID recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_userByID"}, - "Invalid value entry in groupByName recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_groupByName"}, - "Invalid value entry in groupByName recreates entries even without restating group": {userCase: "user1-without-groups", dbFile: "invalid_entry_in_groupByName"}, - "Invalid value entry in userByName recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_userByName"}, - "Invalid value entries in other user and groups don't impact current request": {userCase: "user1", dbFile: "invalid_entries_but_user_and_group1"}, + "Invalid value entry in groupByID but user restating group recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_groupByID"}, + "Invalid value entry in userByID recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_userByID"}, + "Invalid value entry in groupByName recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_groupByName"}, + "Invalid value entry in userByName recreates entries": {userCase: "user1", dbFile: "invalid_entry_in_userByName"}, + "Invalid value entries in other user and groups don't impact current request": {userCase: "user1", dbFile: "invalid_entries_but_user_and_group1"}, // Error cases - "Error on new user without any groups": {userCase: "user1-without-groups", wantErr: true}, + "Error on user without any groups": {userCase: "user1-without-groups", wantErr: true}, + "Error on user with only local group": {userCase: "user1-with-only-local-group", wantErr: true}, "Error on invalid value entry in userToGroups clear database": {userCase: "user1", dbFile: "invalid_entry_in_userToGroups", wantErr: true, wantClearDB: true}, - "Error on invalid value entry in groupByID with user not restating groups clear database": {userCase: "user1-without-groups", dbFile: "invalid_entry_in_groupByID", wantErr: true, wantClearDB: true}, "Error on invalid value entry in groupToUsers clear database": {userCase: "user1", dbFile: "invalid_entry_in_groupToUsers", wantErr: true, wantClearDB: true}, "Error on invalid value entry in groupToUsers for user dropping from group clear database": {userCase: "user1", dbFile: "invalid_entry_in_groupToUsers_secondary_group", wantErr: true, wantClearDB: true}, "Error on invalid value entry in groupByID for user dropping from group clear database": {userCase: "user1", dbFile: "invalid_entry_in_groupByID_secondary_group", wantErr: true, wantClearDB: true}, diff --git a/internal/cache/testdata/TestUpdateFromUserInfo/golden/insert_new_user_without_optional_gecos_field b/internal/cache/testdata/TestUpdateFromUserInfo/golden/insert_new_user_without_optional_gecos_field new file mode 100644 index 000000000..e387eccce --- /dev/null +++ b/internal/cache/testdata/TestUpdateFromUserInfo/golden/insert_new_user_without_optional_gecos_field @@ -0,0 +1,13 @@ +GroupByID: + "11111": '{"Name":"group1","GID":11111}' +GroupByName: + group1: '{"Name":"group1","GID":11111}' +GroupToUsers: + "11111": '{"GID":11111,"UIDs":[1111]}' +UserByID: + "1111": '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' +UserByName: + user1: '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' +UserToBroker: {} +UserToGroups: + "1111": '{"UID":1111,"GIDs":[11111]}' diff --git a/internal/cache/testdata/TestUpdateFromUserInfo/golden/invalid_value_entry_in_groupbyname_recreates_entries_even_without_restating_group b/internal/cache/testdata/TestUpdateFromUserInfo/golden/invalid_value_entry_in_groupbyname_recreates_entries_even_without_restating_group deleted file mode 100644 index 65695498d..000000000 --- a/internal/cache/testdata/TestUpdateFromUserInfo/golden/invalid_value_entry_in_groupbyname_recreates_entries_even_without_restating_group +++ /dev/null @@ -1,13 +0,0 @@ -GroupByID: - "11111": '{"Name":"group1","GID":11111}' -GroupByName: - group1: '{"Name":"group1","GID":11111}' -GroupToUsers: - "11111": '{"GID":11111,"UIDs":[1111]}' -UserByID: - "1111": '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"User1 gecos\nOn multiple lines","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' -UserByName: - user1: '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"User1 gecos\nOn multiple lines","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' -UserToBroker: {} -UserToGroups: - "1111": '{"UID":1111,"GIDs":[11111]}' diff --git a/internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_and_keep_existing_groups_without_specifying_them b/internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_and_keep_existing_groups_without_specifying_them deleted file mode 100644 index 65695498d..000000000 --- a/internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_and_keep_existing_groups_without_specifying_them +++ /dev/null @@ -1,13 +0,0 @@ -GroupByID: - "11111": '{"Name":"group1","GID":11111}' -GroupByName: - group1: '{"Name":"group1","GID":11111}' -GroupToUsers: - "11111": '{"GID":11111,"UIDs":[1111]}' -UserByID: - "1111": '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"User1 gecos\nOn multiple lines","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' -UserByName: - user1: '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"User1 gecos\nOn multiple lines","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' -UserToBroker: {} -UserToGroups: - "1111": '{"UID":1111,"GIDs":[11111]}' diff --git a/internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_by_removing_optional_gecos_field_if_not_set b/internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_by_removing_optional_gecos_field_if_not_set new file mode 100644 index 000000000..e387eccce --- /dev/null +++ b/internal/cache/testdata/TestUpdateFromUserInfo/golden/update_user_by_removing_optional_gecos_field_if_not_set @@ -0,0 +1,13 @@ +GroupByID: + "11111": '{"Name":"group1","GID":11111}' +GroupByName: + group1: '{"Name":"group1","GID":11111}' +GroupToUsers: + "11111": '{"GID":11111,"UIDs":[1111]}' +UserByID: + "1111": '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' +UserByName: + user1: '{"Name":"user1","UID":1111,"GID":11111,"Gecos":"","Dir":"/home/user1","Shell":"/bin/bash","LastPwdChange":-1,"MaxPwdAge":-1,"PwdWarnPeriod":-1,"PwdInactivity":-1,"MinPwdAge":-1,"ExpirationDate":-1,"LastLogin":"ABCDETIME"}' +UserToBroker: {} +UserToGroups: + "1111": '{"UID":1111,"GIDs":[11111]}' diff --git a/internal/testutils/broker.go b/internal/testutils/broker.go index 348711771..46087689d 100644 --- a/internal/testutils/broker.go +++ b/internal/testutils/broker.go @@ -333,6 +333,7 @@ func userInfoFromName(parsedID string, extraGroups []users.GroupInfo) string { group := "group-" + parsedID home := "/home/" + parsedID shell := "/bin/sh/" + parsedID + gecos := "gecos for " + parsedID uuid := "uuid-" + parsedID ugid := "ugid-" + parsedID @@ -345,6 +346,10 @@ func userInfoFromName(parsedID string, extraGroups []users.GroupInfo) string { uuid = "" case "IA_info_missing_ugid": ugid = "" + case "IA_info_missing_gecos": + gecos = "" + case "IA_info_missing_groups": + group = "-" case "IA_info_invalid_home": home = "this is not a homedir" case "IA_info_invalid_shell": @@ -367,6 +372,9 @@ func userInfoFromName(parsedID string, extraGroups []users.GroupInfo) string { UGID: ugid, }) } + if group == "-" { + groups = []groupJSONInfo{} + } user := struct { Name string @@ -374,14 +382,15 @@ func userInfoFromName(parsedID string, extraGroups []users.GroupInfo) string { Home string Shell string Groups []groupJSONInfo - }{Name: name, UUID: uuid, Home: home, Shell: shell, Groups: groups} + Gecos string + }{Name: name, UUID: uuid, Home: home, Shell: shell, Groups: groups, Gecos: gecos} // only used for tests, we can ignore the template execution error as the returned data will be failing. var buf bytes.Buffer _ = template.Must(template.New("").Parse(`{ "name": "{{.Name}}", "uuid": "{{.UUID}}", - "gecos": "gecos for {{.Name}}", + "gecos": "{{.Gecos}}", "dir": "{{.Home}}", "shell": "{{.Shell}}", "avatar": "avatar for {{.Name}}",