github.com/haraldrudell/parl@v0.4.176/debouncer_test.go (about)

     1  /*
     2  © 2021–present Harald Rudell <harald.rudell@gmail.com> (https://haraldrudell.github.io/haraldrudell/)
     3  ISC License
     4  */
     5  
     6  package parl
     7  
     8  import (
     9  	"testing"
    10  	"time"
    11  
    12  	"github.com/haraldrudell/parl/ptime"
    13  	"golang.org/x/exp/slices"
    14  )
    15  
    16  func TestDebouncer(t *testing.T) {
    17  	var value1 = 3
    18  	var value2 = 5
    19  	var debouncePeriod = time.Millisecond
    20  	var noDebounce time.Duration
    21  	var noMaxDelay time.Duration
    22  	var maxDelay1ms = time.Millisecond
    23  	var expValues = []int{value1, value2}
    24  	var expValues1 = []int{value1}
    25  
    26  	var actValues []int
    27  	var t0, t1 time.Time
    28  
    29  	// create debouncer immediately receiving 2 values
    30  	var inputCh = make(chan int, 2)
    31  	inputCh <- value1
    32  	inputCh <- value2
    33  	var receiver NBChan[[]int]
    34  	t0 = time.Now()
    35  	var debouncer = NewDebouncer(
    36  		debouncePeriod,
    37  		noMaxDelay,
    38  		inputCh,
    39  		receiver.Send,
    40  		debouncerPanicErrFn,
    41  	)
    42  
    43  	// actValues should receive a slice of two values
    44  	//	- received because of debounce timer 1 ms
    45  	actValues = <-receiver.Ch()
    46  	t1 = time.Now()
    47  	t.Logf("elapsed debounce: %s", ptime.Duration(t1.Sub(t0)))
    48  	if !slices.Equal(actValues, expValues) {
    49  		t.Errorf("bad receive: %v exp %v", actValues, expValues)
    50  	}
    51  
    52  	// Shutdown should not panic or hang
    53  	t.Log("debouncer.Shutdown…")
    54  	debouncer.Shutdown()
    55  	t.Log("debouncer.Shutdown complete")
    56  
    57  	// create a debouncer receiving no values
    58  	t0 = time.Now()
    59  	debouncer = NewDebouncer(
    60  		debouncePeriod,
    61  		noMaxDelay,
    62  		inputCh,
    63  		receiver.Send,
    64  		debouncerPanicErrFn,
    65  	)
    66  
    67  	// close of input channel should terminate the debouncer
    68  	close(inputCh)
    69  	t.Log("debouncer.Wait…")
    70  	debouncer.Wait()
    71  	t1 = time.Now()
    72  	t.Logf("debouncer.Wait complete: %s", ptime.Duration(t1.Sub(t0)))
    73  
    74  	// create a debouncer with maxDelay
    75  	inputCh = make(chan int, 1)
    76  	inputCh <- value1
    77  	t0 = time.Now()
    78  	debouncer = NewDebouncer(
    79  		noDebounce,
    80  		maxDelay1ms,
    81  		inputCh,
    82  		receiver.Send,
    83  		debouncerPanicErrFn,
    84  	)
    85  
    86  	// maxDelay should release one value
    87  	actValues = <-receiver.Ch()
    88  	t1 = time.Now()
    89  	t.Logf("elapsed maxDelay: %s", ptime.Duration(t1.Sub(t0)))
    90  	if !slices.Equal(actValues, expValues1) {
    91  		t.Errorf("bad receive: %v exp %v", actValues, expValues1)
    92  	}
    93  
    94  	// shutdown should not panic or hang
    95  	debouncer.Shutdown()
    96  
    97  	//t.Fail()
    98  }
    99  
   100  // debouncerPanicErrFn is a debouncer errFN that panics
   101  //   - debuncer does not have any errors
   102  func debouncerPanicErrFn(err error) {
   103  	panic(err)
   104  }