• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2012 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.compatibility.common.util;
18 
19 import junit.framework.Assert;
20 
21 import java.util.concurrent.Callable;
22 import java.util.function.BooleanSupplier;
23 import java.util.function.Function;
24 import java.util.function.Supplier;
25 
26 public abstract class PollingCheck {
27     private static final long TIME_SLICE = 50;
28     private static final long DEFAULT_TIMEOUT = 3_000;
29     private static final String DEFAULT_ERROR_MESSAGE = "unexpected timeout";
30 
31     private final long mTimeout;
32     private final String mErrorMessage;
33 
34     public static interface PollingCheckCondition {
canProceed()35         boolean canProceed();
36     }
37 
PollingCheck()38     public PollingCheck() {
39         this(DEFAULT_TIMEOUT, DEFAULT_ERROR_MESSAGE);
40     }
41 
PollingCheck(long timeout)42     public PollingCheck(long timeout) {
43         this(timeout, DEFAULT_ERROR_MESSAGE);
44     }
45 
PollingCheck(long timeout, String errorMessage)46     public PollingCheck(long timeout, String errorMessage) {
47         mTimeout = timeout;
48         mErrorMessage = errorMessage;
49     }
50 
PollingCheck(String errorMessage)51     public PollingCheck(String errorMessage) {
52         this(DEFAULT_TIMEOUT, errorMessage);
53     }
54 
check()55     protected abstract boolean check();
56 
run()57     public void run() {
58         if (check()) {
59             return;
60         }
61 
62         long timeout = mTimeout;
63         while (timeout > 0) {
64             try {
65                 Thread.sleep(TIME_SLICE);
66             } catch (InterruptedException e) {
67                 Assert.fail("unexpected InterruptedException");
68             }
69 
70             if (check()) {
71                 return;
72             }
73 
74             timeout -= TIME_SLICE;
75         }
76 
77         Assert.assertTrue(mErrorMessage, check());
78     }
79 
runWaitAndReturnResult(Supplier<E> supplier, Function<E, Boolean> condition)80     public <E> E runWaitAndReturnResult(Supplier<E> supplier, Function<E, Boolean> condition) {
81         E output = supplier.get();
82         if (condition.apply(output)) {
83             return output;
84         }
85         long timeout = mTimeout;
86         while (timeout > 0) {
87             try {
88                 Thread.sleep(TIME_SLICE);
89             } catch (InterruptedException e) {
90                 Assert.fail("unexpected InterruptedException");
91             }
92 
93             output = supplier.get();
94             if (condition.apply(output)) {
95                 return output;
96             }
97 
98             timeout -= TIME_SLICE;
99         }
100 
101         return output;
102     }
103 
check(CharSequence message, long timeout, Callable<Boolean> condition)104     public static void check(CharSequence message, long timeout, Callable<Boolean> condition)
105             throws Exception {
106         while (timeout > 0) {
107             if (condition.call()) {
108                 return;
109             }
110 
111             Thread.sleep(TIME_SLICE);
112             timeout -= TIME_SLICE;
113         }
114 
115         Assert.fail(message.toString());
116     }
117 
waitFor(final PollingCheckCondition condition)118     public static void waitFor(final PollingCheckCondition condition) {
119         new PollingCheck() {
120             @Override
121             protected boolean check() {
122                 return condition.canProceed();
123             }
124         }.run();
125     }
126 
waitFor(final PollingCheckCondition condition, String errorMessage)127     public static void waitFor(final PollingCheckCondition condition, String errorMessage) {
128         new PollingCheck(errorMessage) {
129             @Override
130             protected boolean check() {
131                 return condition.canProceed();
132             }
133         }.run();
134     }
135 
waitFor(long timeout, final PollingCheckCondition condition)136     public static void waitFor(long timeout, final PollingCheckCondition condition) {
137         new PollingCheck(timeout) {
138             @Override
139             protected boolean check() {
140                 return condition.canProceed();
141             }
142         }.run();
143     }
144 
waitFor(long timeout, BooleanSupplier condition, String errorMessage)145     public static void waitFor(long timeout, BooleanSupplier condition, String errorMessage) {
146         new PollingCheck(timeout, errorMessage) {
147             @Override
148             protected boolean check() {
149                 return condition.getAsBoolean();
150             }
151         }.run();
152     }
153 
waitFor(long timeout, Supplier<E> supplier, Function<E, Boolean> condition)154     public static <E> E waitFor(long timeout, Supplier<E> supplier,
155             Function<E, Boolean> condition) {
156         return new PollingCheck(timeout) {
157             // Not used in the corresponding runWaitAndReturnResult function, Added just to provide
158             // default implementation of abstract check function.
159             @Override
160             protected boolean check() {
161                 return true;
162             }
163         }.runWaitAndReturnResult(supplier, condition);
164     }
165 }
166