【问题标题】:How to ensure Google Cloud Compute instance is up and running如何确保 Google Cloud Compute 实例启动并运行
【发布时间】:2015-04-03 14:28:01
【问题描述】:

我从 shell 脚本创建 Google Cloud Compute 实例,然后通过 ssh 在该实例上启动几个命令。

如何确保实例中的操作系统正常运行?

例如:

gcloud compute instances create "$my_name" \ --tags "http-server" \ --image container-vm \ --metadata-from-file google-container-manifest="container.yml" \ --zone "$my_zone" \ --machine-type g1-small

然后我想运行 gcloud compute ssh \ "$my_name" --zone "$my_zone" \ --command 'sudo docker stop $(sudo docker ps -q -a)'

gcloud compute copy-files \ some.conf root@"$my_name":/existing_dir/ \ --zone "$my_zone"

据我了解,如果实例未启动,第二个命令可能会因连接拒绝而失败。

如何确保实例已启动并准备好接受 ssh 连接?

【问题讨论】:

    标签: google-cloud-platform gcloud


    【解决方案1】:

    在发送命令前检查 SSH 端口是否打开。在实例操作系统启动之前,SSH 服务器不会启动:

    IP=$(gcloud compute instances list | awk '/'$my_name'/ {print $5}')
    if nc -w 1 -z $IP 22; then
        echo "OK! Ready for heavy metal"
        : Do your heavy metal work
    else
        echo "Maybe later?"
    fi
    

    解释:

    1. 获取实例 $my_name 的 IP
    2. 检查端口 22 是否正在接受传入连接。

    -w: 连接超时(1秒应该够了)

    -z:仅检查端口是否打开并立即退出

    【讨论】:

    • 我好像VM启动可能需要5秒以上
    • 检查实例在循环中是否可用。实例启动时间取决于实例启动配置:)
    • 这是一个好方法。需要注意的是,gcloud 的默认表格格式旨在方便且易于阅读,但不是长期稳定的,因此将来可能会添加新字段并破坏 awk。相反,我建议调用gcloud compute instances list instance-name --format json 以获得更稳定的输出格式。您可以使用 jq 解析 json 输出。 (其他稳定的输出格式包括 text 和 yaml。)
    • --format text 在我看来对 unix 过滤更友好,并且不需要像 jq 这样的外部工具。一旦你有一个基本的方法工作,唯一剩下的就是细节。
    • 您可以通过在响应中搜索 IPv4 地址来使其更加健壮:$( gcloud compute instances list --format text |sed -rn 's/.*([0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}).*/\1/p' )
    【解决方案2】:

    简单的跨平台解决方案:

    gcloud compute --verbosity error --project "MYPROJECT" ssh "MYINSTANCE" -- "echo instance now up" -o StrictHostKeyChecking=no

    循环直到你得到errorLevel=0

    【讨论】:

    • 对我来说,如果 VM 没有运行,这将失败相当严重,带有 python 堆栈跟踪。
    【解决方案3】:

    如果您必须确保 ssh 可用,则有一个脚本。

    #!/usr/bin/env bash
    
    function wait_vm_up {
      local counter=0
    
      local readonly project=${1:?"project required"}
      local readonly instance=${2:?"instance required"}
      local readonly zone=${3:?"zone required"}
      local readonly user=${4:?"user required"}
      local readonly maxRetry=${5:-100}
    
      echo "Project: $project"
      echo "Instance: $instance"
      echo "MaxRetry: $maxRetry"
    
      while true ; do
        if (( $counter == $maxRetry )) ; then
          echo "Reach the retry upper limit $counter"
          exit 1
        fi
    
        gcloud compute ssh --quiet --zone "$zone" "$user@$instance" --tunnel-through-iap --project "$project" --command="true" 2> /dev/null
    
        if (( $? == 0 )) ;then
          echo "The machine is UP !!!"
          exit 0
        else
          echo "Maybe later? $counter"
          ((counter++))
          sleep 1
        fi
      done
    }
    
    wait_vm_up $@
    

    【讨论】:

      【解决方案4】:

      我认为startup scripts 为您完成工作:D

      或者使用REST APIs可以轮询实例状态

      【讨论】:

      • REST API 方式需要授权,从 shell 角度看太复杂了。
      • 我猜container-vm 图像已经定义了启动脚本。启动脚本可以与container-vm 图像一起使用吗?
      • 如果你使用 python 从 shell 调用一个 gapi,它很简单:创建一个 python 脚本来完成这项工作并从 sh 中使用它。关于预定义的图像脚本,我认为它是有效的:试试吧,让我知道!
      • 你为什么不赞成最佳答案? API 是与谷歌沟通的正确方式。其他一切都只是每天都在变化的垃圾¯_(ツ)_/¯
      【解决方案5】:

      您可以使用以下命令:gcloud compute instances describe 'instance name' --zone 'zone name' | grep "状态:正在运行"

      如果您得到准确的输出 status: RUNNING,它将表明实例已启动并正在运行。

      【讨论】:

      • 它不起作用。根据文档: RUNNING - 实例正在启动或运行。您可以在实例进入此状态后立即连接到该实例。
      【解决方案6】:

      简单的命令行或别名。

      alias gcp_status_MY_MACHINE='gcloud compute instances describe salesforce --zone "ZONE" --project "PROJECT" | grep status'
      

      如果您只有一个项目并且没有指定仍然可以工作的区域,这只是详细版本。

      【讨论】:

        猜你喜欢
        • 2020-11-23
        • 1970-01-01
        • 1970-01-01
        • 2017-12-25
        • 2020-04-30
        • 1970-01-01
        • 1970-01-01
        • 2021-04-21
        • 1970-01-01
        相关资源
        最近更新 更多