github.com/blend/go-sdk@v1.20220411.3/cron/immediately_then_test.go (about) 1 /* 2 3 Copyright (c) 2022 - Present. Blend Labs, Inc. All rights reserved 4 Use of this source code is governed by a MIT license that can be found in the LICENSE file. 5 6 */ 7 8 package cron 9 10 import ( 11 "fmt" 12 "sync" 13 "sync/atomic" 14 "testing" 15 "time" 16 17 "github.com/blend/go-sdk/assert" 18 ) 19 20 func Test_Immediately(t *testing.T) { 21 t.Parallel() 22 its := assert.New(t) 23 24 ts := time.Date(2019, 9, 8, 12, 11, 10, 9, time.UTC) 25 26 is := Immediately() 27 its.Equal(StringScheduleImmediately, is.String()) 28 next := is.Next(ts) 29 its.NotEqual(ts, next) 30 next = is.Next(ts) 31 its.True(next.IsZero()) 32 33 thenSchedule := EverySecond() 34 is = Immediately().Then(thenSchedule).(*ImmediateSchedule) 35 its.Equal(fmt.Sprintf("%s %v", StringScheduleImmediatelyThen, thenSchedule), is.String()) 36 37 next = is.Next(ts) 38 its.NotEqual(ts, next) 39 its.Equal(1, is.didRun) 40 41 next = is.Next(ts) 42 its.Equal(ts.Add(time.Second), next) 43 44 // another one to be safe. 45 next = is.Next(ts) 46 its.Equal(ts.Add(time.Second), next) 47 its.Equal(1, is.didRun) 48 } 49 50 func Test_Immediately_new(t *testing.T) { 51 t.Parallel() 52 its := assert.New(t) 53 54 ts := time.Date(2019, 9, 8, 12, 11, 10, 9, time.UTC) 55 56 is := new(ImmediateSchedule) 57 its.Equal(StringScheduleImmediately, is.String()) 58 next := is.Next(ts) 59 its.NotEqual(ts, next) 60 next = is.Next(ts) 61 its.True(next.IsZero()) 62 63 thenSchedule := EverySecond() 64 is = new(ImmediateSchedule).Then(thenSchedule).(*ImmediateSchedule) 65 its.Equal(fmt.Sprintf("%s %v", StringScheduleImmediatelyThen, thenSchedule), is.String()) 66 67 next = is.Next(ts) 68 its.NotEqual(ts, next) 69 its.Equal(1, is.didRun) 70 71 next = is.Next(ts) 72 its.Equal(ts.Add(time.Second), next) 73 74 // another one to be safe. 75 next = is.Next(ts) 76 its.Equal(ts.Add(time.Second), next) 77 its.Equal(1, is.didRun) 78 } 79 80 func Test_Immediately_Then(t *testing.T) { 81 t.Parallel() 82 its := assert.New(t) 83 84 s := Immediately().Then(EveryHour()) 85 its.NotNil(s.Next(Zero)) 86 now := Now() 87 next := s.Next(Now()) 88 its.True(next.Sub(now) > time.Minute, fmt.Sprintf("%v", next.Sub(now))) 89 its.True(next.Sub(now) < (2 * time.Hour)) 90 } 91 92 func Test_ImmediateSchedule_parallel(t *testing.T) { 93 t.Parallel() 94 its := assert.New(t) 95 96 ts := time.Date(2019, 9, 8, 12, 11, 10, 9, time.UTC) 97 98 var nextCount int32 99 next := ScheduleFunc(func(ts time.Time) time.Time { 100 atomic.AddInt32(&nextCount, 1) 101 return ts.Add(time.Minute) 102 }) 103 104 is := Immediately().Then(next) 105 106 start := make(chan struct{}) 107 108 now := Now() 109 times := make(chan time.Time, 10) 110 wg := sync.WaitGroup{} 111 wg.Add(10) 112 for x := 0; x < 10; x++ { 113 go func() { 114 defer wg.Done() 115 <-start 116 out := is.Next(ts) 117 times <- out 118 }() 119 } 120 121 close(start) 122 wg.Wait() 123 124 var allTimes []time.Time 125 for x := 0; x < 10; x++ { 126 allTimes = append(allTimes, <-times) 127 } 128 129 its.AnyCount(allTimes, 1, func(v interface{}) bool { 130 typed, _ := v.(time.Time) 131 return typed.After(now) && typed.Sub(now) < time.Second 132 }, "(1) of the times should be '''now''' and the other 9 should have gone through the next schedule") 133 its.AnyCount(allTimes, 9, func(v interface{}) bool { 134 return v.(time.Time).Equal(ts.Add(time.Minute)) 135 }, "(1) of the times should be '''now''' and the other 9 should have gone through the next schedule") 136 }