AWS boto - 实例 Status/Snapshot 状态不会更新 Python While Loop
AWS boto - Instance Status/Snapshot Status won't update Python While Loop
所以我正在使用 boto 创建一个 Python 脚本,以允许用户准备扩展他们的 Linux 根卷和分区。在脚本的第一部分,我想要一个 While 循环或类似的东西来使脚本直到:
a) 实例已完全停止
b) 快照创建完成。
以下是这两个的代码片段:
实例:
ins_prog = conn.get_all_instances(instance_ids=src_ins, filters={"instance-state":"stopped"})
while ins_prog == "[]":
print src_ins + " is still shutting down..."
time.sleep(2)
if ins_prog != "[]":
break
快照:
snap_prog = conn.get_all_snapshots(snapshot_ids=snap_id, filters={"progress":"100"})
while snap_prog == "[]":
print snap.update
time.sleep(2)
if snap_prog != "[]":
print "done!"
break
因此,当调用 conn.get_all_instances
和 conn.get_all_snapshots
时,如果过滤器不显示任何内容,它们 return 一个空列表,其格式类似于 []
。问题是 While 循环甚至没有 运行。就好像它没有将 []
识别为 get_all
函数生成的字符串。
如果有更简单的方法,请告诉我我现在不知所措 ):
谢谢!
编辑:根据 garnaat 的帮助,这里是后续问题。
snap_prog = conn.get_all_snapshots(snapshot_ids=snap.id)[0]
print snap_prog
print snap_prog.id
print snap_prog.volume_id
print snap_prog.status
print snap_prog.progress
print snap_prog.start_time
print snap_prog.owner_id
print snap_prog.owner_alias
print snap_prog.volume_size
print snap_prog.description
print snap_prog.encrypted
结果:
Snapshot:snap-xxx
snap-xxx
vol-xxx
pending
2015-02-12T21:55:40.000Z
xxxx
None
50
Created by expandDong.py at 2015-02-12 21:55:39
False
请注意 snap_prog.progress
return 是空的,但是 snap_prog.status
放在 While 循环中时保持 'pending'。
已解决:
我和我的同事发现了如何让快照循环工作。
snap = conn.create_snapshot(src_vol)
while snap.status != 'completed':
snap.update()
print snap.status
time.sleep(5)
if snap.status == 'completed':
print snap.id + ' is complete.'
break
snap.update()
调用纯粹将变量 snap
更新为 return 最新信息,其中 snap.status
输出 "pending" | "completed"。我还遇到 snap.status
未根据控制台显示快照的正确状态的问题。显然,控制台和 SDK 调用之间存在明显的滞后时间。当快照在控制台中完成时,我不得不等待约 4 分钟才能将状态更新为 "completed"。
我会尽量先笼统地回答这个问题。因此,您正在查询资源的状态。如果不满足某个状态,您想继续 querying/asking/polling 资源,直到 它处于您希望的状态。显然,这需要您在 循环中实际执行查询 。也就是抽象意义上的:
state = resource.query()
while state != desired_state:
time.sleep(T)
state = resource.query()
想想一般情况下这是如何工作的,为什么会这样。
现在,关于您的代码和问题,您需要自己弄清楚一些不确定性。首先,我非常确定 conn.get_all_instances()
returns 在您的情况下是一个空列表,而不是字符串 '[]'
。也就是说,您的检查应该针对 空列表 而不是特定字符串 (*)。检查 Python 中的空列表就像 not l
:
一样简单
l = give_me_some_list()
if not l:
print "that list is empty."
代码中的另一个问题是您对此处使用的 language/architecture 期望过高。您查询资源并将结果存储在 ins_prog
中。之后,您继续检查 ins_prog
,就好像这会 "magically" 通过后台的某个神奇过程进行更新一样。不,那不会发生!您需要定期致电 conn.get_all_instances()
以获取更新信息。
(*) 这在此处记录:http://boto.readthedocs.org/en/latest/ref/ec2.html#boto.ec2.connection.EC2Connection.get_all_instances - 文档明确说明 "Return type: list"。不是字符串。
如果我想检查特定实例的状态并等到该实例达到某个状态,我会这样做:
import time
import boto.ec2
conn = boto.ec2.connect_to_region('us-west-2') # or whatever region you want
instance = conn.get_all_instances(instance_ids=['i-12345678'])[0].instances[0]
while instance.state != 'stopped':
time.sleep(2)
instance.update()
调用 get_all_instances
的有趣事情是必要的,因为该调用 returns 一个 Reservation
对象,而该对象又具有一个 instances
属性,它是一个列表所有匹配的实例。因此,我们正在获取列表中的第一个(也是唯一的)Reservation
,然后在预订中获取第一个(也是唯一的)Instance
。您可能应该对此进行一些错误检查。
快照可以用类似的方式处理。
snapshot = conn.get_all_snapshots(snapshot_ids=['snap-12345678'])[0]
while snapshot.status != 'completed':
time.sleep(2)
snapshot.update()
两个对象上的 update()
方法向 EC2 查询对象的最新状态,并使用该状态更新本地对象。
所以我正在使用 boto 创建一个 Python 脚本,以允许用户准备扩展他们的 Linux 根卷和分区。在脚本的第一部分,我想要一个 While 循环或类似的东西来使脚本直到:
a) 实例已完全停止
b) 快照创建完成。
以下是这两个的代码片段:
实例:
ins_prog = conn.get_all_instances(instance_ids=src_ins, filters={"instance-state":"stopped"})
while ins_prog == "[]":
print src_ins + " is still shutting down..."
time.sleep(2)
if ins_prog != "[]":
break
快照:
snap_prog = conn.get_all_snapshots(snapshot_ids=snap_id, filters={"progress":"100"})
while snap_prog == "[]":
print snap.update
time.sleep(2)
if snap_prog != "[]":
print "done!"
break
因此,当调用 conn.get_all_instances
和 conn.get_all_snapshots
时,如果过滤器不显示任何内容,它们 return 一个空列表,其格式类似于 []
。问题是 While 循环甚至没有 运行。就好像它没有将 []
识别为 get_all
函数生成的字符串。
如果有更简单的方法,请告诉我我现在不知所措 ):
谢谢!
编辑:根据 garnaat 的帮助,这里是后续问题。
snap_prog = conn.get_all_snapshots(snapshot_ids=snap.id)[0]
print snap_prog
print snap_prog.id
print snap_prog.volume_id
print snap_prog.status
print snap_prog.progress
print snap_prog.start_time
print snap_prog.owner_id
print snap_prog.owner_alias
print snap_prog.volume_size
print snap_prog.description
print snap_prog.encrypted
结果:
Snapshot:snap-xxx
snap-xxx
vol-xxx
pending
2015-02-12T21:55:40.000Z
xxxx
None
50
Created by expandDong.py at 2015-02-12 21:55:39
False
请注意 snap_prog.progress
return 是空的,但是 snap_prog.status
放在 While 循环中时保持 'pending'。
已解决:
我和我的同事发现了如何让快照循环工作。
snap = conn.create_snapshot(src_vol)
while snap.status != 'completed':
snap.update()
print snap.status
time.sleep(5)
if snap.status == 'completed':
print snap.id + ' is complete.'
break
snap.update()
调用纯粹将变量 snap
更新为 return 最新信息,其中 snap.status
输出 "pending" | "completed"。我还遇到 snap.status
未根据控制台显示快照的正确状态的问题。显然,控制台和 SDK 调用之间存在明显的滞后时间。当快照在控制台中完成时,我不得不等待约 4 分钟才能将状态更新为 "completed"。
我会尽量先笼统地回答这个问题。因此,您正在查询资源的状态。如果不满足某个状态,您想继续 querying/asking/polling 资源,直到 它处于您希望的状态。显然,这需要您在 循环中实际执行查询 。也就是抽象意义上的:
state = resource.query()
while state != desired_state:
time.sleep(T)
state = resource.query()
想想一般情况下这是如何工作的,为什么会这样。
现在,关于您的代码和问题,您需要自己弄清楚一些不确定性。首先,我非常确定 conn.get_all_instances()
returns 在您的情况下是一个空列表,而不是字符串 '[]'
。也就是说,您的检查应该针对 空列表 而不是特定字符串 (*)。检查 Python 中的空列表就像 not l
:
l = give_me_some_list()
if not l:
print "that list is empty."
代码中的另一个问题是您对此处使用的 language/architecture 期望过高。您查询资源并将结果存储在 ins_prog
中。之后,您继续检查 ins_prog
,就好像这会 "magically" 通过后台的某个神奇过程进行更新一样。不,那不会发生!您需要定期致电 conn.get_all_instances()
以获取更新信息。
(*) 这在此处记录:http://boto.readthedocs.org/en/latest/ref/ec2.html#boto.ec2.connection.EC2Connection.get_all_instances - 文档明确说明 "Return type: list"。不是字符串。
如果我想检查特定实例的状态并等到该实例达到某个状态,我会这样做:
import time
import boto.ec2
conn = boto.ec2.connect_to_region('us-west-2') # or whatever region you want
instance = conn.get_all_instances(instance_ids=['i-12345678'])[0].instances[0]
while instance.state != 'stopped':
time.sleep(2)
instance.update()
调用 get_all_instances
的有趣事情是必要的,因为该调用 returns 一个 Reservation
对象,而该对象又具有一个 instances
属性,它是一个列表所有匹配的实例。因此,我们正在获取列表中的第一个(也是唯一的)Reservation
,然后在预订中获取第一个(也是唯一的)Instance
。您可能应该对此进行一些错误检查。
快照可以用类似的方式处理。
snapshot = conn.get_all_snapshots(snapshot_ids=['snap-12345678'])[0]
while snapshot.status != 'completed':
time.sleep(2)
snapshot.update()
两个对象上的 update()
方法向 EC2 查询对象的最新状态,并使用该状态更新本地对象。