【问题标题】:Shutdown EC2 Instance if idle right before another billable hour如果在另一个计费时间之前空闲,则关闭 EC2 实例
【发布时间】:2013-04-10 00:38:15
【问题描述】:

在不可预知的时间(用户请求),我需要运行内存密集型作业。为此,我获得了一个现场或按需实例,并将其标记为non_idle。工作完成后(可能需要几个小时),我给它标记idle。由于 AWS 的按小时计费模型,我希望保持该实例处于活动状态,直到另一个计费时间发生,以防有另一个工作进入。如果有工作进入,则应重用该实例并将其标记为 non_idle。如果在此期间没有工作进入,实例应该终止。

AWS 是否为此提供现成的解决方案?据我所知,CloudWatch 无法设置应在特定时间运行的警报,更不用说使用 CPUUtilization 或实例的标签了。否则,也许我可以简单地为每个创建的实例设置一个 java 计时器或 scala actor,在实例创建后每小时运行一次,并检查标签 idle

【问题讨论】:

    标签: timer amazon-web-services amazon-ec2 amazon-cloudwatch


    【解决方案1】:

    对于这种细粒度优化没有现成的 AWS 解决方案,但您可以使用现有的构建块根据当前实例的启动时间构建您自己的解决方案(请参阅 Dmitriy Samovskiy 的智能解决方案推导How Long Ago Was This EC2 Instance Started?) .

    玩“鸡”

    Shlomo Swidler 在他的文章 Play “Chicken” with Spot Instances 中探讨了这种优化,尽管在 Amazon EC2 Spot Instances 的背景下动机略有不同:

    AWS Spot 实例具有一个有趣的经济特征,即 使游戏系统成为可能。与所有 EC2 实例一样, 当您开始终止 Spot 实例时,您会招致 充电一小时,即使您使用的时间不到一小时。 但是,当 AWS 因现货价格超过 出价,您无需为当前小时支付费用。

    机制当然是一样的,所以你可以简单地重复使用他组装的脚本,即执行这个脚本来代替或除了将实例标记为idle

    #! /bin/bash
    t=/tmp/ec2.running.seconds.$$
    if wget -q -O $t http://169.254.169.254/latest/meta-data/local-ipv4 ; then
        # add 60 seconds artificially as a safety margin
        let runningSecs=$(( `date +%s` - `date -r $t +%s` ))+60
        rm -f $t
        let runningSecsThisHour=$runningSecs%3600
        let runningMinsThisHour=$runningSecsThisHour/60
        let leftMins=60-$runningMinsThisHour
        # start shutdown one minute earlier than actually required
        let shutdownDelayMins=$leftMins-1
        if [[ $shutdownDelayMins > 1 && $shutdownDelayMins < 60 ]]; then
            echo "Shutting down in $shutdownDelayMins mins."
            # TODO: Notify off-instance listener that the game of chicken has begun
            sudo shutdown -h +$shutdownDelayMins
        else
            echo "Shutting down now."
            sudo shutdown -h now
        fi
        exit 0
    fi
    echo "Failed to determine remaining minutes in this billable hour. Terminating now."
    sudo shutdown -h now
    exit 1
    

    一旦有作业进入,您就可以取消预定的终止,而不是使用non_idle 标记实例,如下所示:

    sudo shutdown -c
    

    这也是测试/操作期间的“红色按钮”紧急命令,参见例如Shlomo 的警告:

    在使用之前,请确保您真正了解此脚本的作用 它。如果您错误地安排了要关闭的实例,您可以 用这个命令取消它,在实例上运行:sudo shutdown -c

    将 CloudWatch 添加到游戏中

    您可以通过与 Amazon CloudWatch 集成来进一步采用 Shlomo 的自包含方法,该方法最近为 Use Amazon CloudWatch to Detect and Shut Down Unused Amazon EC2 Instances 添加了一个选项,有关详细信息,请参阅介绍性博客文章 Amazon CloudWatch - Alarm Actions

    今天,我们让您能够停止或终止您的 EC2 触发 CloudWatch 警报时的实例。您可以将其用作 故障保护(检测异常情况然后采取行动)或作为 您的应用程序的处理逻辑(等待预期的条件和 然后行动)。 [强调我的]

    您的用例列在应用程序集成部分中:

    您还可以根据您的 Custom Metrics 创建 CloudWatch 警报 逐个实例观察。例如,您可以 衡量对您自己的 Web 服务 API、页面请求或消息的调用 每分钟发帖数,并根据需要回复。

    因此,您可以通过Publishing Custom Metrics 将这一新功能用于 CloudWatch,以指示实例是否应根据 Dmitriy 的启动时间检测终止(为idle),并在有作业进入后再次重置指标 /em> 并且一个实例应该继续运行(non_idle)——就像 EC2 会处理终止一样,3 个自动化步骤中的 2 个将从实例移动到操作环境以及自动化的管理和可见性过程相应地得到改进。

    【讨论】:

    • 我非常喜欢“玩鸡”的想法,并且有一个考虑亚马逊将为您终止您的实例的预期概率的出价策略。更多现场竞价策略信息:cs.technion.ac.il/users/wwwb/cgi-bin/tr-get.cgi/2011/CS/…cloudexchange.org
    • @jmcejuela - 这确实是一个非常高级的优化 - 如果您的目标是那么高,您可能希望您的解决方案也基于更可靠和外部可见的自动化流程,所以我添加了一个建议如何将 CloudWatch 检测添加到自动化流程中。
    • 太棒了,我不知道自定义指标。但是,对于我的用例来说,它们太过分了,因为它们对每个实例和每个月的警报和指标收费。我可能会运行成百上千个不同的实例,因此 cloudwatch 的成本最终可能会高于实例本身的成本。我将改用类似“玩鸡”的解决方案。 -- 非常感谢您的帮助和详细解答!
    • 警告:此方法可能有效,但在任何情况下都不可靠。 1 小时的测量可能很好,但它不可靠,因为这些元数据文件可以由 AWS 重新创建,然后文​​件日期是错误的。因此,无论何时发生这种情况,您的日期都是错误的。这是一个罕见的事件(比如几个月一次),但发生在我身上。
    猜你喜欢
    • 2019-01-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-12-13
    • 2014-08-02
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多