bash scripting awk amazon-ec2 ec2-api-tools

bash - Obtención del ID de una instancia recién lanzada con ec2-api-tools



scripting awk (5)

Como alternativa a las ec2-run-instances , puede crear una instancia de ec2 y obtener InstanceId por una línea mediante las instancias de run-instances awscli:

export MyServerID=$(aws ec2 run-instances --image-id AMI --count 1 --instance-type t2.micro --key-name "my_ssh_key" --security-group-ids sg-xxx --subnet-id subnet-yyy --query ''Instances[0].InstanceId'' --output text)

Estoy lanzando una instancia de EC2, invocando ec2-run-instances desde un simple script de bash, y quiero realizar más operaciones en esa instancia (p. Ej., Asociar el elástico IP), para lo cual necesito la identificación de la instancia.

El comando es algo así como ec2-run-instances ami-dd8ea5a9 -K pk.pem -C cert.pem --region eu-west-1 -t c1.medium -n 1 , y su salida:

RESERVATION r-b6ea58c1 696664755663 default INSTANCE i-945af9e3 ami-dd8ea5b9 pending 0 c1.medium 2010-04-15T10:47:56+0000 eu-west-1a aki-b02a01c4 ari-39c2e94d

En este ejemplo, i-945af9e3 es el id que estoy i-945af9e3 .

Por lo tanto, necesitaría una forma sencilla de analizar el ID de lo que devuelve el comando: ¿cómo lo harías? Mi AWK está un poco oxidado ... No dude en utilizar cualquier herramienta disponible en una caja típica de Linux. (Si hay una manera de obtenerlo directamente utilizando las herramientas de la API de EC2, mucho mejor. Pero afaik no hay un comando de EC2 para, por ejemplo, devolver el ID de la instancia iniciada más recientemente).


Completando su respuesta correcta, aquí hay un script de shell que crea una instancia, ejecuta algunos comandos y elimina la instancia. Utiliza awk de la misma manera que la tuya.

#!/bin/sh # Creates an Amazon EC2 virtual machine (an instance) and runs some # shell commands on it before terminating it. Just an example. # Stephane Bortzmeyer <[email protected]> # Parameters you can set. # Choose an AMI you like (ami-02103876 is a Debian "lenny") AMI=ami-02103876 # Create your key pair first, for instance on the Web interface KEY=test-b KEYDIR=. # The user name to use depends on the AMI. "root" is common but check # the documentation of the AMI. USERNAME=root # Needs to be a legal Unix group of commands COMMANDS="(uname -a; df -h; cat /etc/debian_version)" MAX_CONNECTS=4 MAX_TESTS=6 # If you want to change from the default region, set the environment # variable EC2_URL for instance ''export # EC2_URL=https://ec2.eu-west-1.amazonaws.com'' to use the ''eu-west-1'' # region # Also, be sure your default security group allows incoming SSH. if [ "${EC2_PRIVATE_KEY}" = "" ] || [ "${EC2_CERT}" = "" ]; then echo "You need to have X.509 certificate and private key locally, and to set the environment variables EC2_PRIVATE_KEY and EC2_CERT to indicate their locations" 1>&2 exit 1 fi start=$(ec2-run-instances --key ${KEY} $AMI) if [ $? != 0 ]; then echo "Machine did not start" 1>&2 exit 1 fi AMI_E=$(echo "$start" | awk ''/^INSTANCE/ {print $3}'') if [ "$AMI_E" != "$AMI" ]; then echo "AMI does not match (got $AMI_E instead of $AMI), the machine probably did not start" 1>&2 exit 1 fi INSTANCE=$(echo "$start" | awk ''/^INSTANCE/ {print $2}'') # I do not find a way to block until the machine is ready. We # apparently have to poll. OVER=0 TESTS=0 while [ $OVER != 1 ] && [ $TESTS -lt $MAX_TESTS ]; do description=$(ec2-describe-instances ${INSTANCE}) STATE=$(echo "$description" | awk ''/^INSTANCE/ {print $6}'') NAME=$(echo "$description" | awk ''/^INSTANCE/ {print $4}'') if [ "$NAME" = "" ]; then echo "No instance ${INSTANCE} available. Crashed or was terminated." 1>&2 exit 1 fi if [ $STATE = "running" ]; then OVER=1 else # I like bc but ''echo $(( TESTS+=1 ))'' should work, too. Or expr. TESTS=$(echo $TESTS+1 | bc) sleep 2 fi done if [ $TESTS = $MAX_TESTS ]; then echo "${INSTANCE} never got to running state" 1>&2 ec2-terminate-instances ${INSTANCE} exit 1 fi echo "$INSTANCE is running, name is $NAME" # The SSH server does not seem reachable immediately. We again have to poll OVER=0 TESTS=0 while [ $OVER != 1 ] && [ $TESTS -lt $MAX_CONNECTS ]; do ssh -o "StrictHostKeyChecking no" -i ${KEYDIR}/${KEY}.pem ${USERNAME}@$NAME "${COMMANDS}" if [ $? != 255 ]; then # It means we connected successfully (even if the remote command failed) OVER=1 else TESTS=$(echo $TESTS+1 | bc) sleep 3 fi done if [ $TESTS = $MAX_CONNECTS ]; then echo "Cannot connect to ${NAME}" 1>&2 fi ec2-terminate-instances ${INSTANCE}


No hay necesidad de usar awk:

# create the instance and capture the instance id echo "Launching instance..." instanceid=$(ec2-run-instances --key $pemkeypair --availability-zone $avzone $ami | egrep ^INSTANCE | cut -f2) if [ -z "$instanceid" ]; then echo "ERROR: could not create instance"; exit; else echo "Launched with instanceid=$instanceid" fi

de http://www.hulen.com/post/22802124410/unattended-amazon-ec2-install-script


Ok, al menos algo como esto debería funcionar:

instance_id=$(ec2-run-instances ami-dd8ea5a9 [...] | awk ''/INSTANCE/{print $2}'')

Admito que estaba un poco perezoso pensando que es más rápido preguntar en SO que volver a aprender algunos conceptos básicos de AWK ... :-)

Edición : uso de AWK simplificado como sugirió Dennis. También, usando $() lugar de `` para mayor claridad, y eliminé la variable intermedia.


http://www.tothenew.com/blog/how-to-parse-json-by-command-line-in-linux/ best tool to parse json in shell #get instance id cat sample.json | jq ''.Instances[0].InstanceId''|sed -e ''s/^"//'' -e ''s/"$//'' #check instances is running or not cat status.json | jq ''.InstanceStatuses[0].InstanceState.Name''|sed -e ''s/^"//'' -e ''s/"$//''