@@ -68,71 +68,74 @@ describe("Exponential backoff delay", () => {
68
68
describe ( "with rate 2, backoffLimit 8000 ms" , ( ) => {
69
69
// The initial delay shall be 1 s
70
70
const initialDelay = 1000 ;
71
- const exponentialBackoffParams : ExponentialBackoffParams = {
71
+ const exponentialBackoff : ExponentialBackoffParams = {
72
72
backoffRate : 2 ,
73
73
// We put the ceiling at exactly 8000 ms
74
74
backoffLimit : 8000 ,
75
75
} ;
76
+ const attempts : [ number , number ] [ ] = [
77
+ [ 1000 , 0 ] ,
78
+ [ 2000 , 1 ] ,
79
+ [ 4000 , 2 ] ,
80
+ [ 8000 , 3 ] ,
81
+ [ 8000 , 4 ] ,
82
+ ] ;
76
83
it ( "will never be more than 8000 ms with rate set to 2" , ( ) => {
77
- expect (
78
- calculateRetryDelayFactor ( exponentialBackoffParams , initialDelay , 0 ) ,
79
- ) . toBe ( 1000 ) ;
80
- expect (
81
- calculateRetryDelayFactor ( exponentialBackoffParams , initialDelay , 1 ) ,
82
- ) . toBe ( 2000 ) ;
83
- expect (
84
- calculateRetryDelayFactor ( exponentialBackoffParams , initialDelay , 2 ) ,
85
- ) . toBe ( 4000 ) ;
86
- expect (
87
- calculateRetryDelayFactor ( exponentialBackoffParams , initialDelay , 3 ) ,
88
- ) . toBe ( 8000 ) ;
89
- expect (
90
- calculateRetryDelayFactor ( exponentialBackoffParams , initialDelay , 4 ) ,
91
- ) . toBe ( 8000 ) ;
84
+ attempts . forEach ( ( [ delay , failedAttempts ] ) => {
85
+ expect (
86
+ calculateRetryDelayFactor (
87
+ exponentialBackoff ,
88
+ initialDelay ,
89
+ failedAttempts ,
90
+ ) ,
91
+ ) . toBe ( delay ) ;
92
+ } ) ;
92
93
} ) ;
93
94
94
95
it ( "should delay reconnection attempts exponentially" , async ( ) => {
96
+ // Somehow we need to convincen typescript here that "WebSocket" is
97
+ // totally valid. Could be because it doesn't assume WebSocket is part of
98
+ // global / the index key is missing
95
99
const webSocketSpy = jest . spyOn ( global , "WebSocket" as any ) ;
96
100
webSocketSpy . mockImplementation ( ( ) => { } ) ;
97
101
const setTimeoutSpy = jest . spyOn ( global , "setTimeout" ) ;
98
- const sarus = new Sarus ( {
99
- url,
100
- exponentialBackoff : exponentialBackoffParams ,
101
- } ) ;
102
+ const sarus = new Sarus ( { url, exponentialBackoff } ) ;
102
103
expect ( sarus . state ) . toStrictEqual ( {
103
104
kind : "connecting" ,
104
105
failedConnectionAttempts : 0 ,
105
106
} ) ;
106
107
let instance : WebSocket ;
108
+ // Get the first WebSocket instance, and ...
107
109
[ instance ] = webSocketSpy . mock . instances ;
108
110
if ( ! instance . onopen ) {
109
111
throw new Error ( ) ;
110
112
}
113
+ // tell the sarus instance that it is open, and ...
111
114
instance . onopen ( new Event ( "open" ) ) ;
112
115
if ( ! instance . onclose ) {
113
116
throw new Error ( ) ;
114
117
}
118
+ // close it immediately
115
119
instance . onclose ( new CloseEvent ( "close" ) ) ;
120
+ expect ( sarus . state ) . toStrictEqual ( {
121
+ kind : "closed" ,
122
+ failedConnectionAttempts : 0 ,
123
+ } ) ;
116
124
117
125
let cb : Sarus [ "connect" ] ;
118
126
// We iteratively call sarus.connect() and let it fail, seeing
119
127
// if it reaches 8000 as a delay and stays there
120
- const attempts : [ number , number ] [ ] = [
121
- [ 1000 , 1 ] ,
122
- [ 2000 , 2 ] ,
123
- [ 4000 , 3 ] ,
124
- [ 8000 , 4 ] ,
125
- [ 8000 , 5 ] ,
126
- ] ;
127
- attempts . forEach ( ( [ delay , failedAttempts ] : [ number , number ] ) => {
128
+ attempts . forEach ( ( [ delay , failedAttempts ] ) => {
128
129
const call =
129
130
setTimeoutSpy . mock . calls [ setTimeoutSpy . mock . calls . length - 1 ] ;
130
131
if ( ! call ) {
131
132
throw new Error ( ) ;
132
133
}
134
+ // Make sure that setTimeout was called with the correct delay
133
135
expect ( call [ 1 ] ) . toBe ( delay ) ;
134
136
cb = call [ 0 ] ;
135
137
cb ( ) ;
138
+ // Get the most recent WebSocket instance
136
139
instance =
137
140
webSocketSpy . mock . instances [ webSocketSpy . mock . instances . length - 1 ] ;
138
141
if ( ! instance . onclose ) {
@@ -141,7 +144,7 @@ describe("Exponential backoff delay", () => {
141
144
instance . onclose ( new CloseEvent ( "close" ) ) ;
142
145
expect ( sarus . state ) . toStrictEqual ( {
143
146
kind : "connecting" ,
144
- failedConnectionAttempts : failedAttempts ,
147
+ failedConnectionAttempts : failedAttempts + 1 ,
145
148
} ) ;
146
149
} ) ;
147
150
} ) ;
0 commit comments