Рубрики
Uncategorized

Часть 3 — Простой экземпляр EC2 — AWESOME AWS CDK

Введение Bootstrapa для новой структуры приложения CDK и настройка структуры приложения CDK … Помечено AWS, AWSCDK, EC2, DEVOPS.

Awesome AWS CDK (4 части серии)

  • Вступление
  • Загрузка нового приложения CDK
  • Структура и настройка приложения CDK
    • Состав
    • Настраивать
  • Написание инфраструктурного кода
  • Создание новой ключевой пары в консоли AWS
  • Развертывать
  • Доступ к экземпляру
  • Обновление развернутого стека
  • Тестирование стека
    • Тестовые требования
  • Уничтожать стек
  • Примечания
  • Заключение
  • Следующий

Вступление

Большинство учебных пособий на AWS пытаются заставить вас развернуть всемирно известный T2.Micro Экземпляр (небольшой виртуальный сервер под уровнем бесплатного использования на AWS) с использованием консоли AWS. Затем вы продолжаете установить что-то вроде WordPress через SSH или через Пользовательский скрипт (Сценарий, который работает при создании экземпляра), который вы определяете в консоли AWS.

Так что именно то, что мы собираемся развернуть. Но вместо этого мы будем использовать AWS CDK.

Это то, что вы узнаете в этом руководстве:

  • Загрузка нового приложения CDK
  • Структура и настройка приложения CDK
  • Как обеспечить и установить экземпляр EC2
  • Как настроить доступ клеммы к экземпляру через SSH клавишу.
  • Как обновить экземпляр EC2 с помощью пользовательского скрипта и обновить развернутый стек CDK
  • Как написать тесты для приложения CDK
  • Как уничтожить развернутый стек

Пойдем!

Загрузка нового приложения CDK

Использование вашего терминала создайте новый каталог Simple-EC2 и CD в это:

mkdir simple-ec2 && cd simple-ec2

Раньше мы настроили AWS CDK CLI глобально. Если вы этого не сделали, чтобы увидеть часть 2 в этой серии.

Bootstrap Новый шаблон проекта CDK, который использует TeampScript:

cdk init --language=typescript

Это инициализирует новый проект CDK для вас в Teadercript.

  • Беги Обновление NPM Чтобы убедиться, что вы используете последнюю версию CDK.
  • Если у вас есть версию конфликтов между @ AWS-CDK/CORE и другие @ AWS-CDK Sub-Packages, затем вы встретите некоторые странные ошибки. @ AWS-CDK/CORE и все остальные импортированные @ AWS-CDK/пакет должен иметь ту же версию.

Структура и настройка приложения CDK

Состав

# tree -I 'node_modules'
.
├── bin
│   └── simple-ec2.ts       # entry point
├── cdk.json
├── jest.config.js          # for tests
├── lib                     # where the infrastructure code you write will go
│   └── simple-ec2-stack.ts 
├── package.json
├── package-lock.json
├── README.md
├── test                    # test folder
│   └── simple-ec2.test.ts
└── tsconfig.json
  • ./bin/simple-ec2.ts это файл точек входа, используемый CDK. Это то, где вы определяете свой стек (ы).
  • IAC, которые предусматривают ресурсы, будут внутри lib папка и требуется по ./bin/simple-ec2.ts Во время синтезатор и Развертывание . Действия. Я объясню обе команды позже.
  • ./test/simple-ec2.test.ts Содержит код шаблона для проверки вашего приложения CDK

Настраивать

В ./bin/simple-ec2.ts Новый Приложение () определяется, и это представляет собой один стек.

  • Мы можем добавить описание для нашего стека в этом файле.
  • Это описание будет видно в CloudFormation Console:
// ./bin/simple-ec2.ts

import 'source-map-support/register';
import * as cdk from '@aws-cdk/core';
import { SimpleEc2Stack } from '../lib/simple-ec2-stack';

const app = new cdk.App();
new SimpleEc2Stack(app, 'SimpleEc2Stack', {
   description: 'This is a simple EC2 stack'
});

Давайте отправимся на ./lib/simple-ec2-stack.ts И посмотрите, какой CDK Boostrapped для нас:

// ./lib/simple-ec2-stack.ts

import * as cdk from '@aws-cdk/core';

export class SimpleEc2Stack extends cdk.Stack {
  constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
    super(scope, id, props);

    // The code that defines your stack goes here
  }
}

Как видите, cdk init Команда загрузовать приятный шаблон для нас, чтобы написать наш IAC быстро. Базовый класс CDK. Стек Дает нам возможность создавать новый стопку облака.

Нам также нужно создать .env файл, чтобы сохранить наши AWS Номер счета и регион, который мы будем использовать. В корне проекта создайте файл под названием .env и добавьте следующее. Заменить xxxxxxxxxxxxx С номером учетной записи AWS и используйте нужный регион.

AWS_ACCOUNT_NUMBER=xxXxXxxXXxXxx
AWS_ACCOUNT_REGION=us-west-2

Написание инфраструктурного кода

Мы хотим создать экземпляр EC2, поэтому нам понадобится @ AWS-CDK/EC2 библиотека. (Это тот же процесс для любого другого обслуживания AWS, необходимых для предоставления ресурсов). Мы также понадобится @ AWS-CDK/AWS-IAM Библиотека, чтобы дать разрешения на наш случай, чтобы сделать вещи. Мы также хотим иметь возможность читать наши .env Файл, так что давайте также устанавливаем Доценв упаковка

npm install @aws-cdk/aws-ec2 @aws-cdk/aws-iam dotenv

Помните, поскольку CDK написан в Teadercript и набирает превосходно, при наборе вы можете получить доступ к Intellisense и увидеть различные свойства ресурсов CDK E.G. На изображении ниже я вижу, какие свойства экземпляра EC2.Instance () класс имеет.

Здесь идет наша первая итерация:

import * as cdk from '@aws-cdk/core'
import * as ec2 from '@aws-cdk/aws-ec2' // import ec2 library 
import * as iam from '@aws-cdk/aws-iam' // import iam library for permissions

require('dotenv').config()

const config = {
  env: {
    account: process.env.AWS_ACCOUNT_NUMBER,
    region: process.env.AWS_REGION
  }
}

export class SimpleEc2Stack extends cdk.Stack {
  constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
    // its important to add our env config here otherwise CDK won't know our AWS account number
    super(scope, id, { ...props, env: config.env })

    // Get the default VPC. This is the network where your instance will be provisioned
    // All activated regions in AWS have a default vpc. 
    // You can create your own of course as well. https://aws.amazon.com/vpc/
    const defaultVpc = ec2.Vpc.fromLookup(this, 'VPC', { isDefault: true })

    // Lets create a role for the instance
    // You can attach permissions to a role and determine what your
    // instance can or can not do
      const role = new iam.Role(
        this,
        'simple-instance-1-role', // this is a unique id that will represent this resource in a Cloudformation template
        { assumedBy: new iam.ServicePrincipal('ec2.amazonaws.com') }
      )

    // lets create a security group for our instance
    // A security group acts as a virtual firewall for your instance to control inbound and outbound traffic.
    const securityGroup = new ec2.SecurityGroup(
      this,
      'simple-instance-1-sg',
      {
        vpc: defaultVpc,
        allowAllOutbound: true, // will let your instance send outboud traffic
        securityGroupName: 'simple-instance-1-sg',
      }
    )

    // lets use the security group to allow inbound traffic on specific ports
    securityGroup.addIngressRule(
      ec2.Peer.anyIpv4(),
      ec2.Port.tcp(22),
      'Allows SSH access from Internet'
    )

    securityGroup.addIngressRule(
      ec2.Peer.anyIpv4(),
      ec2.Port.tcp(80),
      'Allows HTTP access from Internet'
    )

    securityGroup.addIngressRule(
      ec2.Peer.anyIpv4(),
      ec2.Port.tcp(443),
      'Allows HTTPS access from Internet'
    )

    // Finally lets provision our ec2 instance
    const instance = new ec2.Instance(this, 'simple-instance-1', {
      vpc: defaultVpc,
      role: role,
      securityGroup: securityGroup,
      instanceName: 'simple-instance-1',
      instanceType: ec2.InstanceType.of( // t2.micro has free tier usage in aws
        ec2.InstanceClass.T2,
        ec2.InstanceSize.MICRO
      ),
      machineImage: ec2.MachineImage.latestAmazonLinux({
        generation: ec2.AmazonLinuxGeneration.AMAZON_LINUX_2,
      }),

      keyName: 'simple-instance-1-key', // we will create this in the console before we deploy
    })

    // cdk lets us output prperties of the resources we create after they are created
    // we want the ip address of this new instance so we can ssh into it later
    new cdk.CfnOutput(this, 'simple-instance-1-output', {
      value: instance.instancePublicIp
    })
  }
}

Создание новой ключевой пары в консоли AWS

Прежде чем мы попытаемся развернуть наш вновь созданный экземпляр, нам нужно перейти к консоли AWS и создать ключевую пару, которую мы будем использовать для доступа к экземпляру, называемыми простой-экземпляр-1 ключ

  • Войдите в консоль AWS.
  • Перейти к EC2 щиток приборов.
  • Перейдите к ключам Пары и нажмите Создать пару ключей
  • Введите имя ключа как Простой-экземпляр-1-ключ и нажмите Create
  • Ваша новая пара клавиши будет создана, и ваш браузер автоматически загрузит новый .пем Файл под названием простой экземпляр-1 ключ.pem
  • Это ключевой файл, который вы будете использовать для получения доступа к вашему экземпляру через SSH
  • Создайте новый каталог под .aws/ называется преступность
mkdir ~./aws/pems/
  • Переместите вновь загруженный файл в этот каталог и дайте ему необходимые разрешения
mv ~/Downloads/simple-instance-1-key.pem ~/.aws/pems

# important step or your key file won't work
chmod 400 ~/.aws/pems/simple-instance-1-key.pem
  • Теперь, когда у нас есть наш ключ файл правильно настроен, давайте развертываем наш экземпляр!

Развертывать

Помните, что мы создали наши профили AWS и Credsnetials в ~/.aws/config и ~/.aws/учетные данные Вернуться в Часть 2

Я буду развернуть мой по умолчанию Профиль, который связан с моей учетной записью AWS в регионе США-Запад-2 Отказ

Если у вас есть другой профиль, который вы хотите использовать, то в приведенных ниже командах используйте это имя профиля вместо по умолчанию Отказ

В вашем терминале:

cdk synth --profile default

Эта команда будет синтезировать ваш стек.

Когда приложения CDK выполняются, они производят (или «синтезировать», в Pormance CDK) шаблон CDK CloudFation для каждого стека, определенного в вашем приложении.

  • По сути, это будет распечатать шаблон CloudFation для вашего стека в вашу консоль.
  • Это хороший способ проверить, что в вашем стеке нет ничего плохого, прежде чем пытаться развернуть с тех пор CDK Synth проверит ресурсы, которые вы пытаетесь обеспечить, можно на самом деле.
  • Вы должны что-то вроде этого:
❯ cdk synth --profile default
Resources:
  simpleinstance1role9EEDA67C:
    Type: AWS::IAM::Role
    Properties:
      AssumeRolePolicyDocument:
        Statement:
          - Action: sts:AssumeRole
            Effect: Allow
            Principal:
              Service: ec2.amazonaws.com
        Version: "2012-10-17"
   ...
   ...
   ...

Если весь стек печатается без ошибки, вы в порядке, чтобы пойти.

Теперь мы можем развернуть:

cdk deploy --profile default

Вы должны получить быстрый доступ к области облака, чтобы позволить созданию ресурсов, которые нуждаются в одобрении. Тип y и нажмите Введите продолжить с развертыванием:

Вы начнете видеть вывод от CloudFation в вашей консоли, поскольку создается стек.

Когда стек был успешно развернут, вы должны увидеть:

Обратите внимание на вывод, который мы определили в конце стека. CDK печатал публичный IP-адрес вновь созданного экземпляра для нас, потому что мы сказали это, потрясающе! Вы можете использовать этот метод для распечатки любого значения, когда стек успешно развернут.

В качестве альтернативы вы можете получить эту информацию из консоли EC2, проверив на приборной панели экземпляров.

Доступ к экземпляру

Давайте SSH в наш недавно созданный экземпляр с нашим ключевым файлом и публичным IP-адресом.

Примечание: что по умолчанию Пользователь Для Amazon Linux изображения это EC2-пользователь

ssh -i ~/.aws/pems/simple-instance-1-key.pem ec2-user@34.220.79.175

Теперь вы должны быть в состоянии войти в ваш экземпляр!

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

Давайте исправить это!

Добавление пользовательского скрипта

  • Давайте создадим новый файл под ./lib/ каталог называется user_script.sh Отказ Вставьте этот код в этот файл.
  • Этот код будет развернуть Apache, WordPress, MySQL Server в этом экземпляре. В этом скрипте пароль базы данных будет pl55w0rd Отказ
  • Очень небезопасно добавлять пароли для скриптов, но в этом случае я делаю это только для демонстрационных целей.
  • В производстве вы должны сначала никогда не использовать такой слабый пароль и во-вторых, а не внутри такого сценария.
  • Скорее, вам следует развернуть базу данных MySQL на учетных данных AWS RDS и настроить учетные данные для этой базы данных с использованием менеджера Saw Secrets.

Вот файл установки:

#! /bin/bash
# become root user
sudo su

# update dependencies
yum -y update

# we'll install 'expect' to input keystrokes/y/n/passwords
yum -y install expect 

# Install Apache
yum -y install httpd

# Start Apache
service httpd start

# Install PHP
yum -y install php php-mysql
# php 7 needed for latest wordpress
amazon-linux-extras -y install php7.2 

# Restart Apache
service httpd restart

# Install MySQL
wget http://repo.mysql.com/mysql-community-release-el7-5.noarch.rpm
rpm -ivh mysql-community-release-el7-5.noarch.rpm

yum -y update 
yum -y install mysql-server

# Start MySQL
service mysqld start

# Create a database named blog
mysqladmin -uroot create blog

# Secure database
# non interactive mysql_secure_installation with a little help from expect.

SECURE_MYSQL=$(expect -c "

set timeout 10
spawn mysql_secure_installation

expect \"Enter current password for root (enter for none):\"
send \"\r\"

expect \"Change the root password?\"
send \"y\r\"
expect \"New password:\"
send \"pl55w0rd\r\"
expect \"Re-enter new password:\"
send \"pl55w0rd\r\"
expect \"Remove anonymous users?\"
send \"y\r\"

expect \"Disallow root login remotely?\"
send \"y\r\"

expect \"Remove test database and access to it?\"
send \"y\r\"

expect \"Reload privilege tables now?\"
send \"y\r\"

expect eof
")

echo "$SECURE_MYSQL"

# Change directory to web root
cd /var/www/html

# Download WordPress
wget http://wordpress.org/latest.tar.gz

# Extract WordPress
tar -xzvf latest.tar.gz

# Rename wordpress directory to blog
mv wordpress blog

# Change directory to blog
cd /var/www/html/blog/

# Create a WordPress config file 
mv wp-config-sample.php wp-config.php

#set database details with perl find and replace
sed -i "s/database_name_here/blog/g" /var/www/html/blog/wp-config.php
sed -i "s/username_here/root/g" /var/www/html/blog/wp-config.php
sed -i "s/password_here/pl55w0rd/g" /var/www/html/blog/wp-config.php

# create uploads folder and set permissions
mkdir wp-content/uploads
chmod 777 wp-content/uploads

#remove wp file
rm -rf /var/www/html/latest.tar.gz

Нам нужно будет добавить ФС Модуль в верхней части нашего ./lib/simple-ec2-stack.ts Файл с instance.adduserdata () необходимо получить доступ к файловой системе во время развертывания.

import * as cdk from '@aws-cdk/core'
import * as ec2 from '@aws-cdk/aws-ec2' // import ec2 library 
import * as iam from '@aws-cdk/aws-iam' // import iam library for permissions

// lets include fs module
import * as fs from 'fs'

Тогда мы можем функцию instance.adduserdata () Прямо перед нашей функцией вывода:

...

    // add user script to instance
    // this script runs when the instance is started 
    instance.addUserData(
      fs.readFileSync('lib/user_script.sh', 'utf8')
    )

    // cdk lets us output prperties of the resources we create after they are created
    // we want the ip address of this new instance so we can ssh into it later
    new cdk.CfnOutput(this, 'simple-instance-1-output', {
      value: instance.instancePublicIp
    })
...

Обновите развернутый стек

Давайте повторно синтезировать, чтобы проверить все в порядке:

cdk --synth --profile default
  • Теперь вы должны увидеть команды пользовательских скриптов в синтез выход
  • Давайте разверним наши новые изменения.
  • Облачная информация будет обновлять только ресурсы, которые обновляются.
  • В этом случае обновляется только экземпляр EC2.
  • Другими вещами, подобными ролям и группам безопасности, останутся, поскольку они нет, поскольку в обновленном стеке нет изменений.
cdk --deploy --profile default

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

Давайте воспользуемся выведенным IP-адресом и проверьте, что WordPress, MySQL и PHP были установлены правильно:

  • В вашем браузере перейдите к http:///блог

  • Вы должны посмотреть:

  • И тогда вы можете завершить установку WordPress!
  • Помните свои учетные данные базы данных root и pl55w0rd Как определено в скрипте

Тестирование стека

Ну, мы знаем, что наш код CDK работает и может предусматривать экземпляр EC2 для запуска нашего сервера и базы данных WordPress. Хороший.

Но как мы можем убедиться, что изменения в код CDK не делают то, что мы не хотим делать?

Вот где приходят испытания.

Тестовые требования

  • Я не хочу никакого экземпляра Другое T2.Micro. Для использования в качестве моего типа экземпляра сервера, потому что я всегда хочу остаться под AWS Free Tier Usage для EC2. Давайте гарантируем это.
  • Я хочу убедиться, что мой экземпляр использует ключ SSH с именем простой-экземпляр-1 ключ

Для этого мы изменяем код внутри файла ./test/simple-ec2.test.ts к:

import { expect as expectCDK, haveResourceLike } from '@aws-cdk/assert';
import * as cdk from '@aws-cdk/core';
import * as SimpleEc2 from '../lib/simple-ec2-stack';

test('Check InstanceType and SSH KeyName', () => {
    const app = new cdk.App();
    const stack = new SimpleEc2.SimpleEc2Stack(app, 'MyTestStack');

    expectCDK(stack).to(
      haveResourceLike('AWS::EC2::Instance', {
        InstanceType: 't2.micro',
        KeyName: 'simple-instance-1-key'
      })
    )
});

Как вы можете видеть из тестового кода, тест проверит генерированный шаблон CloudFormation, генерируемый CDK.

В нашем случае мы хотим проверить, что экземпляр A T2.Micro и что он использует ключ SSH Простой-экземпляр-1-ключ Отказ Это два важных недвижимости для нас.

Вы можете узнать больше о тестировании инфраструктуры с CDK здесь здесь

Запустите тест:

npm test

Все хорошо!

И теперь ваш код должен быть в состоянии запустить тест перед развертыванием вашей инфраструктуры! Фантастика!

npm test && cdk deploy --profile default

Уничтожать стек

Если вы хотите уничтожить инфраструктуру, вы только что предоставили, это так же просто, как:

cdk destroy --profile default

И облачность удалит весь ваш стек!

Примечания:

  • Не рекомендуется запускать MySQL в том же экземпляре, что и ваш сервер WordPress. Вместо этого вы можете использовать AWS управляемую службу базы данных RDS Развернуть базу данных, которую использует WordPress.
  • Не помещайте конфиденциальную информацию, такую как пароли в пользовательских сценариях, поскольку во многих случаях они преданы исходному контролю или их вывод виден в консоли CI/CD или истории терминалов экземпляра.

Заключение

AWS CDK делает писать IAC, предоставление, развертывание, обновление и уничтожение инфраструктуры очень безболезненно. Вы можете написать тесты, чтобы убедиться, что вы не развертываете неправильные вещи.

Это был простой пример и может показаться довольно много, чтобы развернуть экземпляр EC2. Однако, как мы прогрессируемся через серию, вы поймете, как это очень полезно для сложной инфраструктуры.

Следующий

В части 4, используя CDK, мы сделаем наш сервер WordPress больше добычи. Мы будем:

  • Создайте базу данных AWS RDS MySQL вместо того, чтобы запустить базу данных на экземпляре EC2
  • Предоставление этой базы данных в изолированной подсети, чтобы сохранить ее в безопасности от общественного Интернета
  • Используйте AWS SSM для доступа к нашему экземпляру вместо SSH клавиши и получите все преимущества разрешений/ролей IAM
  • Разверните балансировщик нагрузки приложения
  • Создайте наш экземпляр EC2 с лучшим/более продвинутым скриптом
  • Поместите экземпляр WordPress в группе AutoScaling

Привет, я Эммануэль ! Я пишу о программном обеспечении и DEVOPS.

Если вам понравилась эта статья и хочешь увидеть больше, добавьте меня на LinkedIn или следовать за мной на Твиттер

Awesome AWS CDK (4 части серии)

Оригинал: «https://dev.to/emmanuelnk/part-3-simple-ec2-instance-awesome-aws-cdk-37ia»