В чем разница между запросами.post и этим прямым завитком?

Использование python 3.6.2 с requests библиотека.

Я пытаюсь пройти проверку подлинности с помощью oauth2 в API-интерфейсе battle.net, и при втором запросе (запрос на получение токена) я получаю ошибку 400 без полезного объяснения ("внутренняя ошибка сервера"). Кто-то на форуме battle.net предложил попробовать сделать то же самое POST с curlи это работает. (вот мое сообщение на форуме: https://us.battle.net/forums/en/bnet/topic/20762236765)

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

Вот код Python:

data = {
         'code': code,
         'redirect_uri': 'https%3A%2F%2Flocalhost%2Foauth2callback',
         'grant_type': 'authorization_code',
         'client_id': CLIENT_ID,
         'client_secret': CLIENT_SECRET,
         'scope': 'sc2.profile'
    }
resp = requests.post('https://eu.battle.net/oauth/token', data=data)

И вот локон:

curl -X POST -s "https://eu.battle.net/oauth/token" \
    -d client_id='<same as above>' \
    -d client_secret='<same as above>'  \
    -d grant_type='authorization_code' \
    -d redirect_uri='https%3A%2F%2Flocalhost%2Foauth2callback' \
    -d scope='sc2.profile'  \
    -d code='<same as above>'

Как я уже сказал, я думаю, что должно быть что-то другое, но я не эксперт по http. Может быть, что-то в заголовках? Как я могу настроить запросы, чтобы иметь такое же поведение?

1 ответ

Решение

Вам не нужно вручную кодировать redirect_uri; requests сделаю это для вас.

data = {
     'code': code,
     'redirect_uri': 'https://localhost/oauth2callback',
     'grant_type': 'authorization_code',
     'client_id': CLIENT_ID,
     'client_secret': CLIENT_SECRET,
     'scope': 'sc2.profile'
}
resp = requests.post('https://eu.battle.net/oauth/token', data=data)

Эквивалент curl вызов будет использовать --data-urlencode вместо -d/--data,

curl -X POST -s "https://eu.battle.net/oauth/token" \
    -d client_id='<same as above>' \
    -d client_secret='<same as above>'  \
    -d grant_type='authorization_code' \
    --data-urlencode redirect_uri='https://localhost/Foauth2callback' \
    -d scope='sc2.profile'  \
    -d code='<same as above>'

Чтобы отладить подобные проблемы, вы можете написать на https://httpbin.org/post; ответ покажет вам, какие именно данные были отправлены в запросе POST.

Другие вопросы по тегам