@@ -26,39 +26,55 @@ import android.os.Looper
26
26
import androidx.activity.ComponentActivity
27
27
import org.assertj.core.api.Assertions.assertThat
28
28
import org.junit.After
29
+ import org.junit.Before
29
30
import org.junit.Test
30
31
import org.junit.runner.RunWith
32
+ import org.mockito.kotlin.mock
33
+ import org.mockito.kotlin.whenever
31
34
import org.robolectric.Robolectric
32
35
import org.robolectric.RobolectricTestRunner
33
36
import org.robolectric.Shadows.shadowOf
37
+ import kotlin.time.Duration.Companion.minutes
34
38
35
39
@RunWith(RobolectricTestRunner ::class )
36
40
class CheckoutWebViewContainerTest {
37
41
42
+ private val mockCacheClock = mock<CheckoutWebView .CheckoutWebViewCacheClock >()
43
+
44
+ @Before
45
+ fun setUp () {
46
+ CheckoutWebView .cacheClock = mockCacheClock
47
+ }
48
+
38
49
@After
39
50
fun tearDown () {
40
51
CheckoutWebView .clearCache()
52
+ shadowOf(Looper .getMainLooper()).runToEndOfTasks()
41
53
}
42
54
43
55
@Test
44
- fun `should destroy FallbackWebView when it is removed` () {
56
+ fun `should destroy FallbackWebView when it is removed in all cases ` () {
45
57
Robolectric .buildActivity(ComponentActivity ::class .java).use { activityController ->
46
- val activity = activityController.get()
58
+ withPreloadingEnabled {
59
+ val activity = activityController.get()
47
60
48
- val container = CheckoutWebViewContainer (activity)
49
- val fallbackView = FallbackWebView (activity)
50
- val shadow = shadowOf(fallbackView)
61
+ val container = CheckoutWebViewContainer (activity)
62
+ val fallbackView = FallbackWebView (activity)
63
+ val shadow = shadowOf(fallbackView)
51
64
52
- container.addView(fallbackView)
53
- assertThat(shadow.wasDestroyCalled()).isFalse()
65
+ container.addView(fallbackView)
66
+ assertThat(shadow.wasDestroyCalled()).isFalse()
54
67
55
- container.removeView(fallbackView)
56
- assertThat(shadow.wasDestroyCalled()).isTrue()
68
+ container.removeView(fallbackView)
69
+
70
+ assertThat(shadow.wasDestroyCalled()).isTrue()
71
+ }
57
72
}
58
73
}
59
74
75
+ // cache entries are essentially immediately stale if preloading is disabled
60
76
@Test
61
- fun `should destroy CheckoutWebView when it is removed if preloading disabled` () {
77
+ fun `should destroy CheckoutWebView when retainCacheEntry is IF_NOT_STALE and preloading is disabled` () {
62
78
Robolectric .buildActivity(ComponentActivity ::class .java).use { activityController ->
63
79
val activity = activityController.get()
64
80
@@ -69,6 +85,7 @@ class CheckoutWebViewContainerTest {
69
85
container.addView(checkoutWebView)
70
86
assertThat(shadow.wasDestroyCalled()).isFalse()
71
87
88
+ CheckoutWebViewContainer .retainCacheEntry = RetainCacheEntry .IF_NOT_STALE
72
89
container.removeView(checkoutWebView)
73
90
shadowOf(Looper .getMainLooper()).runToEndOfTasks()
74
91
@@ -77,9 +94,11 @@ class CheckoutWebViewContainerTest {
77
94
}
78
95
79
96
@Test
80
- fun `should destroy CheckoutWebView when it is removed if preloading and retain is false ` () {
97
+ fun `should destroy CheckoutWebView when retainCacheEntry is IF_NOT_STALE and entry is stale ` () {
81
98
Robolectric .buildActivity(ComponentActivity ::class .java).use { activityController ->
82
99
withPreloadingEnabled {
100
+ whenever(mockCacheClock.currentTimeMillis()).thenReturn(System .currentTimeMillis())
101
+
83
102
val activity = activityController.get()
84
103
85
104
val container = CheckoutWebViewContainer (activity)
@@ -89,6 +108,9 @@ class CheckoutWebViewContainerTest {
89
108
container.addView(checkoutWebView)
90
109
assertThat(shadow.wasDestroyCalled()).isFalse()
91
110
111
+ CheckoutWebViewContainer .retainCacheEntry = RetainCacheEntry .IF_NOT_STALE
112
+ makeCacheEntryStale()
113
+
92
114
container.removeView(checkoutWebView)
93
115
shadowOf(Looper .getMainLooper()).runToEndOfTasks()
94
116
@@ -98,9 +120,33 @@ class CheckoutWebViewContainerTest {
98
120
}
99
121
100
122
@Test
101
- fun `should not destroy CheckoutWebView when it is removed if preloading and retain is true` () {
123
+ fun `should not destroy non-stale CheckoutWebView when retainCacheEntry == IF_NOT_STALE and entry is not stale` () {
124
+ Robolectric .buildActivity(ComponentActivity ::class .java).use { activityController ->
125
+ withPreloadingEnabled {
126
+ val activity = activityController.get()
127
+
128
+ val container = CheckoutWebViewContainer (activity)
129
+ val checkoutWebView = CheckoutWebView .cacheableCheckoutView(" https://shopify.dev" , activity, true )
130
+ val shadow = shadowOf(checkoutWebView)
131
+
132
+ container.addView(checkoutWebView)
133
+ assertThat(shadow.wasDestroyCalled()).isFalse()
134
+
135
+ CheckoutWebViewContainer .retainCacheEntry = RetainCacheEntry .IF_NOT_STALE
136
+ container.removeView(checkoutWebView)
137
+ shadowOf(Looper .getMainLooper()).runToEndOfTasks()
138
+
139
+ assertThat(shadow.wasDestroyCalled()).isFalse()
140
+ }
141
+ }
142
+ }
143
+
144
+ @Test
145
+ fun `should not destroy CheckoutWebView when retainCacheEntry == YES and entry is stale` () {
102
146
Robolectric .buildActivity(ComponentActivity ::class .java).use { activityController ->
103
147
withPreloadingEnabled {
148
+ whenever(mockCacheClock.currentTimeMillis()).thenReturn(System .currentTimeMillis())
149
+
104
150
val activity = activityController.get()
105
151
106
152
val container = CheckoutWebViewContainer (activity)
@@ -110,13 +156,44 @@ class CheckoutWebViewContainerTest {
110
156
container.addView(checkoutWebView)
111
157
assertThat(shadow.wasDestroyCalled()).isFalse()
112
158
113
- CheckoutWebViewContainer .retainCache = true
159
+ CheckoutWebViewContainer .retainCacheEntry = RetainCacheEntry .YES
160
+ makeCacheEntryStale()
161
+
114
162
container.removeView(checkoutWebView)
115
163
shadowOf(Looper .getMainLooper()).runToEndOfTasks()
164
+ assertThat(shadow.wasDestroyCalled()).isFalse()
165
+ assertThat(CheckoutWebViewContainer .retainCacheEntry).isEqualTo(RetainCacheEntry .IF_NOT_STALE )
166
+ }
167
+ }
168
+ }
169
+
170
+ @Test
171
+ fun `should not destroy CheckoutWebView when retainCacheEntry == YES and entry is not stale` () {
172
+ Robolectric .buildActivity(ComponentActivity ::class .java).use { activityController ->
173
+ withPreloadingEnabled {
174
+ whenever(mockCacheClock.currentTimeMillis()).thenReturn(System .currentTimeMillis())
175
+
176
+ val activity = activityController.get()
177
+
178
+ val container = CheckoutWebViewContainer (activity)
179
+ val checkoutWebView = CheckoutWebView .cacheableCheckoutView(" https://shopify.dev" , activity, true )
180
+ val shadow = shadowOf(checkoutWebView)
116
181
182
+ container.addView(checkoutWebView)
117
183
assertThat(shadow.wasDestroyCalled()).isFalse()
118
- assertThat(CheckoutWebViewContainer .retainCache).isFalse()
184
+
185
+ CheckoutWebViewContainer .retainCacheEntry = RetainCacheEntry .YES
186
+
187
+ container.removeView(checkoutWebView)
188
+ shadowOf(Looper .getMainLooper()).runToEndOfTasks()
189
+ assertThat(shadow.wasDestroyCalled()).isFalse()
190
+ assertThat(CheckoutWebViewContainer .retainCacheEntry).isEqualTo(RetainCacheEntry .IF_NOT_STALE )
119
191
}
120
192
}
121
193
}
194
+
195
+ private fun makeCacheEntryStale () {
196
+ val initialTime = mockCacheClock.currentTimeMillis()
197
+ whenever(mockCacheClock.currentTimeMillis()).thenReturn(initialTime.plus(60 * 10 * 1000 ))
198
+ }
122
199
}
0 commit comments