Разобрать POSTed файл Excel в Python - PullRequest
1 голос
/ 10 марта 2019

Извините, я нуб, когда дело доходит до сети.Я пытаюсь отправить файл Excel, используя шлюз API, и обработать его для записи в S3, используя лямбду в python.Я отправляю файл как «application / octet-stream» и анализирую после того, как получаю объект события следующим образом:

import io
import cgi
import pandas as pd
import xlrd

def read_file(event):
    c_type, c_data = parse_header(event['headers']['Content-Type'])
    encoded_file = event['body'].encode('utf-8')
    c_data['boundary'] = bytes(c_data['boundary'], "utf-8")
    parsed_body = cgi.parse_multipart(io.BytesIO(encoded_file), c_data)
    return(parsed_body)

это, по сути, должно дать мне поток io.BytesIO, который я должен быть в состоянии прочитатькак

df = pd.ExcelFile(list(parsed_body.values())[0][0], engine = 'xlrd')

функция read_file() будет вызываться lambda_handler как

def lambda_handler(event, context):
    p_body = read_file(event)
    df = pd.ExcelFile(list(parsed_body.values())[0][0], engine = 'xlrd')
    # Some post processing to the df

Я потерпел неудачу в точке, когда панды не могут прочитать это parsed_body.Я также попробовал библиотеку multipart, что тоже не дало мне результата.

Если кто-нибудь может показать мне метод для анализа тела события и дать результат, я был бы благодарен.

Я получаю ошибку

File "<ipython-input-264-dfd56a631cc4>", line 1, in <module>
cgi.parse_multipart(event_bytes, c_data)

File    

"/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/cgi.py",line 261, in parse_multipart
    line = fp.readline()

AttributeError: 'bytes' object has no attribute 'readline'

1 Ответ

0 голосов
/ 11 марта 2019

Я наконец нашел ответ, использую кодировку base64 из cURL и передаю данные в API следующим образом

curl -H 'Content-Type:application/octet-stream' --data-binary '{"file": "'"$(base64 /Path/to/file)"'"}' 'https://someAPI.com/some/path?param1=value1\&param2=value2'

, с этим шлюз API получает json в теле со структурой {"file": "Base64 encoded string here"}

Как только у вас будет это тело, сначала получите строку в кодировке base64 как

eventBody = base64.b64decode(json.loads(event['body'])['file'])

Теперь создайте пустой поток и запишите эту декодированную строку в поток.Также установите позицию поиска на 0

toread=io.BytesIO()
toread.write(eventBody)
toread.seek(0)

Наконец, просто передайте этот поток пандам

df=pd.read_excel(toread, sheet_name=sn)

И это сработало.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...