概要
RDSを仕事で本格的に触る機会が増え、自宅でも検証など実施したくEC2で踏み台サーバー(いわゆるBastion)を作ってみたいと思いました。
検証する際はpublicなRDSではなくPrivateなRDSでいろいろ弄りたい。
(別にpublicなRDSならendpointさえ分かれば接続できる)
ただできるだけお金はかけたくなく、PrivateなEC2、かつローカルのLinuxからアクセスして作業することはできないかと調べていたところ「EC2 Instance Connect Endpoint」というものがあることを知りました。
しかも料金は無料!
こちらの記事を参考にterraformを利用して構築してみたいと思います。
この記事はそのメモやまとめです。
すでに設定済みの項目がいくつかある。
試行錯誤しながらやったので、手順として不要かもしれない。あくまでメモ用。
必要なリソースとterraformでも記載方法
必要なリソースは
- ECIエンドポイント用SG
- EC2用SG
- EICエンドポイント(VPC endpoint)
- EC2
で実現できるようです。
terraformについては
あたりを使えばできそうですね。
terraformに落とし込むに当たりこちらを参考にもしました。
terraformで実装
試行錯誤して最終的には以下のようになりました。
# EIC Endpoint SG
resource "aws_security_group" "bastion_eci" {
vpc_id = aws_vpc.vpc.id
name = "bastion_for_eci_allow_ssh"
egress {
from_port = 22
to_port = 22
protocol = "tcp"
cidr_blocks = ["0.0.0.0/0"]
}
}
# Bastion ec2 SG
resource "aws_security_group" "bastion_ec2" {
vpc_id = aws_vpc.vpc.id
name = "bastion_for_ec2_allow_ssh_from_eci"
ingress {
from_port = 22
to_port = 22
protocol = "tcp"
security_groups = [aws_security_group.bastion_eci.id]
}
egress {
from_port = 0
to_port = 0
protocol = "-1"
cidr_blocks = ["0.0.0.0/0"]
ipv6_cidr_blocks = ["::/0"]
}
}
# EC2 Instance Connect Endpoint
resource "aws_ec2_instance_connect_endpoint" "for_bastion_eic" {
subnet_id = aws_subnet.subnet_public_AZa.id
security_group_ids = [aws_security_group.bastion_eci.id]
preserve_client_ip = true
}
# Amazon Linuxの最新AMIを取得
data "aws_ami" "amazon-linux-2" {
most_recent = true #最新版を指定
owners = ["amazon"]
filter {
name = "owner-alias"
values = ["amazon"]
}
filter {
name = "name"
values = ["amzn2-ami-hvm-*-x86_64-gp2"]
}
}
# bastion ec2
resource "aws_instance" "bastion" {
ami = data.aws_ami.amazon-linux-2.id # Amazon Linux 2
instance_type = "t3.nano"
subnet_id = aws_subnet.subnet_private_AZa.id # private subnet
vpc_security_group_ids = [aws_security_group.bastion_ec2.id]
tags = {
Name = "bastion-ec2"
}
lifecycle {
ignore_changes = [
ami,
]
}
}
appyします。
ここでつまずき。
terraformのaws providersが古く、aws_ec2_instance_connect_endpoint
を認識できなかった。
以下のように最新のproviderを指定して上げることで回避することができました。
required_version = ">= 0.15"
required_providers {
aws = {
source = "hashicorp/aws"
version = "5.19.0"
}
}
}
接続してみる(コンソール)
繋がった!
(どうでもいいけどEC2ってでかでかと出てきていた記憶あるのですが今は鳩?になっているのですね)
接続してみる(ターミナル)
aws ec2-instance-connect ssh --instance-id i-xxxxxxx --connection-type eice --region ap-northeast-1
ここでつまずき2。
~ via 🐍 v3.10.8
at 16:55:17 ⬢ [Docker] ❯ aws-vault exec xxxxx -- aws ec2-instance-connect ssh --instance-id i-xxxxxx
usage: aws [options] <command> <subcommand> [<subcommand> ...] [parameters]
To see help text, you can run:
aws help
aws <command> help
aws <command> <subcommand> help
aws: error: argument operation: Invalid choice, valid choices are:
send-ssh-public-key | send-serial-console-ssh-public-key
help
コマンドが認識されていないので、多分aws cliが古いのではと予想。
~ via 🐍 v3.10.8
at 16:57:31 ⬢ [Docker] ❯ aws --version
aws-cli/2.7.14 Python/3.9.11 Linux/5.10.16.3-microsoft-standard-WSL2 exe/x86_64.almalinux.8 prompt/off
~ via 🐍 v3.10.8
at 17:02:01 ⬢ [Docker] ❯
予想通り古かった。
最新に更新する。
curl "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o "awscliv2.zip"
unzip awscliv2.zip
sudo ./aws/install --update
versionを確認してみる。
~ via 🐍 v3.10.8
at 18:07:07 ⬢ [Docker] ❯ aws --version
aws-cli/2.13.22 Python/3.11.5 Linux/5.10.16.3-microsoft-standard-WSL2 exe/x86_64.almalinux.8 prompt/off
~ via 🐍 v3.10.8
at 18:07:09 ⬢ [Docker] ❯
新しくなっているので再度実行。
~ via 🐍 v3.10.8
at 18:07:09 ⬢ [Docker] ❯ aws ec2-instance-connect ssh --instance-id i-xxxxxx --connection-type eice --region ap-northeast-1
Last login: Fri Sep 29 09:01:50 2023 from 88.15.62.130.shared.user.transix.jp
, #_
~\_ ####_ Amazon Linux 2
~~ \_#####\
~~ \###| AL2 End of Life is 2025-06-30.
~~ \#/ ___
~~ V~' '->
~~~ / A newer version of Amazon Linux is available!
~~._. _/
_/ _/ Amazon Linux 2023, GA and supported until 2028-03-15.
_/m/' https://aws.amazon.com/linux/amazon-linux-2023/
[ec2-user@ip-10-0-10-62 ~]$
繋がった!
ハマったところとか
- ツールなどのversion upしていなかったのでソレが原因で躓く場面がちょいちょいあった
- terraformdやろうとするとそこについても調べなくてはならないので、時間がかかってします
次やりたいこと
- privateなRDSを作成してみて今回の方法を利用して接続をしてみる