unit testingnetworking响应。 debugging时工作,而不是实际运行时

我目前正在尝试testingnetworking响应是否正在被接收。

虽然我明白,这不是我应该做的testing方面,它是对我自己的意愿的好奇心,我希望如果可能的话继续下去。

现在,我已经成功地创build了testing。 一个请求发送到一个齐射队列没有问题。

现在奇怪的是:

该请求从未执行。 以下是我如何testing它的一个想法:

@Test public void testSimpleGetResponseFromServerVolley() throws Exception { final CountDownLatch signal = new CountDownLatch(1); NetworkClass.NetworkListener listener = new NetworkClass.NetworkListener() { @Override public void onResponse(Response response) { assertThat(response != null); System.out.println("Got Response"); signal.countDown(); } @Override public void onError(Throwable error) { System.out.println("No Response"); signal.countDown(); } }; NetworkClass.getResponseFromServer(null, listener); signal.await(); } 

此代码意外地导致testing挂起,并从未完成。

然而,这是我停止失去理解的情况:

如果通过debugging运行testing并逐行执行,则testing成功执行,并收到响应。

我认为正在发生:

当我通过debugdebugging时,volley requestQueue成功进行并发出请求,并在await()被调用之前接收到响应。

当我不通过debugging, await()阻止处理所有的线程。

任何想法如何我可以处理这个?

Solutions Collecting From Web of "unit testingnetworking响应。 debugging时工作,而不是实际运行时"

Volley依靠Looper.getMainLooper()来处理它的执行。 当使用RobolectricTestRunner时,Robolectric会嘲笑这一点,因此无法正确设置,从而导致testing失败。

在我的具体情况下,当我使用断点时,系统确实设置了主循环,因为系统正在利用它来显示断点/debugging工具。 这因此描述了我在最初的问题中发现的行为背后的推理。

现在为了在unit testing中获得真正的networking响应的解决scheme,执行者必须改变为不使用主循环。

作为一个简单的解决scheme,创build一个依赖于Executor.singleThreadExecutor()而不是Main Looper的请求队列。

这是我的意思:

  //Specific test queue that uses a singleThreadExecutor instead of the mainLooper for testing purposes. public RequestQueue newVolleyRequestQueueForTest(final Context context) { File cacheDir = new File(context.getCacheDir(), "cache/volley"); Network network = new BasicNetwork(new HurlStack()); ResponseDelivery responseDelivery = new ExecutorDelivery(Executors.newSingleThreadExecutor()); RequestQueue queue = new RequestQueue(new DiskBasedCache(cacheDir), network, 4, responseDelivery); queue.start(); return queue; } 

然后,在testing过程中将其用作Volley的请求队列。

这里的关键是:

ResponseDelivery responseDelivery = new ExecutorDelivery(Executors.newSingleThreadExecutor());

希望这可以帮助!