AWSは全てWeb APIである。それが分かるとAWSもIAMも分かる
「AWSは全てWeb APIである」と気づいたとき、自分のAWSの理解が一気に進んだ記憶があります。これからAWSを学ぶ初学者の方々のために、そこらへんを言語化していこうと思います。
イメージ重視のため正確さを欠く可能性がありますが、その点はご容赦ください。致命的な間違いがあった場合は、コメントで 優しく 教えてください。いいですか、 優しく ですよ。
まずは、AWSがWeb APIであることを見てみよう
例えば、VPCを作ることを考えてみましょう。
- AWSマネジメントコンソール(以下「マネコン」)でVPCのページを開いて、CIDRや名前を指定して[VPCを作成]ボタンをクリックする
- AWS CLIで
aws ec2 create-vpc --cidr-block ...
を実行する
などの方法がありますね。
この背後で何が起こっているのでしょうか?AWS CLIで--debug
オプションを付けると、それを見ることができます。
次のコマンドを実行すると、VPCを作成する際の詳細なログが出力されます。
aws ec2 create-vpc \
--cidr-block "10.10.0.0/16" \
--tag-specifications "ResourceType=vpc,Tags=[{Key=Name,Value=sample-vpc}]" \
--debug
ログを追っていくと、HTTPリクエストをhttps://ec2.ap-northeast-1.amazonaws.com/
にPOSTリクエストを送信していることが分かります。
2025-10-xx xx:35:14,060 - MainThread - botocore.auth - DEBUG - CanonicalRequest:
POST
/
content-type:application/x-www-form-urlencoded; charset=utf-8
host:ec2.ap-northeast-1.amazonaws.com
...
もう少し追うと、レスポンスが返ってきている様子が分かります。(見やすいよう改行を入れています)
レスポンスヘッダーがあり、レスポンスボディはXMLであることが分かりますね。
2025-10-xx xx:35:14,814 - MainThread - botocore.parsers - DEBUG - Response headers: {'x-amzn-RequestId': 'xxxxxxxx', 'Cache-Control': 'no-cache, no-store', 'Strict-Transport-Security': 'max-age=31536000; includeSubDomains', 'Content-Type': 'text/xml;charset=UTF-8', 'Content-Length': '764', ...}
2025-10-xx xx:35:14,814 - MainThread - botocore.parsers - DEBUG - Response body:
b'<?xml version="1.0" encoding="UTF-8"?>\n
<CreateVpcResponse xmlns="http://ec2.amazonaws.com/doc/2016-11-15/">
...
<vpc>
<vpcId>vpc-xxxxxxxxxx</vpcId>
...
<cidrBlock>10.10.0.0/16</cidrBlock>
...
<tagSet>
<item>
<key>Name</key>
<value>sample-vpc</value>
</item>
</tagSet>
...
</vpc>
</CreateVpcResponse>'
つまり aws ec2 create-vpc
コマンドを実行すると、AWSのサーバーにHTTPリクエストを送信し、それを受信したAWSのサーバーがVPCを作成し、レスポンスを返すということです。
マネコンでも同じです。マネコンで[VPCを作成]ボタンをクリックすると、AWSのサーバーにHTTPリクエストを送信し、それを受信したAWSのサーバーがVPCを作成し、レスポンスを返します。
ここまでで、AWSで何かを作成するということは、AWSのWeb APIにリクエストを送信することであると分かりました。
AWSのWeb API仕様
さて、ではもう少し詳しく見てみましょう。先ほど使ったVPC作成のWeb APIは、どんな仕様になっているのでしょうか?
実はAWSのWeb APIは全て仕様が公開されています。EC2のドキュメント一覧を見てみると、[API Reference]というものがあります(歴史的背景から、VPCはEC2に含まれています)。これがWeb APIの仕様書です。
(我々が普段よく読むのは[User Guide]ですね)
これを開き、画面左側の[Actions]からCreateVpc
を探します。これが、先ほどCLIから利用したVPCを作成するWeb APIです。
URLは👇️
EC2にはたくさんのアクション(=Web API)が用意されています。主要なものを紹介しますので、[Actions]の中から探してみてください。
-
CreateVpc
: VPCの作成 -
DeleteVpc
: VPCの削除 -
DescribeVpcs
: VPCを一覧 -
CreateSecurityGroup
: セキュリティグループの作成 -
DeleteSecurityGroup
: セキュリティグループの削除 -
DescribeSecurityGroups
: セキュリティグループを一覧 -
StartInstances
: EC2インスタンスの起動 -
TerminateInstances
: EC2インスタンスの削除 -
DescribeInstances
: EC2インスタンスを一覧
リクエスト・レスポンスのサンプルも紹介されています。
CLIとSDKの正体
AWSがWeb APIだと言うことは、curlコマンドでもVPCが作成できたりします。やろうと思えばできます。しかし、実際には認証のためのリクエストヘッダーを作成したりする必要があります。それに、毎回curlコマンドを使うのはなかなか大変です。
そこで、このWeb APIをラップして使いやすくしたツールがあります。それがCLIとSDKです。
先ほど見た通り、CLIを実行するとAWSのWeb APIへのリクエストが送信されます。加えて、XML形式のレスポンスを、見やすいようにJSONなどに変換してくれます。認証のためのリクエストヘッダーも作成してくれます(デバッグログを詳細に見ると分かります)。
SDKも同様です。AWS SDKはJava・Pythonなど様々な言語のものが提供されています。ちなみにAWS CLIは、Python版のAWS SDKであるbotoというライブラリを内部で使っています。
例えばAWS SDK for Java v2では、以下のコードでVPCが作成できます。内部では先ほどの CreateVpc
のWeb APIにリクエストを送信します。メソッド名などは、CLIとほとんど一緒ですね(キャメルケースとハイフン区切りの違いはありますが)。
Ec2Client ec2Client = Ec2Client.create();
CreateVpcResponse createVpcResponse = ec2Client.createVpc(builder -> builder
.cidrBlock("10.10.0.0/16")
.tagSpecifications(s -> s
.resourceType(ResourceType.VPC)
.tags(t -> t
.key("Name")
.value("sample-vpc")
)
)
);
aws ec2 create-vpc \
--cidr-block "10.10.0.0/16" \
--tag-specifications "ResourceType=vpc,Tags=[{Key=Name,Value=sample-vpc}]"
繰り返しになりますが、CLIとSDKは、AWSのWeb APIのラッパーであることを覚えておいてください。
IAMポリシー
さて、ここからはIAMの説明になります。苦手な方も多いとは思いますが、「AWSはWeb APIである」の原則を理解すると、IAMの理解も進みます。
先ほど説明した通り、AWSのWeb APIには多くの「アクション」があります。
EC2(VPC含む)だとこんなのがありましたね。
-
CreateVpc
: VPCの作成 -
DeleteVpc
: VPCの削除 -
DescribeVpcs
: VPCを一覧 - ...
他にも、よく使うであろうS3にはこんなアクションがあります。
-
CreateBucket
: バケットの作成 -
DeleteBucket
: バケットの削除 -
PutObject
: バケットにオブジェクトをアップロードする -
GetObject
: バケットからオブジェクトをダウンロードする -
DeleteObject
: バケットからオブジェクトを削除する
EC2・ECS・Lambdaなど動くアプリケーションや我々ユーザーが、これらのアクションそれぞれについて許可/拒否されるかどうかの設定がIAMポリシーです。
例えば次のように記述すると、S3バケットsample-bucket
へのオブジェクトのアップロード・ダウンロードが可能になります。
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"s3:PutObject",
"s3:GetObject"
],
"Effect": "Allow",
"Resource": "arn:aws:s3::アカウントID:sample-bucket/*"
}
]
}
IAMポリシーには、我々が作成するものと、AWSが最初から用意してくれているものがあります。例えば、Lambda関数によく使うAWSLambdaBasicExecutionRole
(IAMポリシーなのにRole
という名前なのがややこしい)は、AWSが用意してくれているものです。詳細を見てみると、IAMポリシーのJSONが書かれていることが分かります(CloudWatch Logsでのロググループの作成・ログストリームの作成・ログストリームへのログの出力、というアクションが許可されています)。
IAMロール
作成したIAMポリシーは、IAMロールに紐づけます(1つのIAMロールには複数のIAMポリシーを紐づけ可能)。そしてIAMロールを、EC2インスタンス・ECSタスク・Lambda関数・IAMユーザーなどと紐づけます。
IAMロールを作成する際は、紐づけるIAMポリシーの指定に加えて、信頼関係を設定する必要があります。信頼関係とは、このIAMロールを誰に紐づけられるのか、という設定です。「誰」というのは、
- EC2インスタンス・ECSタスク・Lambda関数などのAWSサービス
- IAMユーザー
などを指します。
例えば、IAMロールをLambda関数に紐づけたい場合は、信頼関係を次のように記述します。"Service": "lambda.amazonaws.com"
の部分がポイントです。
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Service": "lambda.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
まとめ
AWSは全てWeb APIであり、IAMポリシーは1つ1つのWeb APIに対する許可/拒否を設定するものです。
これが腑に落ちたとき、AWSの理解が一気に進みます。
Discussion