9
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

【Lambda】list_objectsでひっかかったこと

Last updated at Posted at 2022-08-15

やりたいこと

  • list_objectsで指定S3バケット上のキー一覧を取得
    • あるキーが存在するならファイルにデータを追記
    • あるキーが存在しない場合ファイルを新規作成
  • ランタイムはPython3.9

①LambdaからS3バケットにアクセスできない

Error
[ERROR] ClientError: An error occurred (AccessDenied) when calling the ListObjects operation: Access Denied
Traceback (most recent call last):

解決策:LambdaにS3のアクセス権限を付与
1.Lambda関数を管理しているIAMロールの概要ページにアクセス
01_アクセス権限.png
2.「許可を追加」→「ポリシーをアタッチ」を選択
02_アクセス権限.PNG
3.追加したいポリシーを選んで「ポリシーをアタッチ」
※私はこのあと書き込み等も行いたかったため「AmazonS3FullAccess」を追加しましたが、読み込みだけなら「AmazonS3ReadOnlyAccess」で問題ありません。
03_アクセス権限.PNG

②キー名のみの取得ができない

失敗例

Example1
import boto3

s3_client = boto3.client("s3")
bucket = "testbucket"   #バケット名

response = s3_client.list_objects(Bucket=bucket)

print("##keylist")
print(response)
Result1
##keylist
{'ResponseMetadata': {'RequestId': '##########', 'HostId': '##########', 'HTTPStatusCode': 200, 'HTTPHeaders': {'x-amz-id-2': '##########', 'x-amz-request-id': '##########', 'date': 'Fri, 12 Aug 2022 07:46:36 GMT', 'x-amz-bucket-region': 'ap-northeast-1', 'content-type': 'application/xml', 'transfer-encoding': 'chunked', 'server': 'AmazonS3'}, 'RetryAttempts': 0}, 'IsTruncated': False, 'Marker': '', 'Contents': [{'Key': 'apple.txt', 'LastModified': datetime.datetime(2022, 8, 12, 5, 19, 14, tzinfo=tzlocal()), 'ETag': '"##########"', 'Size': 0, 'StorageClass': 'STANDARD', 'Owner': {'DisplayName': '##########', 'ID': '##########'}}, {'Key': 'grape.txt', 'LastModified': datetime.datetime(2022, 8, 12, 5, 19, 14, tzinfo=tzlocal()), 'ETag': '"##########"', 'Size': 0, 'StorageClass': 'STANDARD', 'Owner': {'DisplayName': '##########', 'ID': '##########'}}, {'Key': 'peach.txt', 'LastModified': datetime.datetime(2022, 8, 12, 5, 19, 14, tzinfo=tzlocal()), 'ETag': '"##########"', 'Size': 0, 'StorageClass': 'STANDARD', 'Owner': {'DisplayName': '##########', 'ID': '##########'}}], 'Name': 'testbucket', 'Prefix': '', 'MaxKeys': 1000, 'EncodingType': 'url'}

キー名のみがリストで返されるものだと勘違いしていました。(一部伏字にしています)
解決策

Example2
import boto3

s3_client = boto3.client("s3")
bucket = "testbucket"   #バケット名

response = s3_client.list_objects(Bucket=bucket)
keys = []
for r in response.get("Contents")
    keys.append(r.get("Key"))

print("##keylist")
print(keys)
Result2
##keylist
['apple.txt', 'grape.txt', 'peach.txt']

おまけ

指定S3バケットにあるキーが存在するかどうかで処理を分岐させる例文

Example3
import boto3

def lambda_handler(event, context):
    bucket = BUCKET   #バケット名
    key = KEY   #探したいキー名
    s3_client = boto3.client("s3")

    response = s3_client.list_objects(Bucket=bucket)
    keys = []
    for r in response.get("Contents")
        keys.append(r.get("Key"))

    if key in keys:
        #キーが存在する場合の処理
    else:
        #キーが存在しない場合の処理

    return {"statuscode":200}

参考

9
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?