我尝试使用Unirest.get(...).asObjectAsync(...)更新具有计划任务的资源。要停止使用Unirest的程序,需要调用Unirest.shutdown();退出其事件循环和客户端。但是,如果一些线程在成功关闭之后调用Unirest的请求方法,则程序无法退出。
下面的代码是一个非常简单的示例:我启动一个线程,该线程在1.5秒后执行一个GET请求,并在它成功时打印状态消息。同时,在主线程上,Unirest被关闭。(请注意,这个示例使用asStringAsync(...)和一个非常简单的线程来简化。)
import com.mashape.unirest.http.HttpResponse;
import com.mashape.unirest.http.Unirest;
import com.mashape.unirest.http.async.Callback;
import com.mashape.unirest.http.exceptions.UnirestException;
import java.io.IOException;
public class Main {
public static void main(String... args) throws IOException, InterruptedException {
new Thread(() -> {
try {
Thread.sleep(1500);
} catch (InterruptedException e) {
e.printStackTrace();
}
Unirest.get("http://example.org").asStringAsync(new Callback<String>() {
@Override
public void completed(HttpResponse<String> response) {
System.out.println(response.getStatusText());
}
@Override
public void failed(UnirestException e) {
System.out.println("failed");
}
@Override
public void cancelled() {
System.out.println("cancelled");
}
});
}).start();
Unirest.shutdown();
}
}我所期望的是这些案件中的任何一个:
我得到的是:
如何使用Unirest处理一个优雅的出口?我是否应该重组这个项目(如果是的话,如何重组)?
我在Windows上使用Java 8,在IntelliJ Idea 14.1.5中运行代码。我使用的最简单的依赖项是:
<dependency>
<groupId>com.mashape.unirest</groupId>
<artifactId>unirest-java</artifactId>
<version>1.4.7</version>
</dependency>发布于 2016-03-21 22:38:53
在您的例子中,您已经生成了一个运行异步调用的线程。shutdown()调用位于主线程中,因此在调用线程生成时,shutdown()将在第一次调用Unirest的asStringAsync()方法之前被调用。
这是对..Async()的第一次调用,它实例化了最终需要关闭的线程池--在您调用关机方法时没有什么可关闭的,因此它是不操作的。它将在您创建的线程中实例化。
这里的解决方案是删除您创建的线程,并使用Unirest提供的Future对象。在执行异步调用时,Unirest处理线程本身,并且可以根据需要输入回调逻辑。
public static void main(String... args) throws IOException, InterruptedException, ExecutionException {
Future<HttpResponse<String>> asyncCall = Unirest.get("http://thecatapi.com/api/images/get?format=xml&results_per_page=20").asStringAsync(new Callback<String>() {
@Override
public void completed(HttpResponse<String> response) {
System.out.println(response.getStatusText());
}
@Override
public void failed(UnirestException e) {
System.out.println("failed");
}
@Override
public void cancelled() {
System.out.println("cancelled");
}
});
HttpResponse<String> httpResponse = asyncCall.get(); // Can also use Future.isDone(), etc
// System.out.println(httpResponse.getBody());
Unirest.shutdown();
}发布于 2020-06-23 19:54:40
asyncCall.get()将阻止调用,因此最好这样做:
asyncCall.thenAcceptAsync((result)->{
if (null != result && !result.isEmpty()) {
// do your business logic after response and then close Unirest
Unirest.shutdown();
}
});
}但是,在清理资源的情况下,您可以重复使用同一个已创建的资源,并注册一个关闭钩子,在JVM关闭期间清除所有内容。
参考资料:http://kong.github.io/unirest-java/#configuration
https://stackoverflow.com/questions/32873070
复制相似问题