AWS のタグからのリソース検索でresource-type-filtersを使いたいが渡す文字列がわからないあなたへ

## resourcegroupstaggingapi の get-resources は便利

本格的にAWSのリソースを利用していたら、タグは大体の人はつけていると思います

一方で、そのタグを使用してリソースをフィルターして検索する方法は多くのサービスでサポートしていません。

例えば、EC2は対応していますが、RDSやECSでは対応していません

対応:

https://awscli.amazonaws.com/v2/documentation/api/latest/reference/ec2/describe-instances.html

未対応:

https://awscli.amazonaws.com/v2/documentation/api/latest/reference/rds/describe-db-instances.html

https://awscli.amazonaws.com/v2/documentation/api/latest/reference/ecs/describe-clusters.html

もちろん一度取得した後に、`--query`を使用したり、プログラム側フィルタリングをしても良いですが、やはりサーバーサイド側から1発で拾いたいものです。

せっかくタグをつけているんだから、そこから検索したい、という方のために `resourcegroupstaggingapi` の `get-resources`というAPIで実現が可能です。

このAPIがどんなものかは以下の記事を見てみると良いです

https://qiita.com/nkojima/items/b1e5d5260872596f2430

公式リファレンスはこちら

https://docs.aws.amazon.com/cli/latest/reference/resourcegroupstaggingapi/get-resources.html

## リソース * タグ で絞り込みたい

とはいえ、タグだけで絞りこむには困るケースも多いです。
例えば、顧客ごとの共通のタグをつけていてそれで検索したいが、そうすると大量のリソースが検出されてしまうでしょう

`get-resources`APIはそれにも `resource-type-filters` というパラメータで対応しています。これに

これも以下の記事を見るとイメージができると思います

https://qiita.com/SAITO_Keita/items/9a2d239bf0b9b3b3a79c#resourcegroupstaggingapi%E3%81%8B%E3%82%89%E3%81%9B%E3%82%81%E3%81%A6%E3%81%BF%E3%82%8B

なお、こちらの記事にある通り、このフィルターはすべてのリソースでサポートされているわけではありません

>このコマンドのオプションにresource-type-filtersがあり、このオプションでサポートされているサービスは下記の一覧となります。
>[Services that support the Resource Groups Tagging API](https://docs.aws.amazon.com/ja_jp/resourcegroupstagging/latest/APIReference/supported-services.html)
>[AWS Resource Groupsとタグエディタで使用できるリソースタイプ Amazon CloudWatch](https://docs.aws.amazon.com/ja_jp/ARG/latest/userguide/supported-resources.html#services-cloudwatch)


## resource-type-filtersに渡す値

[AWS Resource Groupsとタグエディタで使用できるリソースタイプ Amazon CloudWatch](https://docs.aws.amazon.com/ja_jp/ARG/latest/userguide/supported-resources.html#services-cloudwatch) から対応リソースは分かりましたが、実際に渡す値は何になるのでしょうか

このAPIを使用するAWSコンソールを見ると リソースタイプのところで、上記リンクに表示しているリソースタイプを選択する形になっています

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/372042/47e09388-18e4-462d-b6d6-2b77c3d653be.png)

一方でAPIから実行するときはこの形式ではエラーになります

```bash
 $ aws resourcegroupstaggingapi get-resources  --resource-type-filters "AWS::RDS::DBInstance"   

An error occurred (InvalidParameterException) when calling the GetResources operation: Unsupported service=AWS in ResourceTypeFilter - AWS::RDS::DBInstance
```


そこで、リファレンスを読むと以下のように書いてあります

https://docs.aws.amazon.com/cli/latest/reference/resourcegroupstaggingapi/get-resources.html

```
--resource-type-filters (list)

Specifies the resource types that you want included in the response. The format of each resource type is service[:resourceType] . For example, specifying a resource type of ec2 returns all Amazon EC2 resources (which includes EC2 instances). Specifying a resource type of ec2:instance returns only EC2 instances.

The string for each service name and resource type is the same as that embedded in a resource’s Amazon Resource Name (ARN). For the list of services whose resources you can use in this parameter, see Services that support the Resource Groups Tagging API .

You can specify multiple resource types by using an array. The array can include up to 100 items. Note that the length constraint requirement applies to each resource type filter. For example, the following string would limit the response to only Amazon EC2 instances, Amazon S3 buckets, or any Audit Manager resource:

ec2:instance,s3:bucket,auditmanager
```

ここから以下の内容がわかります。

-  `service` OR `service:resourceType` で絞り込める
-  service と resourceTypeはARN内に存在している

### 各リソースのARNを知る方法 ①

まずARNの形式についてですが、それはこちらの公式ドキュメントに書かれています。

https://docs.aws.amazon.com/ja_jp/IAM/latest/UserGuide/reference-arns.html#arns-syntax

これによると、`arn:partition:service:region:account-id:resource-type/resource-id` のような形式になるので、partitionの後が `service` で account-idのあとが `resource-type`になります

あとはARNがわかればよいということになるのですが、サービスによっては以外とすぐに見つかりません

先ほどの `AWS::RDS::DBInstance`の場合は簡単です。AWSコンソールからリソースの情報を見ればARNが載っています

例えば、以下のようなARNになるので、指定する値は `rds:db` になります

arn:aws:rds:ap-northeast-1:811463838477:db:hoge-fuga-instance 

一方で、載っていないリソースもあります。例えば `AWS::Backup::BackupPlan` の場合、コンソールで見ても以下のようになり、ARNが表示されません

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/372042/3eeea27b-aef9-4a51-9168-a32b379af0f2.png)

そこでWeb検索をすると、以下のような公式ドキュメントが見つかり、ARNが `arn:aws:backup:region:account-id:backup-plan` であることを知ることができました。

https://docs.aws.amazon.com/ja_jp/aws-backup/latest/devguide/access-control.html

しかし、各サービスごとのドキュメントではARNが書かれている箇所は異なります。ですが、サービスごとに毎回Web検索をするのは面倒です


### 各リソースのARNを知る方法 ②

全てのサービスのARNがまとまったページはないのかと思って探したところ、ありました。

このページは各サービスのActions, resources, condition keys がまとまっているページになります

https://docs.aws.amazon.com/service-authorization/latest/reference/reference_policies_actions-resources-contextkeys.html

このページ内の各サービス名のリンクをクリックすると、それぞれのサービスの情報が記載されています。

画像右のResource TypesをクリックするとそのサービスのResource type並びにARNを知ることができます

https://docs.aws.amazon.com/service-authorization/latest/reference/list_awsbackup.html#awsbackup-resources-for-iam-policies

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/372042/caebbb93-7300-4e22-b78d-8fb833e90ede.png)

## まとめ

- ARN形式における `service:resource-type` が有効な値になります
  - `arn:partition:service:region:account-id:resource-type/resource-id` の `service`と `resource-type`

https://docs.aws.amazon.com/cli/latest/reference/resourcegroupstaggingapi/get-resources.html

https://docs.aws.amazon.com/ja_jp/IAM/latest/UserGuide/reference-arns.html#arns-syntax

- 各リソースのARNは以下のドキュメントから調べられます

https://docs.aws.amazon.com/service-authorization/latest/reference/reference_policies_actions-resources-contextkeys.html


動作としては存在しない`service:resource-type`の組み合わせを指定しても、エラーにはならなかったので、以下のような仕組みになっているんだなと思います

- 内部的には汎用的にARNから、`service` と `resource-type`でフィルタリング
- resource-type-filtersで使用できるか（出力として表示するか）は別にフラグを用意している

個人的にはコンソール側の表示とAPI側で渡す値をそろえてほしいなと思いました。