Dataframe을 csv에 s3 Python에 직접 저장
새 CSV 파일에 업로드하려는 pandas DataFrame이 있습니다. 문제는 파일을 s3로 전송하기 전에 로컬에 저장하고 싶지 않다는 것입니다. 데이터 프레임을 s3에 직접 쓰는 to_csv와 같은 방법이 있습니까? boto3를 사용하고 있습니다.
지금까지 내가 가진 것은 다음과 같습니다.
import boto3
s3 = boto3.client('s3', aws_access_key_id='key', aws_secret_access_key='secret_key')
read_file = s3.get_object(Bucket, Key)
df = pd.read_csv(read_file['Body'])
# Make alterations to DataFrame
# Then export DataFrame to CSV through direct transfer to s3
당신이 사용할 수있는:
from io import StringIO # python3; python2: BytesIO
import boto3
csv_buffer = StringIO()
df.to_csv(csv_buffer)
s3_resource = boto3.resource('s3')
s3_resource.Object(bucket, 'df.csv').put(Body=csv_buffer.getvalue())
나는 s3를 (거의) 로컬 파일 시스템처럼 사용할 수있는 s3fs 를 좋아한다.
다음과 같이 할 수 있습니다.
import s3fs
bytes_to_write = df.to_csv(None).encode()
fs = s3fs.S3FileSystem(key=key, secret=secret)
with fs.open('s3://bucket/path/to/file.csv', 'wb') as f:
f.write(bytes_to_write)
s3fs
만 지원 rb
하고 wb
나는이했던 이유 파일, 열기의 모드 bytes_to_write
물건을.
이것은 최신 답변입니다.
import s3fs
s3 = s3fs.S3FileSystem(anon=False)
# Use 'w' for py3, 'wb' for py2
with s3.open('<bucket-name>/<filename>.csv','w') as f:
df.to_csv(f)
StringIO의 문제는 그것이 당신의 기억을 앗아 갈 것이라는 것입니다. 이 방법을 사용하면 파일을 문자열로 변환하지 않고 s3로 스트리밍 한 다음 s3에 기록합니다. 팬더 데이터 프레임과 문자열 사본을 메모리에 보관하는 것은 매우 비효율적 인 것 같습니다.
ec2 인스턴트로 작업하는 경우 s3에 쓸 수 있도록 IAM 역할을 부여 할 수 있으므로 자격 증명을 직접 전달할 필요가 없습니다. 그러나 S3FileSystem()
함수에 자격 증명을 전달하여 버킷에 연결할 수도 있습니다 . 문서 참조 : https://s3fs.readthedocs.io/en/latest/
S3 경로를 직접 사용할 수 있습니다. Pandas 0.24.1을 사용 하고 있습니다.
In [1]: import pandas as pd
In [2]: df = pd.DataFrame( [ [1, 1, 1], [2, 2, 2] ], columns=['a', 'b', 'c'])
In [3]: df
Out[3]:
a b c
0 1 1 1
1 2 2 2
In [4]: df.to_csv('s3://experimental/playground/temp_csv/dummy.csv', index=False)
In [5]: pd.__version__
Out[5]: '0.24.1'
In [6]: new_df = pd.read_csv('s3://experimental/playground/temp_csv/dummy.csv')
In [7]: new_df
Out[7]:
a b c
0 1 1 1
1 2 2 2
S3 파일 처리
pandas는 이제 S3 연결을 처리하기 위해 s3fs를 사용합니다. 이것은 어떤 코드도 깨지 않아야합니다. 그러나 s3fs는 필수 종속성이 아니므로 이전 버전의 pandas에있는 boto처럼 별도로 설치해야합니다. GH11915 .
None
첫 번째 인수로 전달 to_csv()
하면 데이터가 문자열로 반환됩니다. 여기에서 한 번에 S3에 쉽게 업로드 할 수 있습니다.
StringIO
객체를 에 전달할 수도 to_csv()
있지만 문자열을 사용하는 것이 더 쉽습니다.
import boto3
s3_client = boto3.client('s3',aws_access_key_id="AccessKey",aws_secret_access_key="Secretkey")
head_response = s3_client.head_object(Bucket='YourBucket',Key='YourPath')
if head_response['HTTPStatusCode'] == 200:
Your operation if file exsits
버킷 s3에서 두 개의 열이있는 csv와 pandas 데이터 프레임에 넣은 csv 파일의 내용을 읽었습니다.
예:
config.json
{
"credential": {
"access_key":"xxxxxx",
"secret_key":"xxxxxx"
}
,
"s3":{
"bucket":"mybucket",
"key":"csv/user.csv"
}
}
cls_config.json
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import os
import json
class cls_config(object):
def __init__(self,filename):
self.filename = filename
def getConfig(self):
fileName = os.path.join(os.path.dirname(__file__), self.filename)
with open(fileName) as f:
config = json.load(f)
return config
cls_pandas.py
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import pandas as pd
import io
class cls_pandas(object):
def __init__(self):
pass
def read(self,stream):
df = pd.read_csv(io.StringIO(stream), sep = ",")
return df
cls_s3.py
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import boto3
import json
class cls_s3(object):
def __init__(self,access_key,secret_key):
self.s3 = boto3.client('s3', aws_access_key_id=access_key, aws_secret_access_key=secret_key)
def getObject(self,bucket,key):
read_file = self.s3.get_object(Bucket=bucket, Key=key)
body = read_file['Body'].read().decode('utf-8')
return body
test.py
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from cls_config import *
from cls_s3 import *
from cls_pandas import *
class test(object):
def __init__(self):
self.conf = cls_config('config.json')
def process(self):
conf = self.conf.getConfig()
bucket = conf['s3']['bucket']
key = conf['s3']['key']
access_key = conf['credential']['access_key']
secret_key = conf['credential']['secret_key']
s3 = cls_s3(access_key,secret_key)
ob = s3.getObject(bucket,key)
pa = cls_pandas()
df = pa.read(ob)
print df
if __name__ == '__main__':
test = test()
test.process()
참고 URL : https://stackoverflow.com/questions/38154040/save-dataframe-to-csv-directly-to-s3-python
'Nice programing' 카테고리의 다른 글
자체 작업 버튼을 사용하여 스낵바를 닫는 방법은 무엇입니까? (0) | 2020.10.13 |
---|---|
ASP.NET MVC / WebAPI 응용 프로그램에서 HTTP OPTIONS 동사를 지원하는 방법 (0) | 2020.10.13 |
include ()에서 네임 스페이스를 사용할 때 app_name에 대한 ImpropyConfiguredError (0) | 2020.10.13 |
HTTP 범위 헤더 (0) | 2020.10.13 |
인라인 변수로 여러 줄 Python 문자열을 어떻게 생성합니까? (0) | 2020.10.13 |