このハンズオンについて
- このハンズオンでは、Directory Serviceで作成したディレクトリのユーザでManagement Consoleにログインするまでの作業を実施します。
- 今回のハンズオンでは、AD-Connectorは対象外とします。
- 一部の操作はManagement Consoleで実施します。
- Macをお使いの方は、Windows Serverでリモートデスクトップ接続が出来るアプリをご用意ください。
- Windows Serverをドメインに参加させるため、SSMを使用します。SSMが利用可能なリージョンを利用してください。この手順ではオレゴンを利用します。
前提条件
バージョン確認
このハンズオンは以下のバージョンで動作確認を行いました。
aws --version
aws-cli/1.9.5 Python/2.7.10 Linux/4.1.10-17.31.amzn1.x86_64 botocore/1.3.5
必要な権限
作業にあたっては、以下の権限を有したIAMユーザもしくはIAMロールを利用してください。
- EC2に対するフルコントロール権限
- Directory Serviceに関するフルコントロール権限
- IAMに関するフルコントロール権限
- SSMに関するフルコントロール権限
0. 準備
リージョンを指定
export AWS_DEFAULT_REGION='us-west-2'
資格情報を確認
aws configure list
Name Value Type Location
---- ----- ---- --------
profile <not set> None None
access_key ****************PZ4A iam-role
secret_key ****************AZ55 iam-role
region us-west-2 env AWS_DEFAULT_REGION
1. VPCの作成
VPCのCIDRを指定
CIDR_BLOCK='10.0.0.0/16'
パラメータを確認
cat << ETX
VPC_CIDR_BLOCK: "${CIDR_BLOCK}"
ETX
VPC_CIDR_BLOCK: "10.0.0.0/16"
VPCを作成
VPC_ID=`aws ec2 create-vpc --cidr-block ${CIDR_BLOCK} | jq -r .[].VpcId`
echo ${VPC_ID}
vpc-********
Tagを付与
aws ec2 create-tags --resources ${VPC_ID} --tags Key=Name,Value=jawsug-cli
(返値無し)
作成したVPCの確認
aws ec2 describe-vpcs --vpc-ids ${VPC_ID}
{
"Vpcs": [
{
"VpcId": "vpc-********",
"InstanceTenancy": "default",
"Tags": [
{
"Value": "jawsug-cli",
"Key": "Name"
}
],
"State": "available",
"DhcpOptionsId": "dopt-********",
"CidrBlock": "10.0.0.0/16",
"IsDefault": false
}
]
}
2. Internet Gatewayの作成、アタッチ
インターネットゲートウェイの作成
IGW_ID=`aws ec2 create-internet-gateway | jq -r .[].InternetGatewayId`
echo ${IGW_ID}
igw-********
Tagを付与
aws ec2 create-tags --resources ${IGW_ID} --tags Key=Name,Value=jawsug-cli
(返値無し)
作成したInternet Gatewayを確認
aws ec2 describe-internet-gateways --internet-gateway-ids ${IGW_ID}
{
"InternetGateways": [
{
"Tags": [
{
"Value": "jawsug-cli",
"Key": "Name"
}
],
"InternetGatewayId": "igw-********",
"Attachments": []
}
]
}
パラメータを確認
cat << ETX
VPC_ID: "${VPC_ID}"
InternetGateat_ID: "${IGW_ID}"
ETX
VPC_ID: "vpc-********"
InternetGateat_ID: "igw-********"
VPCにインターネットゲートウェイをアタッチ
aws ec2 attach-internet-gateway --internet-gateway-id ${IGW_ID} --vpc-id ${VPC_ID}
(返値なし)
アタッチした結果を確認
aws ec2 describe-internet-gateways --internet-gateway-ids ${IGW_ID}
{
"InternetGateways": [
{
"Tags": [
{
"Value": "jawsug-cli",
"Key": "Name"
}
],
"InternetGatewayId": "igw-********",
"Attachments": [
{
"State": "available",
"VpcId": "vpc-********"
}
]
}
]
}
3. Subnetの作成
Simple-ADのディレクトリは2重化されるため、異なるAvailability-Zoneのサブネットを作成します。
(オレゴンの場合、a, b, cの3つから選択可能です。)
サブネットを指定
CIDR_BLOCK_SUBNET_A='10.0.0.0/24'
CIDR_BLOCK_SUBNET_C='10.0.1.0/24'
パラメータを確認
cat << ETX
VPC_ID: "${VPC_ID}"
Subnet_CIDR_BLOCK_on_${AWS_DEFAULT_REGION}a: "${CIDR_BLOCK_SUBNET_A}"
Subnet_CIDR_BLOCK_on_${AWS_DEFAULT_REGION}c: "${CIDR_BLOCK_SUBNET_C}"
ETX
VPC_ID: "vpc-********"
Subnet_CIDR_BLOCK_on_us-west-2a: "10.0.0.0/24"
Subnet_CIDR_BLOCK_on_us-west-2c: "10.0.1.0/24"
サブネットを作成
SUBNET_A_ID=`aws ec2 create-subnet --vpc-id ${VPC_ID} --cidr-block ${CIDR_BLOCK_SUBNET_A} --availability-zone ${AWS_DEFAULT_REGION}a | jq -r .[].SubnetId`
echo ${SUBNET_A_ID}
SUBNET_C_ID=`aws ec2 create-subnet --vpc-id ${VPC_ID} --cidr-block ${CIDR_BLOCK_SUBNET_C} --availability-zone ${AWS_DEFAULT_REGION}c | jq -r .[].SubnetId`
echo ${SUBNET_C_ID}
作成したサブネットを確認
aws ec2 describe-subnets --subnet-ids ${SUBNET_A_ID} ${SUBNET_C_ID}
{
"Subnets": [
{
"VpcId": "vpc-********",
"CidrBlock": "10.0.0.0/24",
"MapPublicIpOnLaunch": false,
"DefaultForAz": false,
"State": "available",
"AvailabilityZone": "us-west-2a",
"SubnetId": "subnet-********",
"AvailableIpAddressCount": 251
},
{
"VpcId": "vpc-********",
"CidrBlock": "10.0.1.0/24",
"MapPublicIpOnLaunch": false,
"DefaultForAz": false,
"State": "available",
"AvailabilityZone": "us-west-2c",
"SubnetId": "subnet-********",
"AvailableIpAddressCount": 251
}
]
}
4. Route Tableの編集
作成したVPCのデフォルトのルートテーブルIDを確認
ROUTE_TABLE_ID=`aws ec2 describe-route-tables --query RouteTables[?VpcId==\'${VPC_ID}\'].[RouteTableId] | jq -r ".[] | .[]"`
echo ${ROUTE_TABLE_ID}
パラメータを確認
cat << ETX
RouteTable_ID: "${ROUTE_TABLE_ID}"
InternetGateat_ID: "${IGW_ID}"
ETX
RouteTable_ID: "rtb-********"
InternetGateat_ID: "igw-********"
デフォルトのルートテーブルにデフォルトルートを追加
aws ec2 create-route --route-table-id ${ROUTE_TABLE_ID} --destination-cidr-block '0.0.0.0/0' --gateway-id ${IGW_ID}
{
"Return": true
}
ルートテーブルに追加したルートを確認
aws ec2 describe-route-tables --query RouteTables[?VpcId==\'${VPC_ID}\']
[
{
"Associations": [
{
"RouteTableAssociationId": "rtbassoc-********",
"Main": true,
"RouteTableId": "rtb-********"
}
],
"RouteTableId": "rtb-********",
"VpcId": "vpc-********",
"PropagatingVgws": [],
"Tags": [],
"Routes": [
{
"GatewayId": "local",
"DestinationCidrBlock": "10.0.0.0/16",
"State": "active",
"Origin": "CreateRouteTable"
},
{
"GatewayId": "igw-********",
"DestinationCidrBlock": "0.0.0.0/0",
"State": "active",
"Origin": "CreateRoute"
}
]
}
]
5. Sucurity Groupの作成、設定
Security Groupの名前を設定
SG_GROUP_NAME='WindowsServer'
SG_DESCRIPTION='RemoteDesktop'
パラメータの確認
cat << ETX
SG_GROUP_NAME: ${SG_GROUP_NAME}
SG_DESCRIPTION: ${SG_DESCRIPTION}
ETX
SG_GROUP_NAME: WindowsServer
SG_DESCRIPTION: RemoteDesktop
ユーザ作成用のEC2インスタンスに設定するSecurity Groupを作成
aws ec2 create-security-group --group-name ${SG_GROUP_NAME} --description ${SG_DESCRIPTION} --vpc-id ${VPC_ID}
{
"GroupId": "sg-********"
}
SG_ID=`aws ec2 describe-security-groups --filter Name=group-name,Values="${SG_GROUP_NAME}" | jq -r " .[] | .[] | .GroupId"`
echo ${SG_ID}
sg-********
作成したSecurity Groupを確認
(アウトバウンドの通信のみ全て許可する設定のみ、がデフォルト)
aws ec2 describe-security-groups --group-ids ${SG_ID}
{
"SecurityGroups": [
{
"IpPermissionsEgress": [
{
"IpProtocol": "-1",
"IpRanges": [
{
"CidrIp": "0.0.0.0/0"
}
],
"UserIdGroupPairs": [],
"PrefixListIds": []
}
],
"Description": "RemoteDesktop",
"IpPermissions": [],
"GroupName": "WindowsServer",
"VpcId": "vpc-********",
"OwnerId": "************",
"GroupId": "sg-********"
}
]
}
インバウンドのルールを追加
(リモートデスクトップ接続を許可)
接続元のIPアドレスを制限したい場合には、確認君などでIPアドレスを確認してください。
http://www.ugtop.com/spill.shtml
aws ec2 authorize-security-group-ingress --group-id ${SG_ID} --protocol 'tcp' --port 3389 --cidr 0.0.0.0/0
追加されたルールを確認
aws ec2 describe-security-groups --group-ids ${SG_ID}
{
"SecurityGroups": [
{
"IpPermissionsEgress": [
{
"IpProtocol": "-1",
"IpRanges": [
{
"CidrIp": "0.0.0.0/0"
}
],
"UserIdGroupPairs": [],
"PrefixListIds": []
}
],
"Description": "RemoteDesktop",
"IpPermissions": [
{
"PrefixListIds": [],
"FromPort": 3389,
"IpRanges": [
{
"CidrIp": "0.0.0.0/0"
}
],
"ToPort": 3389,
"IpProtocol": "tcp",
"UserIdGroupPairs": []
}
],
"GroupName": "WindowsServer",
"VpcId": "vpc-********",
"OwnerId": "************",
"GroupId": "sg-********"
}
]
}
6. Key Pairの作成
KeyPairの名前および秘密鍵のファイル名を設定
KEY_PAIR_NAME='UserManagementServer'
KEY_MATERIAL_FILE='key.pem'
同名のKey Pairおよび秘密鍵ファイルが存在しないことを確認
aws ec2 describe-key-pairs --key-names ${KEY_PAIR_NAME}
A client error (InvalidKeyPair.NotFound) occurred when calling the DescribeKeyPairs operation: The key pair 'UserManagementServer' does not exist
ls -al ~/.ssh | grep ${KEY_MATERIAL_FILE}
(返値無し)
パラメータの確認
cat << ETX
KEY_PAIR_NAME: ${KEY_PAIR_NAME}
KEY_MATERIAL_FILE: ${KEY_MATERIAL_FILE}
ETX
KEY_PAIR_NAME: UserManagementServer
KEY_MATERIAL_FILE: key.pem
KeyPairの作成
aws ec2 create-key-pair --key-name ${KEY_PAIR_NAME} | jq -r .KeyMaterial > ~/.ssh/${KEY_MATERIAL_FILE}
Key Pairが作成されたことを確認
aws ec2 describe-key-pairs --key-names ${KEY_PAIR_NAME}
{
"KeyPairs": [
{
"KeyName": "UserManagementServer",
"KeyFingerprint": "**:**:**:**:**:**:**:**:**:**:**:**:**:**:**:**:**:**:**:**"
}
]
}
7. インスタンスプロファイルの作成
同名のロールがないことを確認
SSM_ROLE_NAME='ssm-role'
aws iam get-role --role-name ${SSM_ROLE_NAME}
A client error (NoSuchEntity) occurred when calling the GetRole operation: The role with name ssm-role cannot be found.
信頼関係の定義
TRUST_POLICY_DOMAIN_JOIN_FILE='Trust-Policy-domain-join.json'
cat << EOF > ${TRUST_POLICY_DOMAIN_JOIN_FILE}
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "",
"Effect": "Allow",
"Principal": {
"Service": "ec2.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
EOF
JSONファイルを検証
jsonlint -q ${TRUST_POLICY_DOMAIN_JOIN_FILE}
IAMロールの作成
aws iam create-role --role-name ${SSM_ROLE_NAME} --assume-role-policy-document file://${TRUST_POLICY_DOMAIN_JOIN_FILE}
{
"Role": {
"AssumeRolePolicyDocument": {
"Version": "2012-10-17",
"Statement": [
{
"Action": "sts:AssumeRole",
"Principal": {
"Service": "ec2.amazonaws.com"
},
"Effect": "Allow",
"Sid": ""
}
]
},
"RoleId": "A********************",
"CreateDate": "2015-10-25T14:30:52.049Z",
"RoleName": "ssm-role",
"Path": "/",
"Arn": "arn:aws:iam::************:role/ssm-role"
}
}
IAMロールにManaged Policyをアタッチ
SSM_POLICY_ARN='arn:aws:iam::aws:policy/AmazonSSMFullAccess'
aws iam attach-role-policy --role-name ${SSM_ROLE_NAME} --policy-arn ${SSM_POLICY_ARN}
(返値無し)
IAM Roleにポリシーがアタッチされたことを確認
aws iam list-attached-role-policies --role-name ${SSM_ROLE_NAME}
{
"AttachedPolicies": [
{
"PolicyName": "AmazonSSMFullAccess",
"PolicyArn": "arn:aws:iam::aws:policy/AmazonSSMFullAccess"
}
]
}
同名のインスタンスプロファイルが存在しないことを確認
aws iam get-instance-profile --instance-profile-name ${SSM_ROLE_NAME}
A client error (NoSuchEntity) occurred when calling the GetInstanceProfile operation: Instance Profile ssm-role cannot be found.
インスタンスプロファイルを作成
aws iam create-instance-profile --instance-profile-name ${SSM_ROLE_NAME}
{
"InstanceProfile": {
"InstanceProfileId": "A********************",
"Roles": [],
"CreateDate": "2015-10-25T14:42:25.839Z",
"InstanceProfileName": "ssm-role",
"Path": "/",
"Arn": "arn:aws:iam::************:instance-profile/ssm-role"
}
}
インスタンスプロファイルが作成されたことを確認
aws iam get-instance-profile --instance-profile-name ${SSM_ROLE_NAME}
{
"InstanceProfile": {
"InstanceProfileId": "A********************",
"Roles": [],
"CreateDate": "2015-10-25T14:42:25Z",
"InstanceProfileName": "ssm-role",
"Path": "/",
"Arn": "arn:aws:iam::************:instance-profile/ssm-role"
}
}
インスタンスプロファイルにIAM Roleを追加
aws iam add-role-to-instance-profile --instance-profile-name ${SSM_ROLE_NAME} --role-name ${SSM_ROLE_NAME}
(返値無し)
インスタンスプロファイルにIAM Roleが追加されたことを確認
aws iam get-instance-profile --instance-profile-name ${SSM_ROLE_NAME}
{
"InstanceProfile": {
"InstanceProfileId": "A********************",
"Roles": [
{
"AssumeRolePolicyDocument": {
"Version": "2012-10-17",
"Statement": [
{
"Action": "sts:AssumeRole",
"Principal": {
"Service": "ec2.amazonaws.com"
},
"Effect": "Allow",
"Sid": ""
}
]
},
"RoleId": "A********************",
"CreateDate": "2015-10-25T14:30:52Z",
"RoleName": "ssm-role",
"Path": "/",
"Arn": "arn:aws:iam::************:role/ssm-role"
}
],
"CreateDate": "2015-10-25T14:42:25Z",
"InstanceProfileName": "ssm-role",
"Path": "/",
"Arn": "arn:aws:iam::************:instance-profile/ssm-role"
}
}
8. EC2インスタンスの作成
Windows Serverの最新AMIのImage IDを確認
Windows Server 2012 R2を利用したかったのですが、なぜかユーザの作成に失敗するため、Windows Server 2012を利用します。
(フォーラムにいくつか不具合報告あり)
Adding a User to a Simple AD instance generates error.
Windows Server 2012のAMIのうち、作成日が最新のAMIを利用します。
AMI_ID=`aws ec2 describe-images --owners amazon --filters Name=description,Values='Microsoft Windows Server 2012 RTM 64-bit Locale English Base AMI provided by Amazon' | jq -r ".[] | sort_by(.CreationDate) | .[] | .ImageId" | awk 'END {print}'` && echo ${AMI_ID}
パラメータを確認
AWS_ID=$( \
aws iam get-user \
--query 'User.Arn' \
--output text | \
sed 's/^.*:://' | \
sed 's/:.*$//' \
) \
&& echo ${AWS_ID}
************
cat << ETX
AWS_ID: ${AWS_ID}
AMI_ID: "${AMI_ID}"
KEY_PAIR_NAME: ${KEY_PAIR_NAME}
SecurityGroup_ID: "${SG_ID}"
Subnet_ID: "${SUBNET_A_ID}"
Instance Profile ARN: arn:aws:iam::${AWS_ID}:instance-profile/${SSM_ROLE_NAME}
ETX
AWS_ID: ************
AMI_ID: "ami-********"
KEY_PAIR_NAME: UserManagementServer
SecurityGroup_ID: "sg-********"
Subnet_ID: "subnet-********"
Instance Profile ARN: arn:aws:iam::************:instance-profile/ssm-role
EC2インスタンスを作成
ここでは無料枠の対象であるt2.microを利用していますが、動きがかなりもっさりです。
イライラしたくない方はインスタンスタイプを変更してください。
INSTANCE_ID=`aws ec2 run-instances --image-id ${AMI_ID} --key-name ${KEY_PAIR_NAME} --security-group-ids ${SG_ID} --instance-type 't2.micro' --subnet-id ${SUBNET_A_ID} --associate-public-ip-address --iam-instance-profile Arn=arn:aws:iam::${AWS_ID}:instance-profile/${SSM_ROLE_NAME} | jq -r ".Instances | .[].InstanceId"` && echo ${INSTANCE_ID}
EC2インスタンスが作成されたことを確認
aws ec2 describe-instances --instance-ids ${INSTANCE_ID}
{
"Reservations": [
{
"OwnerId": "************",
"ReservationId": "r-********",
"Groups": [],
"Instances": [
{
"Monitoring": {
"State": "disabled"
},
"PublicDnsName": "",
"Platform": "windows",
"State": {
"Code": 16,
"Name": "running"
},
"EbsOptimized": false,
"LaunchTime": "2015-10-11T06:45:58.000Z",
"PublicIpAddress": "**.**.***.***",
"PrivateIpAddress": "10.0.0.162",
"ProductCodes": [],
"VpcId": "vpc-********",
"StateTransitionReason": "",
"InstanceId": "i-********",
"ImageId": "ami-********",
"PrivateDnsName": "ip-10-0-0-162.us-west-2.compute.internal",
"KeyName": "UserManagementServer",
"SecurityGroups": [
{
"GroupName": "WindowsServer",
"GroupId": "sg-********"
}
],
"ClientToken": "",
"SubnetId": "subnet-********",
"InstanceType": "t2.medium",
"NetworkInterfaces": [
{
"Status": "in-use",
"MacAddress": "**:**:**:**:**:**",
"SourceDestCheck": true,
"VpcId": "vpc-********",
"Description": "",
"Association": {
"PublicIp": "**.**.***.***",
"PublicDnsName": "",
"IpOwnerId": "amazon"
},
"NetworkInterfaceId": "eni-********",
"PrivateIpAddresses": [
{
"Association": {
"PublicIp": "**.**.***.***",
"PublicDnsName": "",
"IpOwnerId": "amazon"
},
"Primary": true,
"PrivateIpAddress": "10.0.0.162"
}
],
"Attachment": {
"Status": "attached",
"DeviceIndex": 0,
"DeleteOnTermination": true,
"AttachmentId": "eni-attach-********",
"AttachTime": "2015-10-11T06:45:58.000Z"
},
"Groups": [
{
"GroupName": "WindowsServer",
"GroupId": "sg-********"
}
],
"SubnetId": "subnet-********",
"OwnerId": "************",
"PrivateIpAddress": "10.0.0.162"
}
],
"SourceDestCheck": true,
"Placement": {
"Tenancy": "default",
"GroupName": "",
"AvailabilityZone": "us-west-2a"
},
"Hypervisor": "xen",
"BlockDeviceMappings": [
{
"DeviceName": "/dev/sda1",
"Ebs": {
"Status": "attached",
"DeleteOnTermination": true,
"VolumeId": "vol-********",
"AttachTime": "2015-10-11T06:46:02.000Z"
}
}
],
"Architecture": "x86_64",
"RootDeviceType": "ebs",
"RootDeviceName": "/dev/sda1",
"VirtualizationType": "hvm",
"AmiLaunchIndex": 0
}
]
}
]
}
9. Windowsパスワードの確認、Public IPの確認
パラメータを確認
cat << ETX
Instance_ID: "${INSTANCE_ID}"
KeyMaterialFile: "${KEY_MATERIAL_FILE}"
ETX
Instance_ID: "i-********"
KeyMaterialFile: "key.pem"
パスワードを復号化
EC2インスタンスの作成からパスワードが表示されるまでに数分の時間がかかります。
しかし、SSMによるドメイン参加が成功した場合には不要なため、次の手順に進みます。
aws ec2 get-password-data --instance-id ${INSTANCE_ID} --priv-launch-key ~/.ssh/${KEY_MATERIAL_FILE}
{
"InstanceId": "i-********",
"Timestamp": "2015-10-11T06:48:35.000Z",
"PasswordData": "**********"
}
パブリックIPを確認
PUBLIC_IP_ADDRESS=`aws ec2 describe-instances --instance-ids ${INSTANCE_ID} | jq -r ".[] | .[].Instances | .[].PublicIpAddress"` && echo ${PUBLIC_IP_ADDRESS}
以上です。