Могу ли я автоматически запускать и закрывать свой инстанс Amazon с помощью Amazon API? Не могли бы вы описать, как это можно сделать? В идеале мне нужно запускать экземпляр и останавливать его через определенные интервалы времени каждый день.
Могу ли я автоматически запускать и закрывать свой инстанс Amazon с помощью Amazon API? Не могли бы вы описать, как это можно сделать? В идеале мне нужно запускать экземпляр и останавливать его через определенные интервалы времени каждый день.
Ответы:
На всякий случай, если кто-то наткнется на этот старый вопрос, в настоящее время вы можете добиться того же, добавив расписание в группу автоматического масштабирования: увеличьте количество экземпляров в группе автоматического масштабирования до 1 в определенное время и затем уменьшите его до 0 впоследствии. .
И поскольку этот ответ набирает много просмотров, я решил связать с очень полезным руководством по этому поводу: Запуск экземпляров EC2 по повторяющемуся расписанию с автоматическим масштабированием
Вы можете попробовать использовать инструменты API Amazon EC2 напрямую. На самом деле вам нужны только две команды: ec2-start-instance и ec2-stop-instance. Убедитесь, что переменные среды, такие как EC2_HOME, AWS_CREDENTIAL_FILE, EC2_CERT, EC2_PRIVATE_KEY и т. Д., Правильно настроены, а все файлы учетных данных AWS, сертификатов и закрытых ключей находятся в правильном месте - дополнительную информацию можно найти в документации инструментов API AWS EC2.
Вы можете сначала протестировать команду вручную, а затем, когда все будет работать нормально, настроить Unix crontab или запланированные задачи в Windows. Вы можете найти приведенный ниже пример для файла Linux / etc / crontab (не забывайте, что все упомянутые выше переменные среды должны присутствовать для пользователя your-account.
/etc/crontab
0 8 * * * your-account ec2-start-instances <your_instance_id>
0 16 * * * your-account ec2-stop-instances <your_instance_id>
# Your instance will be started at 8am and shutdown at 4pm.
Я разработчик проекта BitNami Cloud, в котором мы упаковываем инструменты AWS (включая упомянутые мною) в бесплатный, простой в использовании установщик, который вы, возможно, захотите попробовать: Пакет пакетов BitNami CloudTools
Я рекомендую вам взглянуть на Руководство по началу работы с EC2 , в котором показано, как делать то, что вам нужно, с помощью инструментов командной строки EC2. Вы можете легко записать это в задание cron (в Linux / UNIX) или запланированное задание в Windows, чтобы вызвать команды запуска и остановки в заданное время.
Если вы хотите сделать это из собственного кода, вы можете использовать API-интерфейсы SOAP или REST; подробности см. в Руководстве разработчика .
Для этого я написал код на Python, используя библиотеку Boto. Вы можете настроить это для собственного использования. Обязательно запускайте это как часть задания cron, и тогда вы сможете запускать или выключать столько экземпляров, сколько вам нужно, во время выполнения заданий cron.
#!/usr/bin/python
#
# Auto-start and stop EC2 instances
#
import boto, datetime, sys
from time import gmtime, strftime, sleep
# AWS credentials
aws_key = "AKIAxxx"
aws_secret = "abcd"
# The instances that we want to auto-start/stop
instances = [
# You can have tuples in this format:
# [instance-id, name/description, startHour, stopHour, ipAddress]
["i-12345678", "Description", "00", "12", "1.2.3.4"]
]
# --------------------------------------------
# If its the weekend, then quit
# If you don't care about the weekend, remove these three
# lines of code below.
weekday = datetime.datetime.today().weekday()
if (weekday == 5) or (weekday == 6):
sys.exit()
# Connect to EC2
conn = boto.connect_ec2(aws_key, aws_secret)
# Get current hour
hh = strftime("%H", gmtime())
# For each instance
for (instance, description, start, stop, ip) in instances:
# If this is the hour of starting it...
if (hh == start):
# Start the instance
conn.start_instances(instance_ids=[instance])
# Sleep for a few seconds to ensure starting
sleep(10)
# Associate the Elastic IP with instance
if ip:
conn.associate_address(instance, ip)
# If this is the hour of stopping it...
if (hh == stop):
# Stop the instance
conn.stop_instances(instance_ids=[instance])
У компании, в которой я работаю, клиенты регулярно спрашивали об этом, поэтому мы написали бесплатное приложение для планирования EC2, доступное здесь:
http://blog.simple-help.com/2012/03/free-ec2-scheduler/
Он работает на Windows и Mac, позволяет создавать несколько ежедневных / еженедельных / ежемесячных расписаний и позволяет использовать соответствующие фильтры, чтобы легко включать большое количество экземпляров или включать те, которые вы добавите в будущем.
AWS Data Pipeline работает нормально. https://aws.amazon.com/premiumsupport/knowledge-center/stop-start-ec2-instances/
Если вы хотите исключить дни из начала (например, выходные), добавьте объект ShellCommandPrecondition.
В AWS Console / Data Pipeline создайте новый конвейер. Легче редактировать / импортировать определение (JSON)
{
"objects": [
{
"failureAndRerunMode": "CASCADE",
"schedule": {
"ref": "DefaultSchedule"
},
"resourceRole": "DataPipelineDefaultResourceRole",
"role": "DataPipelineDefaultRole",
"pipelineLogUri": "s3://MY_BUCKET/log/",
"scheduleType": "cron",
"name": "Default",
"id": "Default"
},
{
"name": "CliActivity",
"id": "CliActivity",
"runsOn": {
"ref": "Ec2Instance"
},
"precondition": {
"ref": "PreconditionDow"
},
"type": "ShellCommandActivity",
"command": "(sudo yum -y update aws-cli) && (#{myAWSCLICmd})"
},
{
"period": "1 days",
"startDateTime": "2015-10-27T13:00:00",
"name": "Every 1 day",
"id": "DefaultSchedule",
"type": "Schedule"
},
{
"scriptUri": "s3://MY_BUCKET/script/dow.sh",
"name": "DayOfWeekPrecondition",
"id": "PreconditionDow",
"type": "ShellCommandPrecondition"
},
{
"instanceType": "t1.micro",
"name": "Ec2Instance",
"id": "Ec2Instance",
"type": "Ec2Resource",
"terminateAfter": "50 Minutes"
}
],
"parameters": [
{
"watermark": "aws [options] <command> <subcommand> [parameters]",
"description": "AWS CLI command",
"id": "myAWSCLICmd",
"type": "String"
}
],
"values": {
"myAWSCLICmd": "aws ec2 start-instances --instance-ids i-12345678 --region eu-west-1"
}
}
Поместите сценарий Bash для загрузки и выполнения в качестве предварительного условия в вашей корзине S3
#!/bin/sh
if [ "$(date +%u)" -lt 6 ]
then exit 0
else exit 1
fi
При активации и запуске конвейера в выходные дни на консоли AWS Pipeline Health Status отображается вводящая в заблуждение «ERROR». Сценарий bash возвращает ошибку (выход 1), и EC2 не запускается. В дни с 1 по 5 статус «ЗДОРОВЫЙ».
Чтобы остановить EC2 автоматически во время закрытия офиса, используйте команду AWS CLI ежедневно без предварительных условий.
Вы можете посмотреть на Ylastic, чтобы сделать это. Альтернативой, похоже, является работа одной машины, которая выключает / запускает другие экземпляры с помощью задания cron или запланированной задачи.
Очевидно, что если вам нужен только один экземпляр, это дорогостоящее решение, поскольку одна машина должна работать постоянно, и платить ~ 80 долларов в месяц за выполнение заданий cron на одной машине не рентабельно.
AutoScaling ограничивается завершением экземпляров. Если вы хотите остановить экземпляр и сохранить состояние сервера, лучше всего использовать внешний сценарий.
Вы можете сделать это, запустив задание на другом экземпляре, который работает 24/7, или вы можете использовать сторонний сервис, такой как Ylastic (упомянутый выше) или Rocket Peak .
Например, в C # код для остановки сервера довольно прост:
public void stopInstance(string instance_id, string AWSRegion)
{
RegionEndpoint myAWSRegion = RegionEndpoint.GetBySystemName(AWSRegion);
AmazonEC2 ec2 = AWSClientFactory.CreateAmazonEC2Client(AWSAccessKey, AWSSecretKey, myAWSRegion);
ec2.StopInstances(new StopInstancesRequest().WithInstanceId(instance_id));
}
ИМХО, добавление расписания в группу автоматического масштабирования - лучший «облачный» подход, как упоминалось ранее.
Но если вы не можете прекратить работу своих экземпляров и использовать новые, например, если у вас есть эластичные IP-адреса, связанные с и т. Д.
Вы можете создать сценарий Ruby для запуска и остановки ваших экземпляров в зависимости от диапазона дат и времени.
#!/usr/bin/env ruby
# based on https://github.com/phstc/amazon_start_stop
require 'fog'
require 'tzinfo'
START_HOUR = 6 # Start 6AM
STOP_HOUR = 0 # Stop 0AM (midnight)
conn = Fog::Compute::AWS.new(aws_access_key_id: ENV['AWS_ACCESS_KEY_ID'],
aws_secret_access_key: ENV['AWS_SECRET_ACCESS_KEY'])
server = conn.servers.get('instance-id')
tz = TZInfo::Timezone.get('America/Sao_Paulo')
now = tz.now
stopped_range = (now.hour >= STOP_HOUR && now.hour < START_HOUR)
running_range = !stopped_range
if stopped_range && server.state != 'stopped'
server.stop
end
if running_range && server.state != 'running'
server.start
# if you need an Elastic IP
# (everytime you stop an instance Amazon dissociates Elastic IPs)
#
# server.wait_for { state == 'running' }
# conn.associate_address server.id, 127.0.0.0
end
Взгляните на amazon_start_stop, чтобы создать планировщик бесплатно с помощью Heroku Scheduler .
Несмотря на то, что есть способы добиться этого с помощью автоматического масштабирования, он может не подходить для всех случаев, поскольку он завершает экземпляры. Задания Cron никогда не будут работать для одного экземпляра (хотя его можно идеально использовать для таких ситуаций, как остановка одного экземпляра и планирование других экземпляров при запуске нескольких экземпляров). Вы можете использовать вызовы API, такие как StartInstancesRequest и StopInstancesRequest, чтобы добиться того же, но опять же вам придется полагаться на третий ресурс. Существует множество приложений для планирования экземпляров AWS с множеством функций, но для простого решения я бы порекомендовал бесплатное приложение, например snapleaf.io.
Да, это можно сделать с помощью AWS Lambda. Вы можете выбрать триггер в Cloudwatch, который работает на выражениях Cron в UTC.
Вот соответствующая ссылка https://aws.amazon.com/premiumsupport/knowledge-center/start-stop-lambda-cloudwatch/
Другой альтернативой является использование awscli
которая доступна pip
, apt-get
, yum
или brew
, а затем работает aws configure
с учетными данными , экспортируемые из IAM и выполнив следующий Баш скрипт, чтобы остановить EC2, которая была помечена с Name: Appname
и Value: Appname Prod
. Вы можете использовать awscli
для тегирования экземпляров или вручную с консоли AWS. aws ec2 stop-instances
остановит экземпляр и jq
будет использоваться для фильтрации запроса json и получения правильного идентификатора экземпляра с помощью тегов из aws ec2 describe-instances
.
Чтобы убедиться, что это aws configure
было успешным и возвращает вывод json, запустите, aws ec2 describe-instances
и ваш идентификатор запущенного экземпляра должен быть в выводе. Вот пример вывода
{
"Reservations": [
{
"Instances": [
{
"Monitoring": {
"State": "disabled"
},
"PublicDnsName": "ec2-xxx.ap-south-1.compute.amazonaws.com",
"State": {
"Code": xx,
"Name": "running"
},
"EbsOptimized": false,
"LaunchTime": "20xx-xx-xxTxx:16:xx.000Z",
"PublicIpAddress": "xx.127.24.xxx",
"PrivateIpAddress": "xxx.31.3.xxx",
"ProductCodes": [],
"VpcId": "vpc-aaxxxxx",
"StateTransitionReason": "",
"InstanceId": "i-xxxxxxxx",
"ImageId": "ami-xxxxxxx",
"PrivateDnsName": "ip-xxxx.ap-south-1.compute.internal",
"KeyName": "node",
"SecurityGroups": [
{
"GroupName": "xxxxxx",
"GroupId": "sg-xxxx"
}
],
"ClientToken": "",
"SubnetId": "subnet-xxxx",
"InstanceType": "t2.xxxxx",
"NetworkInterfaces": [
{
"Status": "in-use",
"MacAddress": "0x:xx:xx:xx:xx:xx",
"SourceDestCheck": true,
"VpcId": "vpc-xxxxxx",
"Description": "",
"NetworkInterfaceId": "eni-xxxx",
"PrivateIpAddresses": [
{
"PrivateDnsName": "ip-xx.ap-south-1.compute.internal",
"PrivateIpAddress": "xx.31.3.xxx",
"Primary": true,
"Association": {
"PublicIp": "xx.127.24.xxx",
"PublicDnsName": "ec2-xx.ap-south-1.compute.amazonaws.com",
"IpOwnerId": "xxxxx"
}
}
],
"PrivateDnsName": "ip-xxx-31-3-xxx.ap-south-1.compute.internal",
"Attachment": {
"Status": "attached",
"DeviceIndex": 0,
"DeleteOnTermination": true,
"AttachmentId": "xxx",
"AttachTime": "20xx-xx-30Txx:16:xx.000Z"
},
"Groups": [
{
"GroupName": "xxxx",
"GroupId": "sg-xxxxx"
}
],
"Ipv6Addresses": [],
"OwnerId": "xxxx",
"PrivateIpAddress": "xx.xx.xx.xxx",
"SubnetId": "subnet-xx",
"Association": {
"PublicIp": "xx.xx.xx.xxx",
"PublicDnsName": "ec2-xx.ap-south-1.compute.amazonaws.com",
"IpOwnerId": "xxxx"
}
}
],
"SourceDestCheck": true,
"Placement": {
"Tenancy": "default",
"GroupName": "",
"AvailabilityZone": "xx"
},
"Hypervisor": "xxx",
"BlockDeviceMappings": [
{
"DeviceName": "/dev/xxx",
"Ebs": {
"Status": "attached",
"DeleteOnTermination": true,
"VolumeId": "vol-xxx",
"AttachTime": "20xxx-xx-xxTxx:16:xx.000Z"
}
}
],
"Architecture": "x86_64",
"RootDeviceType": "ebs",
"RootDeviceName": "/dev/xxx",
"VirtualizationType": "xxx",
"Tags": [
{
"Value": "xxxx centxx",
"Key": "Name"
}
],
"AmiLaunchIndex": 0
}
],
"ReservationId": "r-xxxx",
"Groups": [],
"OwnerId": "xxxxx"
}
]
}
Следующий сценарий Баш находится stop-ec2.sh
в /home/centos/cron-scripts/
которых вдохновлен этой должности SO
(instance=$(aws ec2 describe-instances | jq '.Reservations[].Instances | select(.[].Tags[].Value | startswith("Appname Prod") ) | select(.[].Tags[].Key == "Appname") | {InstanceId: .[].InstanceId, PublicDnsName: .[].PublicDnsName, State: .[].State, LaunchTime: .[].LaunchTime, Tags: .[].Tags} | [.]' | jq -r .[].InstanceId) && aws ec2 stop-instances --instance-ids ${instance} )
Запустите файл с помощью sh /home/centos/cron-scripts/stop-ec2.sh
и убедитесь, что экземпляр EC2 остановлен. Для отладки запустите aws ec2 describe-instances | jq '.Reservations[].Instances | select(.[].Tags[].Value | startswith("Appname Prod") ) | select(.[].Tags[].Key == "Appname") | {InstanceId: .[].InstanceId, PublicDnsName: .[].PublicDnsName, State: .[].State, LaunchTime: .[].LaunchTime, Tags: .[].Tags} | [.]' | jq -r .[].InstanceId
и убедитесь, что он возвращает правильный идентификатор экземпляра, который был помечен.
Затем в crontab -e
следующей строке можно добавить
30 14 * * * sh /home/centos/cron-scripts/stop-ec2.sh >> /tmp/stop
который будет записывать вывод в /tmp/stop
. Это 30 14 * * *
выражение UTC cron, которое вы можете проверить https://crontab.guru/
. Аналогичным образом замена на aws ec2 start-instances
может запустить экземпляр.
Я считаю, что первоначальный вопрос немного сбивал с толку. Это зависит от того, что нужно Pasta: 1. запуск / завершение (хранилище экземпляров) - автоматическое масштабирование - правильное решение (ответ Nakedible) 2. запуск / остановка экземпляра загрузки EBS - автоматическое масштабирование не поможет, я использую удаленные запланированные сценарии (т.е. , интерфейс командной строки ec2).
Вы не можете сделать это автоматически или, по крайней мере, без некоторого программирования и манипуляций API в файлах сценариев. Если вам нужно надежное решение для остановки, перезапуска и управления вашими изображениями (предположительно, для контроля затрат в вашей среде), вы можете взглянуть на LabSlice . Отказ от ответственности: я работаю в этой компании.