【问题标题】:How to get latest file-name or file from S3 bucket using event triggered lambda如何使用事件触发的 lambda 从 S3 存储桶获取最新的文件名或文件
【发布时间】:2018-02-01 18:14:03
【问题描述】:

我对 AWS 服务非常陌生,并且只有一周的无服务器架构经验,我的要求是在将新文​​件上传到特定存储桶时触发事件,一旦设置了事件触发器,我的 Lambda 应该得到最新文件的详细信息,例如名称、大小和创建日期。

源每次都将这个文件上传到一个新文件夹中,并用当前日期命名文件夹。

到目前为止,我能够破解如何创建我的 Lambda 函数并监听事件触发器。

这是我的代码。

import boto3
import botocore
import datetime
import logging

def lambda_handler(event, context):
    logging.info('Start function')
    s3 = boto3.resource('s3')
    DATE = datetime.datetime.today().strftime('%Y-%m-%d')
    BUCKET_NAME = 'monkey-banana-dev'
    KEY = '/banana/incoming/daily/{}'.format(DATE)
    logging.info('Getting file from {}'.format(KEY))
    try:
        s3.Bucket(BUCKET_NAME).download_file(KEY, 'name_of_my_file')
    except botocore.exceptions.ClientError as e:
        if e.response['Error']['Code'] == "404":
            print("The object does not exist.")
        else:
            raise

在这里,因为我知道这将是今天的日期,因此我使用datetime 来获取确切的 KEY,但文件名总是不同的。虽然我知道这将是一个带有 .txt 后缀的文本文件,但我无法解决如何从触发器中获取最新上传文件的名称和其他详细信息。

【问题讨论】:

标签: python python-3.x amazon-web-services amazon-s3 aws-lambda


【解决方案1】:

你有一个event object,它包含一个键“记录”,它是一个列表。

您可以过滤 eventName 'ObjectCreated:Put' 的记录,然后按“eventTime”键对列表进行排序以获取最新的事件数据。

def lambda_handler(event, context):
    records = [x for x in event.get('Records', []) if x.get('eventName') == 'ObjectCreated:Put']
    sorted_events = sorted(records, key=lambda e: e.get('eventTime'))
    latest_event = sorted_events[-1] if sorted_events else {}
    info = latest_event.get('s3', {})
    file_key = info.get('object', {}).get('key')
    bucket_name = info.get('bucket', {}).get('name')

【讨论】:

  • 应该不需要排序。每个通知应该只有一个记录。它仅表示为数组,因为这是跨多个 AWS 服务使用的标准化消息格式。
  • 它包含整个文件路径还是只包含文件名?
【解决方案2】:

如前所述,此链接包含信息 - http://docs.aws.amazon.com/lambda/latest/dg/eventsources.html#eventsources-s3-put

您需要做的是利用传递给函数的 event 对象。其中包含链接中提供的详细信息。正如您在链接中的示例中看到的那样,您需要访问 key。这将包含完整路径,包括您提到的日期,因为密钥是完整文件路径。

为了帮助调试,您始终使用 Python 中的 print 函数将事件的值打印到控制台。

【讨论】:

【解决方案3】:

'Key' 将包含整个文件路径。 例子-

import boto3
import os
s3 = boto3.resource('s3')
bucket=s3.Bucket('hcss-heavyjob-raw-tables')
for key in bucket.objects.all():
    if key.key.startswith('heavyjob/EMPMAST'):
           print(key.key)'

输出-

heavyjob/EMPMAST/20190524-165352044.csv

heavyjob/EMPMAST/20190529-153011532.csv

heavyjob/EMPMAST/LOAD00000001.csv

您可以通过在key.key 上使用basename 来获取文件名 或

head,tail = os.path.split(key.key)
print(tail)

【讨论】:

  • 你能否详细说明答案,如果可能的话,举个例子?
猜你喜欢
  • 1970-01-01
  • 2021-12-23
  • 2020-04-01
  • 2017-09-14
  • 2021-12-26
  • 1970-01-01
  • 2019-11-12
  • 2019-06-01
  • 1970-01-01
相关资源
最近更新 更多