Расшифровка ответов разных кодировок

1

Я пытаюсь получить данные о тике из всех списков в S & P 500 из программирования python для учебных пособий по финансам (ссылка). К сожалению, при запуске моего кода появляется следующая ошибка:

requests.exceptions.ContentDecodingError: ('Received response with 
content-encoding: gzip, but failed to decode it.', error('Error -3 while
decompressing data: incorrect data check',))

Я предполагаю, что эта проблема исходит из разных кодировок для разных запасов. Как я могу изменить свой код (показано ниже), чтобы разрешить декодирование gzip?

import bs4 as bs
import pickle
import requests
import datetime as dt
import os
import pandas as pd
import pandas_datareader.data as web

def save_sp500_tickers():
response = requests.get('https://en.wikipedia.org/wiki/List_of_S%26P_500_companies')
#retrieve src code from url

soup = bs.BeautifulSoup(response.text, 'lxml')
#convert src code into bs4 format

table = soup.find('table', {'class':'wikitable sortable'})
#search the new soup object for the table tag of class wikitable sortable

tickers = []
#create a target array

for row in table.findAll('tr')[1:]:
#for each row in table find all rows sliced from index1
    ticker = row.findAll('td')[0].text
    #find all tableDefinitions and convert to text
    tickers.append(ticker)
    #add ticker to our tickers array
with open("sp500tickers.pickle","wb") as f:
    pickle.dump(tickers, f)

print(tickers)

return tickers

def getDataFromYahoo(reload_sp500 = False):
if(reload_sp500):
    tickers = save_sp500_tickers()
else:
    with open("sp500tickers.pickle","rb") as f:
        tickers = pickle.load(f)

if not os.path.exists('stock_dfs'):
    os.makedirs('stock_dfs')

start = dt.datetime(2010,1,1)
end = dt.datetime(2018,7,26)

for ticker in tickers:
    print(ticker)
    if not os.path.exists('stocks_dfs/{}.csv'.format(ticker)):
        df = web.DataReader(ticker, 'yahoo', start, end)
    else:
        print('Already have {}'.format(ticker))

getDataFromYahoo()

Traceback (последний последний вызов):

  File "C:\Users\dan gilmore\Desktop\EclipseOxygen64WCSPlugin\cherryPY\S7P\index.py", line 55, in <module>
    getDataFromYahoo()
  File "C:\Users\dan gilmore\Desktop\EclipseOxygen64WCSPlugin\cherryPY\S7P\index.py", line 51, in getDataFromYahoo
    df = web.DataReader(ticker, 'yahoo', start, end)
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pandas_datareader\data.py", line 311, in DataReader
    session=session).read()
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pandas_datareader\base.py", line 210, in read
    params=self._get_params(self.symbols))
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pandas_datareader\yahoo\daily.py", line 129, in _read_one_data
    resp = self._get_response(url, params=params)
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\pandas_datareader\base.py", line 132, in _get_response
    headers=headers)
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\requests\sessions.py", line 525, in get
    return self.request('GET', url, **kwargs)
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\requests\sessions.py", line 512, in request
    resp = self.send(prep, **send_kwargs)
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\requests\sessions.py", line 662, in send
    r.content
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\requests\models.py", line 827, in content
    self._content = b''.join(self.iter_content(CONTENT_CHUNK_SIZE)) or b''
  File "C:\Users\dan gilmore\AppData\Local\Programs\Python\Python36-32\lib\site-packages\requests\models.py", line 754, in generate
    raise ContentDecodingError(e)
requests.exceptions.ContentDecodingError: ('Received response with content-encoding: gzip, but failed to decode it.', error('Error -3 while decompressing data: incorrect data check',))
  • 0
    Показать полную трассировку.
  • 0
    content-encoding - это отдельная вещь от кодировки символов. Страница имеет набор символов, например, UTF-8, а затем она имеет кодировку содержимого поверх этого. Кодировка содержимого gzip сжимает страницу с помощью gzip чтобы сделать ее меньше, поэтому для отправки по сети требуется меньше времени.
Показать ещё 4 комментария
Теги:
pandas-datareader

1 ответ

0
Лучший ответ

Коренная проблема заключается в том, что вы следуете устаревшему учебнику.

Если вы посмотрите на документы для pandas-datareader, прямо вверху, там появится большая коробка, в которой говорится:

Предупреждение

Начиная с v0.6.0 Yahoo !, Параметры Google, Google Quotes и EDGAR были немедленно устарели из-за больших изменений в их API и стабильной замены.

Всякий раз, когда вы следите за учебником или блога, и что-то не работает правильно, первое, что вам нужно сделать, это посмотреть фактическую документацию на то, что они учат вас использовать. Все меняется, и вещи, которые завершают веб-API, меняются особенно быстро.

В любом случае, если вы перейдете к списку источников данных, вы увидите, что нет записи Yahoo. Но код все еще присутствует в источнике. Таким образом, вместо того, чтобы получать ошибку об отсутствии такого источника, вы получаете ошибку немного позже, пытаясь использовать разбитый источник.

На поверхностном уровне происходит то, что код datareader делает какой-то запрос (вам придется копаться в библиотеке или, может быть, захватить его с помощью Wireshark, чтобы увидеть, что такое URL и заголовки), который получает ответ, который утверждает, что использует кодирование содержимого gzip, но делает это неправильно.

Кодировка содержимого - это то, что применяется к странице веб-сервером и отменено вашим браузером или клиентом, обычно сжатием, чтобы сделать страницу меньше времени для отправки по сети. gzip - наиболее распространенная форма сжатия. Это очень простой формат, поэтому он так часто используется (сервер может gzip тысячи страниц без необходимости фермы суперкомпьютеров), но это означает, что если что-то пойдет не так - как сервер просто обрезает поток 16KB или что-то еще не может сказать, что пошло не так, за исключением того, что распаковка gzip не удалась.

Но независимо от того, нет никакого способа исправить это; 1 вы должны переписать свой код для использования другого источника данных.

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


1. Если вы не хотите понять новый API Yahoo, предполагая, что он есть, и выяснить, как его разобрать, и написать целый новый источник pandas-datareader, хотя эксперты, которые пишут эту библиотеку, отказались от попыток разобраться с Yahoo...

  • 0
    Отличный ответ! Я бы проголосовал, если бы мог. TYSM, я найду новый источник

Ещё вопросы

Сообщество Overcoder
Наверх
Меню