寄木細工としてフォーマットされたキネシスファイアホースからs3にデータを取り込みたいです。これまでのところ、EMRを作成することを意味する解決策を見つけましたが、受け取ったjsonをfirehoseから直接寄木細工として保存したり、Lambda関数を使用したりするような安価で高速なものを探しています。
どうもありがとう、ハビ。
良いニュース、この機能は本日リリースされました!
Amazon Kinesis Data Firehoseは、入力データの形式をJSONからApache ParquetまたはApache ORCに変換してから、Amazon S3にデータを保存できます。寄木細工とORCは、スペースを節約し、より高速なクエリを可能にする円柱状のデータ形式です
有効にするには、Firehoseストリームに移動してクリックします Edit。次のスクリーンショットのように、レコード形式の変換セクションが表示されます。
詳細については、ドキュメントを参照してください: https://docs.aws.Amazon.com/firehose/latest/dev/record-format-conversion.html
AWSサポートサービスと数百の異なる実装を扱った後、私が達成したことを説明したいと思います。
最後に、Kinesis Firehoseによって生成されたすべてのファイルを処理し、ペイロードに従ってイベントを分類し、結果をS3のParquetファイルに保存するLambda関数を作成しました。
それをするのはとても簡単ではありません:
まず、必要なすべてのライブラリ(私の場合はPandas、NumPy、Fastparquetなど)を含むPython仮想envを作成する必要があります。結果ファイルとして(すべてのライブラリとmy Lambda関数は重いため、EC2インスタンスを起動する必要があります(無料利用枠に含まれているものを使用しました)。仮想envを作成するには、次の手順に従います。
Lambda_functionを適切に作成します。
import json
import boto3
import datetime as dt
import urllib
import zlib
import s3fs
from fastparquet import write
import pandas as pd
import numpy as np
import time
def _send_to_s3_parquet(df):
s3_fs = s3fs.S3FileSystem()
s3_fs_open = s3_fs.open
# FIXME add something else to the key or it will overwrite the file
key = 'mybeautifullfile.parquet.gzip'
# Include partitions! key1 and key2
write( 'ExampleS3Bucket'+ '/key1=value/key2=othervalue/' + key, df,
compression='GZIP',open_with=s3_fs_open)
def lambda_handler(event, context):
# Get the object from the event and show its content type
bucket = event['Records'][0]['s3']['bucket']['name']
key = urllib.unquote_plus(event['Records'][0]['s3']['object']['key'])
try:
s3 = boto3.client('s3')
response = s3.get_object(Bucket=bucket, Key=key)
data = response['Body'].read()
decoded = data.decode('utf-8')
lines = decoded.split('\n')
# Do anything you like with the dataframe (Here what I do is to classify them
# and write to different folders in S3 according to the values of
# the columns that I want
df = pd.DataFrame(lines)
_send_to_s3_parquet(df)
except Exception as e:
print('Error getting object {} from bucket {}.'.format(key, bucket))
raise e
Lambda関数をlambda.Zipにコピーして、lambda_functionをデプロイします。
たとえば、S3で新しいファイルが作成されるたびに、またはラムダ関数をFirehoseに関連付けることもできます。 (「ラムダ」の制限がFirehoseの制限より低いため、このオプションを選択しませんでした。128Mbまたは15分ごとにファイルを書き込むようにFirehoseを構成できますが、このラムダ関数をFirehoseに関連付けると、ラムダ関数が実行されます私の場合、ラムダ関数が起動されるたびに少なくとも10個のファイルを生成するため、3分または5MBごとに、小さな寄せ木細工のファイルを大量に生成するという問題がありました。
Amazon Kinesis Firehoseはストリーミングレコードを受信し、Amazon S3(またはAmazon RedshiftまたはAmazon Elasticsearch Service)に保存できます。
各レコードは最大1000KBです。
ただし、レコードはテキストファイルに追加され、時間またはサイズに基づいてバッチ処理されます。従来、レコードはJSON形式です。
寄木細工のファイルを送信できませんになります。これは、このファイル形式に準拠しないためです。
Lambdaデータ変換関数をトリガーすることは可能ですが、これは寄木細工のファイルを出力することもできません。
実際、寄木細工のファイルの性質を考えると、それらを作成できるとは考えられません一度に1レコード。列単位のストレージ形式であるため、レコードごとにデータを追加するのではなく、バッチで作成する必要があると思います。
一番下の行:いいえ。