From fb09f96e1a07a6f8520f5c3ce95a29ef39be1733 Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Fri, 15 Sep 2023 06:54:34 -0400 Subject: [PATCH 1/5] Update newBrokerForTests helper Updating function signature to allow for creation of multiple brokers per test case. --- internal/brokers/broker_test.go | 17 ++++++++++------- internal/brokers/manager_test.go | 2 +- 2 files changed, 11 insertions(+), 8 deletions(-) diff --git a/internal/brokers/broker_test.go b/internal/brokers/broker_test.go index 03a7900d9..620b51860 100644 --- a/internal/brokers/broker_test.go +++ b/internal/brokers/broker_test.go @@ -115,7 +115,7 @@ func TestGetAuthenticationModes(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "") + b := newBrokerForTests(t, "", "") if tc.supportedUILayouts == nil { tc.supportedUILayouts = []string{"required-entry"} @@ -173,7 +173,7 @@ func TestSelectAuthenticationMode(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "") + b := newBrokerForTests(t, "", "") if tc.supportedUILayouts == nil { tc.supportedUILayouts = []string{"required-entry"} @@ -226,7 +226,7 @@ func TestIsAuthenticated(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "") + b := newBrokerForTests(t, "", "") // Stores the combined output of both calls to IsAuthenticated var firstCallReturn, secondCallReturn string @@ -277,7 +277,7 @@ func TestCancelIsAuthenticated(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "") + b := newBrokerForTests(t, "", "") var access string ctx, cancel := context.WithCancel(context.Background()) @@ -299,14 +299,17 @@ func TestCancelIsAuthenticated(t *testing.T) { } } -func newBrokerForTests(t *testing.T, cfgDir string) (b brokers.Broker) { +func newBrokerForTests(t *testing.T, cfgDir, brokerName string) (b brokers.Broker) { t.Helper() if cfgDir == "" { cfgDir = t.TempDir() } + if brokerName == "" { + brokerName = strings.ReplaceAll(t.Name(), "/", "_") + } - cfgPath, cleanup, err := testutils.StartBusBrokerMock(cfgDir, strings.ReplaceAll(t.Name(), "/", "_")) + cfgPath, cleanup, err := testutils.StartBusBrokerMock(cfgDir, brokerName) require.NoError(t, err, "Setup: could not start bus broker mock") t.Cleanup(cleanup) @@ -314,7 +317,7 @@ func newBrokerForTests(t *testing.T, cfgDir string) (b brokers.Broker) { require.NoError(t, err, "Setup: could not connect to system bus") t.Cleanup(func() { require.NoError(t, conn.Close(), "Teardown: Failed to close the connection") }) - b, err = brokers.NewBroker(context.Background(), strings.ReplaceAll(t.Name(), "/", "_"), cfgPath, conn) + b, err = brokers.NewBroker(context.Background(), brokerName, cfgPath, conn) require.NoError(t, err, "Setup: could not create broker") return b diff --git a/internal/brokers/manager_test.go b/internal/brokers/manager_test.go index 4696e65d6..5728a9056 100644 --- a/internal/brokers/manager_test.go +++ b/internal/brokers/manager_test.go @@ -136,7 +136,7 @@ func TestBrokerFromSessionID(t *testing.T) { t.Parallel() cfgDir := t.TempDir() - b := newBrokerForTests(t, cfgDir) + b := newBrokerForTests(t, cfgDir, "") m, err := brokers.NewManager(context.Background(), nil, brokers.WithCfgDir(cfgDir)) require.NoError(t, err, "Setup: could not create manager") From aefbd30fc3eeb6c6955b13ee06e549ff9a781ac1 Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Fri, 15 Sep 2023 06:55:41 -0400 Subject: [PATCH 2/5] Add tests with multiple brokers to manager_test.go We were not testing some important scenarios of the brokers.Manager (e.g. starting/ending session on the correct broker if multiple are configured, not triggering autodiscovery when configuredBrokers != nil). This commit adds test cases to cover those scenarios. --- internal/brokers/manager_test.go | 48 +++++++++++++++---- ...utodiscovery_when_configuredbrokers_is_set | 2 + ...tart_a_new_session_with_the_correct_broker | 2 + 3 files changed, 42 insertions(+), 10 deletions(-) create mode 100644 internal/brokers/testdata/TestNewManager/golden/creates_without_autodiscovery_when_configuredbrokers_is_set create mode 100644 internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker diff --git a/internal/brokers/manager_test.go b/internal/brokers/manager_test.go index 5728a9056..59cf78401 100644 --- a/internal/brokers/manager_test.go +++ b/internal/brokers/manager_test.go @@ -20,12 +20,14 @@ var ( func TestNewManager(t *testing.T) { tests := map[string]struct { - cfgDir string - noBus bool + cfgDir string + configuredBrokers []string + noBus bool wantErr bool }{ "Creates all brokers when config dir has only valid brokers": {cfgDir: "valid_brokers"}, + "Creates without autodiscovery when configuredBrokers is set": {cfgDir: "valid_brokers", configuredBrokers: []string{"valid_2"}}, "Creates only correct brokers when config dir has valid and invalid brokers": {cfgDir: "mixed_brokers"}, "Creates only local broker when config dir has only invalid ones": {cfgDir: "invalid_brokers"}, "Creates only local broker when config dir does not exist": {cfgDir: "does/not/exist"}, @@ -41,7 +43,7 @@ func TestNewManager(t *testing.T) { t.Setenv("DBUS_SYSTEM_BUS_ADDRESS", "/dev/null") } - got, err := brokers.NewManager(context.Background(), nil, brokers.WithRootDir(brokerCfgs), brokers.WithCfgDir(tc.cfgDir)) + got, err := brokers.NewManager(context.Background(), tc.configuredBrokers, brokers.WithRootDir(brokerCfgs), brokers.WithCfgDir(tc.cfgDir)) if tc.wantErr { require.Error(t, err, "NewManager should return an error, but did not") return @@ -171,9 +173,12 @@ func TestNewSession(t *testing.T) { brokerID string username string + configuredBrokers []string + wantErr bool }{ - "Successfully start a new session": {username: "success"}, + "Successfully start a new session": {username: "success"}, + "Successfully start a new session with the correct broker": {username: "success", configuredBrokers: []string{t.Name() + "_Broker1", t.Name() + "_Broker2"}}, "Error when broker does not exist": {brokerID: "does_not_exist", wantErr: true}, "Error when broker does not provide an ID": {username: "NS_no_id", wantErr: true}, @@ -185,8 +190,18 @@ func TestNewSession(t *testing.T) { t.Parallel() cfgDir := t.TempDir() - wantBroker := newBrokerForTests(t, cfgDir) - m, err := brokers.NewManager(context.Background(), nil, brokers.WithCfgDir(cfgDir)) + if tc.configuredBrokers == nil { + tc.configuredBrokers = []string{strings.ReplaceAll(t.Name(), "/", "_")} + } + + wantBroker := newBrokerForTests(t, cfgDir, tc.configuredBrokers[0]) + if len(tc.configuredBrokers) > 1 { + for _, name := range tc.configuredBrokers[1:] { + newBrokerForTests(t, cfgDir, name) + } + } + + m, err := brokers.NewManager(context.Background(), tc.configuredBrokers, brokers.WithCfgDir(cfgDir)) require.NoError(t, err, "Setup: could not create manager") if tc.brokerID == "" { @@ -226,9 +241,12 @@ func TestEndSession(t *testing.T) { brokerID string sessionID string + configuredBrokers []string + wantErr bool }{ - "Successfully end session": {sessionID: "success"}, + "Successfully end session": {sessionID: "success"}, + "Successfully end session on the correct broker": {sessionID: "success", configuredBrokers: []string{t.Name() + "_Broker1", t.Name() + "_Broker2"}}, "Error when broker does not exist": {brokerID: "does not exist", sessionID: "dont matter", wantErr: true}, "Error when ending session": {sessionID: "ES_error", wantErr: true}, @@ -239,12 +257,22 @@ func TestEndSession(t *testing.T) { t.Parallel() cfgDir := t.TempDir() - b := newBrokerForTests(t, cfgDir) - m, err := brokers.NewManager(context.Background(), nil, brokers.WithCfgDir(cfgDir)) + if tc.configuredBrokers == nil { + tc.configuredBrokers = []string{strings.ReplaceAll(t.Name(), "/", "_")} + } + + wantBroker := newBrokerForTests(t, cfgDir, tc.configuredBrokers[0]) + if len(tc.configuredBrokers) > 1 { + for _, name := range tc.configuredBrokers[1:] { + newBrokerForTests(t, cfgDir, name) + } + } + + m, err := brokers.NewManager(context.Background(), tc.configuredBrokers, brokers.WithCfgDir(cfgDir)) require.NoError(t, err, "Setup: could not create manager") if tc.brokerID != "does not exist" { - m.SetBrokerForSession(&b, tc.sessionID) + m.SetBrokerForSession(&wantBroker, tc.sessionID) } err = m.EndSession(tc.sessionID) diff --git a/internal/brokers/testdata/TestNewManager/golden/creates_without_autodiscovery_when_configuredbrokers_is_set b/internal/brokers/testdata/TestNewManager/golden/creates_without_autodiscovery_when_configuredbrokers_is_set new file mode 100644 index 000000000..4d944c950 --- /dev/null +++ b/internal/brokers/testdata/TestNewManager/golden/creates_without_autodiscovery_when_configuredbrokers_is_set @@ -0,0 +1,2 @@ +- local +- Broker2 diff --git a/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker b/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker new file mode 100644 index 000000000..3441f9991 --- /dev/null +++ b/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker @@ -0,0 +1,2 @@ +ID: BROKER_ID-success-session_id +Encryption Key: TestNewSession_Broker1_key From 070452a7f422b35f7556bcb497dccfa65c66d4c7 Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Tue, 19 Sep 2023 07:55:40 -0400 Subject: [PATCH 3/5] Update broker tests to use a MockBroker per family Before we were creating a MockBroker per test case, but this is not necessary since the broker has sync mechanisms. Now, it's a broker per test family, which uses less memory overall and is more useful from a testing POV --- internal/brokers/broker_test.go | 40 +++++++++++-------- .../golden/error_when_authenticating | 2 +- ...enticated_a_second_time_without_cancelling | 2 +- 3 files changed, 25 insertions(+), 19 deletions(-) diff --git a/internal/brokers/broker_test.go b/internal/brokers/broker_test.go index 620b51860..792e59944 100644 --- a/internal/brokers/broker_test.go +++ b/internal/brokers/broker_test.go @@ -93,6 +93,8 @@ func TestNewBroker(t *testing.T) { func TestGetAuthenticationModes(t *testing.T) { t.Parallel() + b := newBrokerForTests(t, "", "") + tests := map[string]struct { sessionID string supportedUILayouts []string @@ -115,8 +117,6 @@ func TestGetAuthenticationModes(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "", "") - if tc.supportedUILayouts == nil { tc.supportedUILayouts = []string{"required-entry"} } @@ -126,7 +126,7 @@ func TestGetAuthenticationModes(t *testing.T) { supportedUILayouts = append(supportedUILayouts, supportedLayouts[layout]) } - gotModes, err := b.GetAuthenticationModes(context.Background(), tc.sessionID, supportedUILayouts) + gotModes, err := b.GetAuthenticationModes(context.Background(), prefixID(t, tc.sessionID), supportedUILayouts) if tc.wantErr { require.Error(t, err, "GetAuthenticationModes should return an error, but did not") return @@ -136,7 +136,7 @@ func TestGetAuthenticationModes(t *testing.T) { modesStr, err := json.Marshal(gotModes) require.NoError(t, err, "Post: error when marshaling result") - got := "MODES:\n" + string(modesStr) + "\n\nVALIDATORS:\n" + b.LayoutValidatorsString(tc.sessionID) + got := "MODES:\n" + string(modesStr) + "\n\nVALIDATORS:\n" + b.LayoutValidatorsString(prefixID(t, tc.sessionID)) want := testutils.LoadWithUpdateFromGolden(t, got) require.Equal(t, want, got, "GetAuthenticationModes should return the expected modes, but did not") }) @@ -146,6 +146,8 @@ func TestGetAuthenticationModes(t *testing.T) { func TestSelectAuthenticationMode(t *testing.T) { t.Parallel() + b := newBrokerForTests(t, "", "") + tests := map[string]struct { sessionID string supportedUILayouts []string @@ -173,8 +175,6 @@ func TestSelectAuthenticationMode(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "", "") - if tc.supportedUILayouts == nil { tc.supportedUILayouts = []string{"required-entry"} } @@ -184,9 +184,9 @@ func TestSelectAuthenticationMode(t *testing.T) { supportedUILayouts = append(supportedUILayouts, supportedLayouts[layout]) } // This is normally done in the broker's GetAuthenticationModes method, but we need to do it here to test the SelectAuthenticationMode method. - brokers.GenerateLayoutValidators(&b, tc.sessionID, supportedUILayouts) + brokers.GenerateLayoutValidators(&b, prefixID(t, tc.sessionID), supportedUILayouts) - gotUI, err := b.SelectAuthenticationMode(context.Background(), tc.sessionID, "mode1") + gotUI, err := b.SelectAuthenticationMode(context.Background(), prefixID(t, tc.sessionID), "mode1") if tc.wantErr { require.Error(t, err, "SelectAuthenticationMode should return an error, but did not") return @@ -202,6 +202,8 @@ func TestSelectAuthenticationMode(t *testing.T) { func TestIsAuthenticated(t *testing.T) { t.Parallel() + b := newBrokerForTests(t, "", "") + tests := map[string]struct { sessionID string secondCall bool @@ -226,8 +228,6 @@ func TestIsAuthenticated(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "", "") - // Stores the combined output of both calls to IsAuthenticated var firstCallReturn, secondCallReturn string @@ -237,8 +237,8 @@ func TestIsAuthenticated(t *testing.T) { done := make(chan struct{}) go func() { defer close(done) - access, gotData, err := b.IsAuthenticated(ctx, tc.sessionID, "password") - firstCallReturn = fmt.Sprintf("FIRST CALL:\n\taccess: %s\n\tdata: %+v\n\terr: %v\n", access, gotData, err) + access, gotData, err := b.IsAuthenticated(ctx, prefixID(t, tc.sessionID), "password") + firstCallReturn = fmt.Sprintf("FIRST CALL:\n\taccess: %s\n\tdata: %s\n\terr: %v\n", access, gotData, err) }() // Give some time for the first call to block @@ -249,8 +249,8 @@ func TestIsAuthenticated(t *testing.T) { cancel() <-done } - access, gotData, err := b.IsAuthenticated(context.Background(), tc.sessionID, "password") - secondCallReturn = fmt.Sprintf("SECOND CALL:\n\taccess: %s\n\tdata: %+v\n\terr: %v\n", access, gotData, err) + access, gotData, err := b.IsAuthenticated(context.Background(), prefixID(t, tc.sessionID), "password") + secondCallReturn = fmt.Sprintf("SECOND CALL:\n\taccess: %s\n\tdata: %s\n\terr: %v\n", access, gotData, err) } <-done @@ -264,6 +264,8 @@ func TestIsAuthenticated(t *testing.T) { func TestCancelIsAuthenticated(t *testing.T) { t.Parallel() + b := newBrokerForTests(t, "", "") + tests := map[string]struct { sessionID string @@ -277,13 +279,11 @@ func TestCancelIsAuthenticated(t *testing.T) { t.Run(name, func(t *testing.T) { t.Parallel() - b := newBrokerForTests(t, "", "") - var access string ctx, cancel := context.WithCancel(context.Background()) done := make(chan struct{}) go func() { - access, _, _ = b.IsAuthenticated(ctx, tc.sessionID, "password") + access, _, _ = b.IsAuthenticated(ctx, prefixID(t, tc.sessionID), "password") close(done) }() defer cancel() @@ -322,3 +322,9 @@ func newBrokerForTests(t *testing.T, cfgDir, brokerName string) (b brokers.Broke return b } + +// prefixID is a helper function that prefixes the given ID with the test name to avoid conflicts. +func prefixID(t *testing.T, id string) string { + t.Helper() + return t.Name() + testutils.IDSeparator + id +} diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_authenticating b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_authenticating index b3169ef48..86039d36a 100644 --- a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_authenticating +++ b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_authenticating @@ -1,4 +1,4 @@ FIRST CALL: access: data: - err: Broker "TestIsAuthenticated_Error_when_authenticating": IsAuthenticated errored out + err: Broker "TestIsAuthenticated": IsAuthenticated errored out diff --git a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_calling_isauthenticated_a_second_time_without_cancelling b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_calling_isauthenticated_a_second_time_without_cancelling index f0017c1d3..49c24531b 100644 --- a/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_calling_isauthenticated_a_second_time_without_cancelling +++ b/internal/brokers/testdata/TestIsAuthenticated/golden/error_when_calling_isauthenticated_a_second_time_without_cancelling @@ -5,4 +5,4 @@ FIRST CALL: SECOND CALL: access: data: - err: Broker "TestIsAuthenticated_Error_when_calling_IsAuthenticated_a_second_time_without_cancelling": IsAuthenticated already running for session "IA_second_call" + err: Broker "TestIsAuthenticated": IsAuthenticated already running for session "TestIsAuthenticated/Error_when_calling_IsAuthenticated_a_second_time_without_cancelling_separator_IA_second_call" From 2b84bf085e9daedf4f11f04c4f4d6f0ab465e52c Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Tue, 19 Sep 2023 07:54:13 -0400 Subject: [PATCH 4/5] Extract MockBroker ID & Key generation to funcs To avoid having to harcode the expected values, it's better to extract the session ID (and encryption key) generation "logic" to public functions that we can use on tests. --- .../golden/successfully_start_a_new_session | 2 +- ...fully_start_a_new_session_with_the_correct_broker | 2 +- ...cessfully_select_a_broker_and_creates_the_session | 2 +- internal/testutils/broker.go | 12 +++++++++++- 4 files changed, 14 insertions(+), 4 deletions(-) diff --git a/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session b/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session index a37fdcf8e..715fc790f 100644 --- a/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session +++ b/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session @@ -1,2 +1,2 @@ ID: BROKER_ID-success-session_id -Encryption Key: TestNewSession_Successfully_start_a_new_session_key +Encryption Key: TestNewSession_Successfully_start_a_new_session-key diff --git a/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker b/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker index 3441f9991..41c729be3 100644 --- a/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker +++ b/internal/brokers/testdata/TestNewSession/golden/successfully_start_a_new_session_with_the_correct_broker @@ -1,2 +1,2 @@ ID: BROKER_ID-success-session_id -Encryption Key: TestNewSession_Broker1_key +Encryption Key: TestNewSession_Broker1-key diff --git a/internal/services/pam/testdata/TestSelectBroker/golden/successfully_select_a_broker_and_creates_the_session b/internal/services/pam/testdata/TestSelectBroker/golden/successfully_select_a_broker_and_creates_the_session index 948b72fe5..f4051d902 100644 --- a/internal/services/pam/testdata/TestSelectBroker/golden/successfully_select_a_broker_and_creates_the_session +++ b/internal/services/pam/testdata/TestSelectBroker/golden/successfully_select_a_broker_and_creates_the_session @@ -1,2 +1,2 @@ ID: BROKER_ID-TestSelectBroker/Successfully_select_a_broker_and_creates_the_session_separator_success-session_id -Encryption Key: BrokerMock_key +Encryption Key: BrokerMock-key diff --git a/internal/testutils/broker.go b/internal/testutils/broker.go index e7bc3cfd2..a325e95ab 100644 --- a/internal/testutils/broker.go +++ b/internal/testutils/broker.go @@ -118,7 +118,7 @@ func (b *BrokerBusMock) NewSession(username, lang string) (sessionID, encryption if parsedUsername == "NS_no_id" { return "", username + "_key", nil } - return fmt.Sprintf("%s-session_id", username), b.name + "_key", nil + return GenerateSessionID(username), GenerateEncryptionKey(b.name), nil } // GetAuthenticationModes returns default values to be used in tests or an error if requested. @@ -318,3 +318,13 @@ func userInfoFromName(name string) string { return buf.String() } + +// GenerateSessionID returns a sessionID that can be used in tests. +func GenerateSessionID(username string) string { + return fmt.Sprintf("%s-session_id", username) +} + +// GenerateEncryptionKey returns an encryption key that can be used in tests. +func GenerateEncryptionKey(brokerName string) string { + return fmt.Sprintf("%s-key", brokerName) +} From 51817fe6757f15d1c07b6c836ead8a1c6b8d29b0 Mon Sep 17 00:00:00 2001 From: denisonbarbosa Date: Tue, 19 Sep 2023 07:57:08 -0400 Subject: [PATCH 5/5] Add TestStartAndEndSession to manager_test This test purpose is to test concurrent calls to NewSession and EndSession on the manager, using different brokers for different users. It's very verbose on the assertions, but it's a well needed test. --- internal/brokers/manager_test.go | 76 ++++++++++++++++++++++++++++++++ 1 file changed, 76 insertions(+) diff --git a/internal/brokers/manager_test.go b/internal/brokers/manager_test.go index 59cf78401..c082bf9c1 100644 --- a/internal/brokers/manager_test.go +++ b/internal/brokers/manager_test.go @@ -7,6 +7,7 @@ import ( "os" "path/filepath" "strings" + "sync" "testing" "github.com/stretchr/testify/require" @@ -287,6 +288,81 @@ func TestEndSession(t *testing.T) { } } +func TestStartAndEndSession(t *testing.T) { + t.Parallel() + + cfgDir := t.TempDir() + b1 := newBrokerForTests(t, cfgDir, t.Name()+"_Broker1") + b2 := newBrokerForTests(t, cfgDir, t.Name()+"_Broker2") + + m, err := brokers.NewManager(context.Background(), []string{b1.Name, b2.Name}, brokers.WithCfgDir(cfgDir)) + require.NoError(t, err, "Setup: could not create manager") + + // Fetches the broker IDs + for _, broker := range m.AvailableBrokers() { + if broker.Name == b1.Name { + b1.ID = broker.ID + } else if broker.Name == b2.Name { + b2.ID = broker.ID + } + } + + /* Starting the sessions */ + var firstID, firstKey, secondID, secondKey *string + var firstErr, secondErr *error + wg := sync.WaitGroup{} + wg.Add(1) + go func() { + defer wg.Done() + id, key, err := m.NewSession(b1.ID, "user1", "some_lang") + firstID, firstKey, firstErr = &id, &key, &err + }() + wg.Add(1) + go func() { + defer wg.Done() + id, key, err := m.NewSession(b2.ID, "user2", "some_lang") + secondID, secondKey, secondErr = &id, &key, &err + }() + wg.Wait() + + require.NoError(t, *firstErr, "First NewSession should not return an error, but did") + require.NoError(t, *secondErr, "Second NewSession should not return an error, but did") + + require.Equal(t, b1.ID+"-"+testutils.GenerateSessionID("user1"), *firstID, "First NewSession should return the expected session ID, but did not") + require.Equal(t, testutils.GenerateEncryptionKey(b1.Name), *firstKey, "First NewSession should return the expected encryption key, but did not") + require.Equal(t, b2.ID+"-"+testutils.GenerateSessionID("user2"), *secondID, "Second NewSession should return the expected session ID, but did not") + require.Equal(t, testutils.GenerateEncryptionKey(b2.Name), *secondKey, "Second NewSession should return the expected encryption key, but did not") + + assignedBroker, err := m.BrokerFromSessionID(*firstID) + require.NoError(t, err, "First NewSession should have assigned a broker for the session, but did not") + require.Equal(t, b1.Name, assignedBroker.Name, "First NewSession should have assigned the expected broker for the session, but did not") + assignedBroker, err = m.BrokerFromSessionID(*secondID) + require.NoError(t, err, "Second NewSession should have assigned a broker for the session, but did not") + require.Equal(t, b2.Name, assignedBroker.Name, "Second NewSession should have assigned the expected broker for the session, but did not") + + /* Ending the sessions */ + wg.Add(1) + go func() { + defer wg.Done() + *firstErr = m.EndSession(*firstID) + }() + wg.Add(1) + go func() { + defer wg.Done() + *secondErr = m.EndSession(*secondID) + }() + wg.Wait() + + require.NoError(t, *firstErr, "First EndSession should not return an error, but did") + require.NoError(t, *secondErr, "Second EndSession should not return an error, but did") + + _, err = m.BrokerFromSessionID(*firstID) + require.Error(t, err, "First EndSession should have removed the broker for the session, but did not") + + _, err = m.BrokerFromSessionID(*secondID) + require.Error(t, err, "Second EndSession should have removed the broker for the session, but did not") +} + func TestMain(m *testing.M) { testutils.InstallUpdateFlag() flag.Parse()