等待EC2实例创建的Java API。

9

我刚开始使用Java中的Amazon EC2 API。

我使用ec2.runInstances(runInstancesRequest)创建了实例;

但是,启动实例需要一些时间(通常需要1-2分钟)。

我需要通过Java EC2 API获取机器的公共DNS。

如何知道实例何时从“待处理”状态变为“已处理”状态,并如何通过EC2 API获取EC2实例的公共DNS。

提前感谢。 Kanna


请注意,对于Shell用户有一个类似的问题https://dev59.com/xnE85IYBdhLWcg3wtV71,并且答案也是相同的,您必须进行轮询(反复测试)。 - bortzmeyer
3个回答

9

SDK没有提供任何事件模型或其他信号来告诉您EC2对象何时更改状态-唯一的方法是定期对对象进行DescribeXXXXXXXX调用,例如每30秒一次,直到状态字段更改。

调用执行和响应需要有限的最小时间,因此您需要找到一个间隔,不要在之前一个完成之前触发请求。或者等待响应,然后再等待另外“n”秒再重新发出调用。即使它们在响应之间计时,也不希望快速请求AWS API。在我的控制器应用程序中,我将间隔设置为30秒,发出请求,等待响应,然后从间隔中减去经过的时间并休眠那么长时间。在多线程模型中,我可以同时跟踪许多对象的状态更改,而不会淹没我的本地CPU或API。

一旦检测到状态更改(并假设新状态是您所期望的-不要忘记处理故障模式),则可以从API响应对象返回的结构中获取各种描述性信息,包括公共DNS地址(在实例对象的情况下)。


谢谢@Jonners。我已经成功了。感谢你的帮助。 - kanap008

0
这就是我正在做的事情。如果有更优雅的方法,我很愿意看到它。
        Callable<String> getInstanceMetadata = () -> {
          Instance instance = null;
          while (null == instance) {
            // Describe the instance to check its state
            Thread.sleep(10 * 1000);
            //Each reservation is a representation of a request that may be tens of nodes.
            List<Reservation> reservations = ec2.describeInstances().getReservations();
            //create a stream of instances from all reservations
            Stream<Instance> instancesStream = reservations.stream().flatMap(reservation -> reservation.getInstances().stream());
            //filter the stream to find the instance with the instanceId
            instance = instancesStream.filter(i -> i.getInstanceId().equals(instanceId)).findFirst().orElse(null);
        }

        String publicIp = instance.getPublicIpAddress();
        assert instance.getInstanceId() == instanceId;

        log.debug("Successfully created ec2 node {} with public IP {}", instance.getInstanceId(), publicIp);
        return instance.getInstanceId()
    };

    TimeLimiter timeLimiter = SimpleTimeLimiter.create(Executors.newSingleThreadExecutor());

-1

实际上,你可以轮询来查找实例的状态。以下是一些 Bash 代码用于这样做,只需将其调整为 JAVA。在 Java SDK 中可能有类似的命令,这样就不必从 Java 执行 Bash。命令 'ec2-describe-instances' 来自Amazon AWS CLI。我会开始编写函数或方法等待运行状态以测试实例是否为 'pending',如果它不是正在启动或 'pending',则失败。然后记录时间,并给出最多3分钟的限制,在循环中继续轮询 'running' 状态,检查3分钟的限制。无论哪个先到达,都要返回到调用点:'not started'、'startup time exceeded' 或 'running'。

    setInstanceStatus () {
  instanceStatus=`ec2-describe-instances $INSTANCE_ID -C $CERTIFICATE_FILE -K $PRIVATE_KEY --region $REGION -U $AWS_URL`

  is_pending="`echo $instanceStatus|grep -c " pending "`"
  is_running="`echo $instanceStatus|grep -c " running "`"
  is_shutting_down="`echo $instanceStatus|grep -c " shutting-down "`"
  is_terminated="`echo $instanceStatus|grep -c " terminated "`"
  is_stopping="`echo $instanceStatus|grep -c " stopping "`"
  is_stopped="`echo $instanceStatus|grep -c " stopped "`"

  if   [ "$is_pending" -eq "1" ]; then
    status="pending"
  elif [  "$is_running" -eq "1" ]; then
    status="running"
  elif [  "$is_shutting_down" -eq "1" ]; then
    status="shutting-down"
  elif [  "$is_terminated" -eq "1" ]; then
    status="terminated"
  elif [  "$is_stopping" -eq "1" ]; then
    status="stopping"
  elif [  "$is_stopped" -eq "1" ]; then
    status="stopped"
  else
    status="bad-instance-state"
  fi
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接