Как передать код ошибки из пользовательских данных в конвейер кода, чтобы указать на сбой

#amazon-web-services #amazon-ec2 #aws-codepipeline

#amazon-web-services #amazon-ec2 #aws-codepipeline

Вопрос:

У меня есть требование, согласно которому я буду загружать jar из s3 с другой версией в экземпляр ec2. Я сделаю это как часть раздела userdata . Все работает нормально. Предположим, что если jar недоступен, приложение не запускается. У меня есть проверка для этого и возвращает значение, отличное от 0 (т.е. Выход 1 ). В cloud-init-output.log я вижу сообщение об ошибке и его выход из системы со значением, отличным от 0. Но на этапе конвейера он показывает успех. Ниже приведен пример кода:

 echo "Post deployment checks"

if [ `netstat -ntpl | grep java | grep 8080 | wc -l` -eq 0 ]
    then
        echo "Application doesn't listen 8080 port"
        echo "Deployment is unsuccessful!"
        exit 1
    else
        echo "Application listens 8080 port"
fi
  

Мой вопрос в том, как я могу передать значение обратно в конвейер, чтобы обработка остановилась на этапе, если приложение не запущено.

Комментарии:

1. Какое действие в конвейере инициирует это?

2. Тип действия — Развертывание

3. — Имя: CreateEC2Stack InputArtifacts: — Имя: SourceOutput ActionTypeId: Категория: Развертывание Владелец: Поставщик AWS: CloudFormation Версия: 1 Конфигурация: ActionMode: REPLACE_ON_FAILURE StackName: ! Sub scs-${EnvironmentName}-${Region}-${PipelineType}-hds-ec2 RoleArn: !Ссылка на CodePipelineExecutionRoleArn Возможности: CAPABILITY_NAMED_IAM Путь к шаблону: SourceOutput::ec2-route53.yaml

Ответ №1:

В вашем шаблоне CloudFormation можно дождаться получения сигнала перед завершением. Если этот сигнал не получен в течение времени ожидания, произойдет ОТКАТ шаблона, и ваше развертывание завершится неудачно. Есть несколько способов сделать это. Вот несколько вариантов документации.

https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/cfn-signal.html
https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/using-cfn-waitcondition.html

Я бы предпочел первый вариант, просто добавьте a CreationPolicy в экземпляр EC2, а затем сообщите об этом UserData . Вот так:

 Resources:
  AppEC2Instance:
    Type: "AWS::EC2::Instance"
    CreationPolicy:
      ResourceSignal:
        Timeout: "PT5M"
    Properties:
      UserData:
        Fn::Base64:
          Fn::Join:
            - ""
            - - "#!/bin/bash -xn"
              - "aws s3 sync s3://mybucket-id/ ./n"
              - "java -jar ./app.jarn"
              - "/opt/aws/bin/cfn-signal -e $? --stack ",
              - !Ref AWS::StackName
              - " --resource AppEC2Instance --region "
              - !Ref AWS::Region
              - "n"
  

Использование -e $? должно предоставить код выхода обратно в стек и, я надеюсь, затем отправить его обратно в конвейер.

Ответ №2:

Я могу придумать три варианта высокого уровня, чтобы вернуть сбой в конвейер:

  1. Выясните, как выполнить сбой обновления стека CloudFormation при сбое инициализации облака.
  2. Добавьте последующее действие в конвейер (например, лямбда-вызов), где вы пишете некоторый код для сбоя действия в случае сбоя cloud-init.
  3. Используйте что-то вроде CodeDeploy для управления развертываниями в экземплярах EC2.