Java ScheduledExecutorService等待资源可用
我的java应用程序有问题。启动应用程序时,应用程序需要连接到另一个应用程序。我的想法是在我的应用程序启动时进行检查,每秒钟检查另一个应用程序是否可用没有等待5分钟之类的条件,只是无限期地等待,直到可用为止 我在下面的抽象示例中尝试了这一点。在此示例中,我的申请将在3次尝试后获得另一个申请Java ScheduledExecutorService等待资源可用,java,multithreading,runnable,callable,Java,Multithreading,Runnable,Callable,我的java应用程序有问题。启动应用程序时,应用程序需要连接到另一个应用程序。我的想法是在我的应用程序启动时进行检查,每秒钟检查另一个应用程序是否可用没有等待5分钟之类的条件,只是无限期地等待,直到可用为止 我在下面的抽象示例中尝试了这一点。在此示例中,我的申请将在3次尝试后获得另一个申请 package main; import java.util.concurrent.Callable; import java.util.concurrent.CancellationException;
package main;
import java.util.concurrent.Callable;
import java.util.concurrent.CancellationException;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.TimeUnit;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
public class Main {
private static final Logger logger = LogManager.getLogger(Main.class);
public static void main(String[] args) {
final Callable<String> sleeper = new Callable<String>() {
// local timer for resource getter
ScheduledExecutorService executor = Executors.newScheduledThreadPool(1);
ScheduledFuture<?> timer;
String returnValue;
@Override
public String call() throws Exception {
// start on first call
if (null == timer) {
logger.info("sleeper - starting getter ...");
timer = executor.scheduleAtFixedRate(new getter(3), 0, 1, TimeUnit.SECONDS);
}
// the right way - this seems to be ugly!
try {
timer.get();
} catch (CancellationException | ExecutionException | InterruptedException e) {
logger.error("sleeper - got an exception ... but nothing bad?!");
}
logger.info("sleeper - returning="+returnValue);
return returnValue;
}
class getter implements Runnable {
int _trys;
int _maxTrys;
String _res = null;
getter(int maxTrys) {
logger.info("getter - init, maxTrys=" + maxTrys);
_maxTrys=maxTrys;
}
@Override
public void run() {
if (null == _res) {
if (_trys<_maxTrys) {
++_trys;
logger.info("getter - sleeping trys="+_trys + "/" + _maxTrys);
} else {
_res = "*MIGHTY RESOURCE*";
logger.info("getter - found resource after "+_trys+" trys!");
}
} else {
logger.info("getter - returning resource to parent");
returnValue = _res; // hand over
this.notify(); // exit?
}
}
}
};
logger.info("Main - starting sleeper");
ScheduledExecutorService sleeperExecutor = Executors.newScheduledThreadPool(1);
Future<String> resource = sleeperExecutor.submit(sleeper);
try {
logger.info("Main - got="+resource.get());
} catch (ExecutionException | InterruptedException e) {
e.printStackTrace();
}
}
}
问候
S.您要连接的资源是什么?数据库、web服务器、消息总线等?有一些资源,但主要资源是数据库。假设:数据库服务器托管在其他地方,您不尝试启动它。我会使用一个数据库连接池,例如,并假设在应用程序启动时一切正常。我不会写任何特殊的开始代码。在您的应用程序进程处于活动状态的整个生命周期中,数据库可能因任何原因在任何时候都无法访问-因此我认为没有任何特殊原因需要在应用程序启动时检查连接。希望这是有道理的。
Application {
start() {
while (!otherAppl.isAvailable) {
// wait until other appl is available
}
// other application is available ... go on with startup
}
}