确定性地创建和标记EC2实例

时间:2013-04-07 18:06:38

标签: amazon-web-services amazon-ec2

我正在创建3个EC2实例,然后迭代并标记每个实例。 有时标签请求会失败,尽管后来的实例似乎正在运行。

这可能是一个时间问题吗?在标记之前我应该​​在创建实例后等待几秒钟吗?有没有确定的方法等待它开始?

2 个答案:

答案 0 :(得分:12)

更新20140512

AWS同时在Troubleshooting API Request Errors上添加了更详细的文档,其中包括一个代表Eventual Consistency的部分,该部分基本上证实了我在下面的初步答案中的分析:

  

由于支持API的系统的分布式特性,Amazon EC2 API遵循最终的一致性模型。 这意味着您运行的API命令会影响您的Amazon EC2资源的结果可能不会立即显示给您运行的所有后续命令。 [...]

     

[...]例如,[...] 如果您运行命令来修改或描述您刚刚创建的资源,则其ID可能不会在整个系统中传播,您将获得错误响应资源不存在

     

要管理最终一致性,您可以执行以下操作:

     
      
  • 在运行命令进行修改之前,请确认资源的状态。 使用指数退避运行相应的Describe命令   算法,以确保您为前一个留出足够的时间   命令通过系统传播。 [...]

  •   
  • 在后续命令之间添加等待时间,即使Describe命令返回准确的响应。应用指数退避   算法从几秒钟的等待时间开始,并增加   逐渐长达约五分钟的等待时间。

  •   
     

[强调我的]

请注意:大多数AWS SDKs同时自动应用这些建议,包括调整默认重试策略的选项或甚至添加自定义实现 - 请参阅Error Retries and Exponential Backoff in AWS以获取有关如何如果需要的话,自己实现它。


更新20130719

各种大型AWS用户越来越多地遇到AWS API的最终一致设计,他们自然需要深入了解并相应地解决它,例如参见以下文章:


初步答复

正如@datasage已经commented一样,AWS API显然通常只需要被视为eventually consistent - 这在第一次遇到时肯定是意料之外的,但对于大规模服务来说实际上并不太令人惊讶后见之明,即工程学。操作权衡以解决CAP theorem

另见我对Alex Ciminian的问题Implementing idempotency for AWS Spot Instance Requests的评论,他在那里讨论了关于类似一致性问题的测试结果:

  

有趣的问题 - [...]我遇到了各种类似的API延迟   Bamboo AWS Plugin的上下文并得出AWS API的结论   需要被视为只有eventually consistent   板;例如,我甚至遇到过我收到资源的情况   来自创建调用的id,可以根据其id而不是标记资源   此后仍然描述它,因为据说它不存在   (尚)。

  • 我在这里描述的似乎表明,每一个单独的API动作实际上都是由AWS完全独立运行的(不仅是在外部可见的服务中,而且甚至在像EC2这样的单个服务中),因此可能最终受到影响一致性,必须相应处理。

有关上述案例的详细信息,您可能需要查看Frequent polling of AWS API causes throttle limit,其中我总结了我们的分析和方法,通过AWS SDK for Java中可用但有限的重试/退避功能改进处理 - 解决方案几乎是理想的,但它似乎暂时大大改善了。

在类似的说明中,重新设计的AWS SDK for PHP 2引入了专用的“Waiter”对象,允许您轮询资源,直到它处于所需的状态来解决问题,请参阅< Quick Start中的em>服务员了解详情:

  

SDK提供的一个高级抽象是概念   “服务员”服务员帮助最终更轻松地工作   通过提供一种等待资源的简便方法来实现一致的系统   通过轮询资源进入特定状态。 [...] 任何   以“waitUntil”开头的@method标签将使用服务员。

$client->waitUntil('BucketExists', array('Bucket' => 'my-bucket'));

答案 1 :(得分:0)

在启动实例之前,无法创建标记名称。您可以尝试在创建实例时提供key_name。如果您使用的是boto,可以通过

完成
reservation = conn.run_instances(1, 1, instance_type='m1.small', key_name='samplename')

然后可以通过传递key_name来检索实例,一旦它们处于运行状态,你也可以给它们标记名称。