Örnek içinden EC2 etiketlerini sorgulayın


99

Amazon, kısa süre önce çok sayıda VM'nin yönetimini biraz daha kolaylaştırmak için EC2 bulut sunucularının anahtar / değer çiftleriyle etiketlenmesi gibi harika bir özelliği ekledi.

Bu etiketleri diğer kullanıcı grubu verileriyle aynı şekilde sorgulamanın bir yolu var mı? Örneğin:

$ curl http://169.254.169.254/latest/meta-data/placement/availability-zone
us-east-1d

Etiketleri sorgulamanın benzer bir yolu var mı?

Yanıtlar:


36

Geçerli bulut sunucusunun etiketlerini almak için AWS meta veri aracı (örnek kimliğinizi almak için) ve yeni Etiket API'sinin bir kombinasyonunu kullanabilirsiniz .


Tamam, o bağlantıyı takip ettim ve görünüşe göre API dokümantasyonu. Kullanabileceğim bir araç yok mu yoksa API belgelerini okuyup kendi aracımı yazmam mı gerekiyor?
Edward Falk

3
Ec2-define-etiketleri komutu kolayca kullanılabilir mi? Sözüm ona ec2-api-tools paketinde, ama kurmaya çalıştığımda 404'ten başka bir şey almadım.
Edward Falk

2
bir örnek verin, etiket rolünün değerini alın: aws ec2 açık-etiketleri - filtreler İsim = kaynak-kimliği, Değerler = ec2metadata --instance-id--out = json | jq '.Etiketler [] | seçin (.Anahtar == "rol") | .Value '
jolestar

13
Bu bir cevaba işaret ediyor, ancak kendi başına bir cevap değil
Roy Truelove

3
ec2metadataAracı uygun görülmedi. Şimdi 169.254.169.254/latest/meta-data adresinde 'sihirli' URL'yi sorguluyorsunuz - cURL ile vurun ve size çeşitli veri bitleri elde etmek için kullanabileceğiniz sihirli uç noktaları verir. Bu durumda curl http://169.254.169.254/latest/meta-data/instance-idörnek kimliğinizi alır
Asfand Qazi

58

Aşağıdaki bash komut dosyası, geçerli ec2 örneğinizin Adını ("Ad" etiketinin değeri) döndürür. TAG_NAME'i özel durumunuza göre değiştirin.

TAG_NAME="Name"
INSTANCE_ID="`wget -qO- http://instance-data/latest/meta-data/instance-id`"
REGION="`wget -qO- http://instance-data/latest/meta-data/placement/availability-zone | sed -e 's:\([0-9][0-9]*\)[a-z]*\$:\\1:'`"
TAG_VALUE="`aws ec2 describe-tags --filters "Name=resource-id,Values=$INSTANCE_ID" "Name=key,Values=$TAG_NAME" --region $REGION --output=text | cut -f5`"

Aws klibini kurmak için

sudo apt-get install python-pip -y
sudo pip install awscli

Açık kimlik bilgileri yerine IAM kullanmanız durumunda şu IAM izinlerini kullanın:

{
  "Version": "2012-10-17",
  "Statement": [
    {    
      "Effect": "Allow",
      "Action": [ "ec2:DescribeTags"],
      "Resource": ["*"]
    }
  ]
}

İle "Bu işlemi yapmaya yetkili değilsiniz" mesajı alıyordum aws ec2 describe-tags. Bu IAM'yi IAM rolümün satır içi politikalarına eklemem gerekiyordu. Teşekkürler!
Victor D.

1
Çok küçük bir optimizasyon, | cut -f5ile değiştirmek OLABİLİR --query="Tags[0].Value".
Richard A Quadling

47

Kurduktan ec2-metadatave ec2-describe-tagsyükledikten sonra ( yukarıdaki Ranieri'nin cevabında belirtildiği gibi ), üzerinde bir "Name = Foo" etiketi olduğunu varsayarak, mevcut örneğin "adını" almak için örnek bir kabuk komutu.

EC2_PRIVATE_KEY ve EC2_CERT ortam değişkenlerinin ayarlandığını varsayar.

ec2-describe-tags \
  --filter "resource-type=instance" \
  --filter "resource-id=$(ec2-metadata -i | cut -d ' ' -f2)" \
  --filter "key=Name" | cut -f5

Bu geri döner Foo.


17
İşlemlerim, bulut sunucusunda EC2_PRIVATE_KEY'e de sahip olmak zorunda kalmadan mevcut bulut sunucusunun etiketlerini alabilseydi iyi olurdu. :-(
William Payne

1
@ william-payne Evet, bu gerçekten kötü. Belki de Amazon'un IAM'sini kullanarak en azından herhangi bir şeye çok sınırlı erişimi olan bir kullanıcı kullanabilirsiniz. FWIW, bu yaklaşımı artık kullanmıyorum ve kutuyu kurmak için sadece harici komut dosyaları kullanıyorum.
overthink

12
@WilliamPayne "Amazon EC2 Salt Okunur Erişim" politikasıyla bir IAM Rolü ayarlayabilir ve bu role sahip bulut sunucusu oluşturabilirsiniz. Daha ayrıntılı olmak istiyorsanız, yalnızca "DescribeTags" ayrıcalığına sahip özel bir ilke oluşturmak da mümkündür.
roverwolf

@WilliamPayne roverwolf'un önerisini beğendim. Harika çalıştı. Aslında, görmek isterseniz ayrıntılarıyla başka bir soruyu yanıtladım: stackoverflow.com/questions/9950586/…
Tony

2
Not ec2-describe-tagsiçin varsayılan us-east-2. Lütfen --regionfarklı bir bölge kullanmak için bayrağı iletin.
advait

15

EC2 etiketlerini yerel bir dosyaya indirmek için bu komut dosyasını bulut başlatma kullanıcı verilerinize ekleyebilirsiniz:

#!/bin/sh
INSTANCE_ID=`wget -qO- http://instance-data/latest/meta-data/instance-id`
REGION=`wget -qO- http://instance-data/latest/meta-data/placement/availability-zone | sed 's/.$//'`
aws ec2 describe-tags --region $REGION --filter "Name=resource-id,Values=$INSTANCE_ID" --output=text | sed -r 's/TAGS\t(.*)\t.*\t.*\t(.*)/\1="\2"/' > /etc/ec2-tags

Sisteminizde kurulu AWS CLI araçlarına ihtiyacınız var: Bunları packageskomut dosyasından önce bir bulut yapılandırma dosyasında bir bölümle yükleyebilir, bunları zaten içeren bir AMI kullanabilir aptveya yumkomut dosyasının başına bir veya komutu ekleyebilirsiniz .

EC2 etiketlerine erişmek için örneğinizin IAM rolünde buna benzer bir politikaya ihtiyacınız vardır:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "Stmt1409309287000",
      "Effect": "Allow",
      "Action": [
        "ec2:DescribeTags"
      ],
      "Resource": [
        "*"
      ]
    }
  ]
}

Bulut sunucusunun EC2 etiketleri şu biçimde sunulacaktır /etc/ec2-tags:

FOO="Bar"
Name="EC2 tags with cloud-init"

Dosyayı olduğu gibi bir kabuk betiğine dahil edebilirsiniz . /etc/ec2-tags, örneğin:

#!/bin/sh
. /etc/ec2-tags
echo $Name

Etiketler, örnek başlatma sırasında indirilir, bu nedenle sonraki değişiklikleri yansıtmazlar.


Komut dosyası ve IAM politikası, itaifrenkel'in cevabına dayanmaktadır.


a + bu yöntemi tercih et
Cmag

bu, otomatik ölçeklendirme grupları tarafından oluşturulan etiketler için çok kötü:aws:autoscaling:groupName
Cmag

2
O zaman şunu deneyin:aws ec2 describe-tags --region $REGION --filter "Name=resource-id,Values=$INSTANCE_ID" --output=text | sed -r 's/TAGS\t(.*)\t.*\t.*\t(.*)/EC2_TAG_\1="\2"/' |sed -r 's/aws:autoscaling:/aws_autoscaling_/' > /etc/ec2-tags
Ryan Gooler

11

Varsayılan kullanılabilirlik bölgesinde değilseniz, aşırı düşünmeden elde edilen sonuçlar boş dönecektir.

ec2-describe-tags \
   --region \
     $(curl -s http://169.254.169.254/latest/meta-data/placement/availability-zone  | sed -e "s/.$//") \
   --filter \
     resource-id=$(curl --silent http://169.254.169.254/latest/meta-data/instance-id)

Belirli bir etiketi (elastikbeanstalk: benim durumumda çevre-adı) almak için bir filtre eklemek istiyorsanız, bunu yapabilirsiniz.

ec2-describe-tags \
   --region \
     $(curl -s http://169.254.169.254/latest/meta-data/placement/availability-zone  | sed -e "s/.$//") \
   --filter \
     resource-id=$(curl --silent http://169.254.169.254/latest/meta-data/instance-id) \
   --filter \
     key=elasticbeanstalk:environment-name | cut -f5

Ve sadece filtrelediğim etiketin değerini elde etmek için, kesip beşinci alanı elde etmek için boru hattı oluşturuyoruz.

ec2-describe-tags \
  --region \
    $(curl -s http://169.254.169.254/latest/meta-data/placement/availability-zone  | sed -e "s/.$//") \
  --filter \
    resource-id=$(curl --silent http://169.254.169.254/latest/meta-data/instance-id) \
  --filter \
    key=elasticbeanstalk:environment-name | cut -f5

harika iş, teşekkür ederim, farklı bir dns örneğine sahip olmak benim için çalışmıyor, sonuncusu için Ad etiketinielasticbeanstalk:environment-nameName
detzu

5

Python için:

from boto import utils, ec2
from os import environ

# import keys from os.env or use default (not secure)
aws_access_key_id = environ.get('AWS_ACCESS_KEY_ID', failobj='XXXXXXXXXXX')
aws_secret_access_key = environ.get('AWS_SECRET_ACCESS_KEY', failobj='XXXXXXXXXXXXXXXXXXXXX')

#load metadata , if  = {} we are on localhost
# http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/AESDG-chapter-instancedata.html
instance_metadata = utils.get_instance_metadata(timeout=0.5, num_retries=1)
region = instance_metadata['placement']['availability-zone'][:-1]
instance_id = instance_metadata['instance-id']

conn = ec2.connect_to_region(region, aws_access_key_id=aws_access_key_id, aws_secret_access_key=aws_secret_access_key)
# get tag status for our  instance_id using filters
# http://docs.aws.amazon.com/AWSEC2/latest/CommandLineReference/ApiReference-cmd-DescribeTags.html
tags = conn.get_all_tags(filters={'resource-id': instance_id, 'key': 'status'})
if tags:
    instance_status = tags[0].value
else:
    instance_status = None
    logging.error('no status tag for '+region+' '+instance_id)

Yasal. Okuyucular, temel yerel bilgiler için kimlik bilgilerine bile ihtiyacınız olmadığını not ediyor, sadeceinstance_metadata = utils.get_instance_metadata(timeout=0.5, num_retries=1)
Bartvds

Ayrıca, bu, IAM rollerinde iyi bir şekilde oynar - bir örnek rolü ayarlarsanız, boto otomatik olarak kimliği ve anahtarı algılayacaktır.
dbn

5

Alternatif olarak, aşağıdakilerden describe-instancesziyade cli çağrısını kullanabilirsiniz describe-tags:

Bu örnek, örnek için "my-tag-name" etiketinin değerinin nasıl alınacağını gösterir:

aws ec2 describe-instances \
  --instance-id $(curl -s http://169.254.169.254/latest/meta-data/instance-id) \
  --query "Reservations[*].Instances[*].Tags[?Key=='my-tag-name'].Value" \
  --region ap-southeast-2 --output text

Bölgeyi yerel koşullarınıza uyacak şekilde değiştirin. Bu, örneğinizin örnek profil politikasında örnekleri tanımlama ayrıcalığına sahip olduğu ancak etiketleri tanımlama ayrıcalığına sahip olmadığı durumlarda yararlı olabilir.


4

Umarım mevcut yanıtların bazılarından daha basit ve daha temiz olan ve yalnızca AWS CLI'yi kullanan ve ek araçlar kullanmayan aşağıdakileri bir araya getirdim.

Bu kod örneği, mevcut EC2 örneği için "myTag" etiketinin değerinin nasıl alınacağını gösterir:

Tanımlama etiketlerini kullanma :

export AWS_DEFAULT_REGION=us-east-1
instance_id=$(curl -s http://169.254.169.254/latest/meta-data/instance-id)
aws ec2 describe-tags \
  --filters "Name=resource-id,Values=$instance_id" 'Name=key,Values=myTag' \
  --query 'Tags[].Value' --output text

Veya alternatif olarak, açıklayıcı örnekleri kullanarak :

aws ec2 describe-instances --instance-id $instance_id \
  --query 'Reservations[].Instances[].Tags[?Key==`myTag`].Value' --output text

3

AWS "kullanıcı verileri" ve "meta veri" API'lerini kullanarak, kuklayı özel bir sertifika adıyla başlatmak için kuklayı saran bir komut dosyası yazmak mümkündür.

Önce özel kullanıcı verileriyle bir aws örneği başlatın: 'role: webserver'

#!/bin/bash

# Find the name from the user data passed in on instance creation
USER=$(curl -s "http://169.254.169.254/latest/user-data")
IFS=':' read -ra UDATA <<< "$USER"

# Find the instance ID from the meta data api
ID=$(curl -s "http://169.254.169.254/latest/meta-data/instance-id")
CERTNAME=${UDATA[1]}.$ID.aws

echo "Running Puppet for certname: " $CERTNAME
puppet agent -t --certname=$CERTNAME 

Bu, 'webserver.i-hfg453.aws' gibi bir sertifika adıyla kuklayı çağırır, daha sonra 'web sunucusu' adlı bir düğüm bildirimi oluşturabilirsiniz ve kuklaların 'bulanık düğüm eşleşmesi', tüm web sunucularını sağlamak için kullanıldığı anlamına gelir.

Bu örnek, kukla yüklü bir temel görüntü üzerine inşa ettiğinizi varsayar.

Faydaları:

1) Kimlik bilgilerinizi geçmek zorunda değilsiniz

2) Rol yapılandırmalarıyla istediğiniz kadar ayrıntılı olabilirsiniz.


2

Yukarıdaki yanıtlardan bazılarının bir varyasyonu ancak bir örnekteki kullanıcı verisi komut dosyasından belirli bir etiketin değerini bu şekilde aldım

REGION=$(curl http://instance-data/latest/meta-data/placement/availability-zone | sed 's/.$//')

INSTANCE_ID=$(curl -s http://instance-data/latest/meta-data/instance-id)

TAG_VALUE=$(aws ec2 describe-tags --region $REGION --filters "Name=resource-id,Values=$INSTANCE_ID" "Name=key,Values='<TAG_NAME_HERE>'" | jq -r '.Tags[].Value')

2

Jq + ec2metadata onu biraz daha güzel hale getirir. Ben cf kullanıyorum ve bölgeye erişimim var. Aksi takdirde, bash'ta yakalayabilirsiniz.

aws ec2 describe-tags --region $REGION \
--filters "Name=resource-id,Values=`ec2metadata --instance-id`" | jq --raw-output \
'.Tags[] | select(.Key=="TAG_NAME") | .Value'

Jq yok.

aws ec2 describe-tags --region us-west-2 \
--filters "Name=resource-id,Values=`ec2-metadata --instance-id | cut -d " " -f 2`" \
--query 'Tags[?Key==`Name`].Value' \
--output text

1

AWS CLI'yi yükleyin:

curl "https://s3.amazonaws.com/aws-cli/awscli-bundle.zip" -o "awscli-bundle.zip"
sudo apt-get install unzip
unzip awscli-bundle.zip
sudo ./awscli-bundle/install -i /usr/local/aws -b /usr/local/bin/aws

Geçerli örnek için etiketleri alın:

aws ec2 describe-tags --filters "Name=resource-id,Values=`ec2metadata --instance-id`"

Çıktılar:

{
    "Tags": [
        {
            "ResourceType": "instance", 
            "ResourceId": "i-6a7e559d", 
            "Value": "Webserver", 
            "Key": "Name"
        }
    ]
}

Etiketleri çıkarmak için biraz perl kullanın:

aws ec2 describe-tags --filters \
"Name=resource-id,Values=`ec2metadata --instance-id`" | \
perl -ne 'print "$1\n" if /\"Value\": \"(.*?)\"/'

İadeler:

Webserver

ec2metadataaws-cli'de değil, ancak ile değiştirilebilir curl --silent http://169.254.169.254/latest/meta-data/instance-id. ayrıca, jqjson'u daha kolay ayrıştırabilir veya farklı bir çıktı biçimi daha da kolaydır.
tedder42

Bu işe yarıyor, ancak şunu eklemem gerekiyor: sudo apt-get -y install pythonveexport AWS_DEFAULT_REGION=us-west-1
Eugene

Bu işe yaramayacak ... 1. ec2metadata yanlış komuttur. 2. ec2-meta-veri - örnek-kimliği geri dönecekinstance-id: i-07f59f3564618f148
Daniel


0

EC2'de Fish shell kullanacak kadar çılgın olanlar için, işte size /home/ec2-user/.config/fish/config.fish için kullanışlı bir pasaj. Hostdata komutu şimdi tüm etiketlerinizin yanı sıra genel IP ve ana bilgisayar adını listeleyecektir.

set -x INSTANCE_ID (wget -qO- http://instance-data/latest/meta-data/instance-id)
set -x REGION (wget -qO- http://instance-data/latest/meta-data/placement/availability-zone | sed 's/.$//')

function hostdata
    aws ec2 describe-tags --region $REGION --filter "Name=resource-id,Values=$INSTANCE_ID" --output=text | sed -r 's/TAGS\t(.*)\t.*\t.*\t(.*)/\1="\2"/'
    ec2-metadata | grep public-hostname
    ec2-metadata | grep public-ipv4
end
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.