github.com/Axway/agent-sdk@v1.1.101/pkg/notification/notification_test.go (about)

     1  package notification
     2  
     3  import (
     4  	"testing"
     5  	"time"
     6  
     7  	"github.com/stretchr/testify/assert"
     8  )
     9  
    10  const defTimeout = 5
    11  
    12  type chanData struct {
    13  	name        string
    14  	msgReceived interface{}      // The message received by the channel
    15  	msgChan     chan interface{} // The channel receiving messages
    16  	closeChan   chan struct{}    // Channel to close the for loop waiting for messages
    17  	notifChan   chan int         // Channel to notify the test to continue validation
    18  }
    19  
    20  func createTestChannel(t *testing.T, name string, isSource bool) *chanData {
    21  	thisChan := &chanData{
    22  		name:      name,
    23  		msgChan:   make(chan interface{}),
    24  		closeChan: make(chan struct{}),
    25  		notifChan: make(chan int, 1),
    26  	}
    27  
    28  	go func(t *testing.T) {
    29  		if isSource {
    30  			// source channels only need to be stopped in this test, not listend too
    31  			for {
    32  				select {
    33  				case <-thisChan.closeChan:
    34  					return
    35  				}
    36  			}
    37  		} else {
    38  			// output channels need to listen for stops and receive messages
    39  			for {
    40  				select {
    41  				case <-thisChan.closeChan:
    42  					return
    43  				case msg, ok := <-thisChan.msgChan:
    44  					if ok {
    45  						t.Logf("message received %s", thisChan.name)
    46  						thisChan.msgReceived = msg
    47  						thisChan.notifChan <- 1
    48  					}
    49  				}
    50  			}
    51  		}
    52  	}(t)
    53  
    54  	return thisChan
    55  }
    56  
    57  func channelTimeout(notifChan chan int, timeout int) {
    58  	// Write to a notify channel after waiting timeout seconds
    59  	time.Sleep(time.Duration(timeout) * time.Second)
    60  	select {
    61  	case <-notifChan:
    62  	default:
    63  		notifChan <- 2
    64  	}
    65  }
    66  
    67  func closeChannels(cd *chanData) {
    68  	close(cd.closeChan)
    69  	close(cd.msgChan)
    70  	close(cd.notifChan)
    71  	<-cd.closeChan
    72  	<-cd.msgChan
    73  	<-cd.notifChan
    74  }
    75  
    76  func TestRegisterNotifier(t *testing.T) {
    77  
    78  	// Create a new Notifier
    79  	serv1Name := "regnotifier"
    80  	serv1ChanData := createTestChannel(t, serv1Name, true)
    81  	notifier1, err := RegisterNotifier(serv1Name, serv1ChanData.msgChan)
    82  	// Test GetName
    83  	assert.Equal(t, notifier1.GetName(), serv1Name, "GetName did not return what was expected")
    84  	assert.Nil(t, err, "Error returned by RegisterNotifier: %s", err)
    85  	assert.Len(t, notifiers, 1, "The length of notifiers should have been 1")
    86  
    87  	// Attempt to create a notifier with a name that already exists
    88  	_, err = RegisterNotifier(serv1Name, serv1ChanData.msgChan)
    89  	assert.NotNil(t, err, "RegisterNotifier should have returned an err")
    90  	assert.Len(t, notifiers, 1, "The length of notifiers should have been 1")
    91  
    92  	closeChannels(serv1ChanData)
    93  	delete(notifiers, serv1Name)
    94  }
    95  
    96  func TestOneSubscriber(t *testing.T) {
    97  	// Create a new Notifier
    98  	serv1Name := "onenotifier"
    99  	serv1ChanData := createTestChannel(t, serv1Name, true)
   100  	notifier1, err := RegisterNotifier(serv1Name, serv1ChanData.msgChan)
   101  	notifier1.Start()
   102  	assert.Nil(t, err, "Error returned by RegisterNotifier: %s", err)
   103  	assert.Len(t, notifiers, 1, "The length of notifiers should have been 1")
   104  
   105  	// Create an output channel
   106  	output1Name := "oneoutput"
   107  	output1ChanData := createTestChannel(t, output1Name, false)
   108  
   109  	// Subscribe to a notifier that dows not exist
   110  	subscriberBad, err := Subscribe("bad-notifier", output1ChanData.msgChan)
   111  	assert.Nil(t, subscriberBad, "Expected the Subscribe call to return a nil Subscriber")
   112  	assert.NotNil(t, err, "Expected an error to be returned, since the notifier name does not exist")
   113  
   114  	// Subscribe to a good notifier
   115  	subscriber1, err := Subscribe(serv1Name, output1ChanData.msgChan)
   116  	assert.NotNil(t, subscriber1, "The returned subscriber should not have been nil")
   117  	assert.NotEqual(t, "", subscriber1.GetID(), "An ID was not returned by the subscribe call")
   118  	assert.Nil(t, err, "An error was returned from the Subscribe, when it was not expected")
   119  
   120  	// Send a message to the source channel, receive on 1 subscriber
   121  	testMessage := "test message 1"
   122  	serv1ChanData.msgChan <- testMessage
   123  
   124  	// Start channel timeout
   125  	go channelTimeout(output1ChanData.notifChan, defTimeout)
   126  	<-output1ChanData.notifChan // Wait for message to be received
   127  
   128  	assert.NotNil(t, output1ChanData.msgReceived, "Expected a message to have been received")
   129  	assert.Equal(t, testMessage, output1ChanData.msgReceived.(string), "The message received was not the expected message")
   130  
   131  	closeChannels(serv1ChanData)
   132  	// closeChannels(output1ChanData)
   133  	delete(notifiers, serv1Name)
   134  }
   135  
   136  func TestTwoSubscribers(t *testing.T) {
   137  	// Create a new Notifier
   138  	serv1Name := "twonotifier"
   139  	serv1ChanData := createTestChannel(t, serv1Name, true)
   140  	notifier1, err := RegisterNotifier(serv1Name, serv1ChanData.msgChan)
   141  	notifier1.Start()
   142  	assert.Nil(t, err, "Error returned by RegisterNotifier: %s", err)
   143  	assert.Len(t, notifiers, 1, "The length of notifiers should have been 1")
   144  
   145  	// Create output channels
   146  	output1Name := "twooutput1"
   147  	output1ChanData := createTestChannel(t, output1Name, false)
   148  	output2Name := "twooutput2"
   149  	output2ChanData := createTestChannel(t, output2Name, false)
   150  
   151  	// Add 2 subscribers
   152  	subscriber1, err := Subscribe(serv1Name, output1ChanData.msgChan)
   153  	assert.NotNil(t, subscriber1, "The returned subscriber should not have been nil")
   154  	assert.NotEqual(t, "", subscriber1.GetID(), "An ID was not returned by the subscribe call")
   155  	assert.Nil(t, err, "An error was returned from Subscribe, when it was not expected")
   156  	subscriber2, err := Subscribe(serv1Name, output2ChanData.msgChan)
   157  	assert.NotNil(t, subscriber2, "The returned subscriber should not have been nil")
   158  	assert.NotEqual(t, "", subscriber2.GetID(), "An ID was not returned by the subscribe call")
   159  	assert.Nil(t, err, "An error was returned from Subscribe, when it was not expected")
   160  	assert.Len(t, notifier1.(*channelNotifier).subscribers, 2, "Expected the notifier to have 2 subscribers")
   161  
   162  	testMessage := "test message 2 subs"
   163  	serv1ChanData.msgChan <- testMessage
   164  
   165  	// Start channel timeout
   166  	go channelTimeout(output1ChanData.notifChan, defTimeout)
   167  	go channelTimeout(output2ChanData.notifChan, defTimeout)
   168  	<-output1ChanData.notifChan // Wait for message to be received on output1
   169  	<-output2ChanData.notifChan // Wait for message to be received on output2
   170  
   171  	assert.NotNil(t, output1ChanData.msgReceived, "Expected a message to have been received on output1")
   172  	assert.Equal(t, testMessage, output1ChanData.msgReceived.(string), "The message received on output1 was not the expected message")
   173  	assert.NotNil(t, output2ChanData.msgReceived, "Expected a message to have been received on output2")
   174  	assert.Equal(t, testMessage, output2ChanData.msgReceived.(string), "The message received on output2 was not the expected message")
   175  
   176  	closeChannels(serv1ChanData)
   177  	closeChannels(output1ChanData)
   178  	closeChannels(output2ChanData)
   179  	delete(notifiers, serv1Name)
   180  }
   181  
   182  func TestStopUnsubscribe(t *testing.T) {
   183  
   184  	// Create a new Notifier
   185  	serv1Name := "stopnotifier"
   186  	serv1ChanData := createTestChannel(t, serv1Name, true)
   187  	notifier1, err := RegisterNotifier(serv1Name, serv1ChanData.msgChan)
   188  	notifier1.Start()
   189  	assert.Nil(t, err, "Error returned by RegisterNotifier: %s", err)
   190  	assert.Len(t, notifiers, 1, "The length of notifiers should have been 1")
   191  
   192  	// Create output channels
   193  	output1Name := "stopoutput1"
   194  	output1ChanData := createTestChannel(t, output1Name, false)
   195  	output2Name := "stopoutput2"
   196  	output2ChanData := createTestChannel(t, output2Name, false)
   197  	output3Name := "stopoutput3"
   198  	output3ChanData := createTestChannel(t, output3Name, false)
   199  
   200  	// Add 2 subscribers
   201  	subscriber1, err := Subscribe(serv1Name, output1ChanData.msgChan)
   202  	assert.NotNil(t, subscriber1, "The returned subscriber should not have been nil")
   203  	assert.NotEqual(t, "", subscriber1.GetID(), "An ID was not returned by the subscribe call")
   204  	assert.Nil(t, err, "An error was returned from Subscribe, when it was not expected")
   205  	subscriber2, err := Subscribe(serv1Name, output2ChanData.msgChan)
   206  	assert.NotNil(t, subscriber2, "The returned subscriber should not have been nil")
   207  	assert.NotEqual(t, "", subscriber2.GetID(), "An ID was not returned by the subscribe call")
   208  	assert.Nil(t, err, "An error was returned from Subscribe, when it was not expected")
   209  	subscriber3, err := Subscribe(serv1Name, output3ChanData.msgChan)
   210  	assert.NotNil(t, subscriber3, "The returned subscriber should not have been nil")
   211  	assert.NotEqual(t, "", subscriber3.GetID(), "An ID was not returned by the subscribe call")
   212  	assert.Nil(t, err, "An error was returned from Subscribe, when it was not expected")
   213  	assert.Len(t, notifier1.(*channelNotifier).subscribers, 3, " Expected the notifier to have 3 subscribers")
   214  
   215  	// Unsubscribe output3
   216  	err = Unsubscribe("fakeName", subscriber3.GetID())
   217  	assert.NotNil(t, err, "Expected an error to be returned when unsubscribing from a non-existent notifier")
   218  	err = notifier1.Unsubscribe("fakeID")
   219  	assert.NotNil(t, err, "Expected an error to be returned when unsubscribing with an ID that does not exist")
   220  	err = Unsubscribe(serv1Name, subscriber3.GetID())
   221  	assert.Nil(t, err, "An error was returned from Unsubscribe, when it was not expected")
   222  	assert.Len(t, notifier1.(*channelNotifier).subscribers, 2, " Expected the notifier to have 2 subscribers")
   223  
   224  	// Unsubscribe subscriber2
   225  	subscriber2.Close()
   226  	assert.Len(t, notifier1.(*channelNotifier).subscribers, 1, " Expected the notifier to have 1 subscribers")
   227  
   228  	// Close the notifier, the subscribers should close too
   229  	notifier1.Stop()
   230  	val1, ok1 := <-output1ChanData.msgChan
   231  	assert.Nil(t, val1, "Didn't expect a message on the channel")
   232  	assert.False(t, ok1, "Expected the message channel to be closed")
   233  
   234  	assert.Len(t, notifier1.(*channelNotifier).subscribers, 0, " Expected the notifier to have 0 subscribers")
   235  
   236  	close(serv1ChanData.closeChan)
   237  	delete(notifiers, serv1Name)
   238  }