Skip to content

Commit 46952fa

Browse files
jlsherrillMichaelMraka
authored andcommitted
RHELENG-25687: add test for empty notifications
adds a test to guard against notifications being sent with empty advisory lists
1 parent 9d6f363 commit 46952fa

1 file changed

Lines changed: 103 additions & 0 deletions

File tree

evaluator/notifications_test.go

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import (
99
"app/base/utils"
1010
"fmt"
1111
"testing"
12+
"time"
1213

1314
"github.com/bytedance/sonic"
1415
"github.com/stretchr/testify/assert"
@@ -143,3 +144,105 @@ func TestGetSystemTags(t *testing.T) {
143144
assert.Equal(t, expected, tags)
144145
}
145146
}
147+
148+
// TestAdvisoriesNotificationAlreadyNotified verifies that no Kafka message is sent when all
149+
// advisories on the system have already been notified (notified IS NOT NULL). This is the
150+
// exact scenario that caused the blank-email production bug introduced in RHINENG-21786.
151+
func TestAdvisoriesNotificationAlreadyNotified(t *testing.T) {
152+
utils.SkipWithoutDB(t)
153+
core.SetupTestEnvironment()
154+
configure()
155+
156+
mockWriter := mqueue.MockKafkaWriter{}
157+
notificationsPublisher = &mockWriter
158+
159+
advisoryIDs := []int64{1, 2}
160+
database.DeleteAdvisoryAccountData(t, rhAccountID, advisoryIDs)
161+
162+
now := time.Now()
163+
for _, id := range advisoryIDs {
164+
err := database.DB.Create(&models.AdvisoryAccountData{
165+
AdvisoryID: id,
166+
RhAccountID: rhAccountID,
167+
SystemsInstallable: 1,
168+
SystemsApplicable: 1,
169+
Notified: &now,
170+
}).Error
171+
assert.NoError(t, err)
172+
}
173+
defer database.DeleteAdvisoryAccountData(t, rhAccountID, advisoryIDs)
174+
175+
system := &models.SystemPlatform{
176+
ID: systemID,
177+
RhAccountID: rhAccountID,
178+
InventoryID: inventoryID,
179+
DisplayName: "test-display-name",
180+
}
181+
newAdvs := SystemAdvisoryMap{
182+
"RH-1": {AdvisoryID: 1},
183+
"RH-2": {AdvisoryID: 2},
184+
}
185+
186+
err := publishNewAdvisoriesNotification(database.DB, system, orgID, newAdvs)
187+
assert.NoError(t, err)
188+
assert.Empty(t, mockWriter.Messages, "no notification should be sent when all advisories are already notified")
189+
}
190+
191+
// TestAdvisoriesNotificationEmptyAdvisoryMap verifies that no Kafka message is sent when
192+
// publishNewAdvisoriesNotification is called with an empty SystemAdvisoryMap (no advisories
193+
// on the system at all).
194+
func TestAdvisoriesNotificationEmptyAdvisoryMap(t *testing.T) {
195+
utils.SkipWithoutDB(t)
196+
core.SetupTestEnvironment()
197+
configure()
198+
199+
mockWriter := mqueue.MockKafkaWriter{}
200+
notificationsPublisher = &mockWriter
201+
202+
system := &models.SystemPlatform{
203+
ID: systemID,
204+
RhAccountID: rhAccountID,
205+
InventoryID: inventoryID,
206+
DisplayName: "test-display-name",
207+
}
208+
209+
// An empty map means there is nothing to query — no messages should be produced regardless.
210+
publishNewAdvisoriesNotification(database.DB, system, orgID, SystemAdvisoryMap{}) //nolint:errcheck
211+
assert.Empty(t, mockWriter.Messages, "no notification should be sent when the advisory map is empty")
212+
}
213+
214+
// TestGetUnnotifiedAdvisoriesReturnsEmpty documents the return-type contract of
215+
// getUnnotifiedAdvisories: when all candidate advisories are already notified the function
216+
// must return a non-nil empty slice (not nil). This prevents a future nil-vs-empty regression
217+
// from silently bypassing the len == 0 guard in publishNewAdvisoriesNotification.
218+
func TestGetUnnotifiedAdvisoriesReturnsEmpty(t *testing.T) {
219+
utils.SkipWithoutDB(t)
220+
core.SetupTestEnvironment()
221+
configure()
222+
223+
advisoryIDs := []int64{1, 2}
224+
database.DeleteAdvisoryAccountData(t, rhAccountID, advisoryIDs)
225+
226+
now := time.Now()
227+
for _, id := range advisoryIDs {
228+
err := database.DB.Create(&models.AdvisoryAccountData{
229+
AdvisoryID: id,
230+
RhAccountID: rhAccountID,
231+
SystemsInstallable: 1,
232+
SystemsApplicable: 1,
233+
Notified: &now,
234+
}).Error
235+
assert.NoError(t, err)
236+
}
237+
defer database.DeleteAdvisoryAccountData(t, rhAccountID, advisoryIDs)
238+
239+
newAdvs := SystemAdvisoryMap{
240+
"RH-1": {AdvisoryID: 1},
241+
"RH-2": {AdvisoryID: 2},
242+
}
243+
244+
result, err := getUnnotifiedAdvisories(database.DB, rhAccountID, newAdvs)
245+
assert.NoError(t, err)
246+
assert.NotNil(t, result, "result must be a non-nil slice so callers can use len() safely")
247+
assert.Empty(t, result, "no advisories should be returned when all are already notified")
248+
}

0 commit comments

Comments
 (0)