В документации django-rest-auth обсуждается интеграция с Facebook, которой меня не интересует... моя забота заключается в предоставлении социального входа через Google. Я пробовал это уже довольно давно, и мне интересно, есть ли у кого-нибудь еще какая-либо документация о том, как они это сделали... даже приблизительный эскиз был бы полезен. До сих пор я не нашел никаких результатов для этого поиска. Я почти нахожусь там, но не могу заставить его работать с API-интерфейсом Django rest framework (DRF).
Вот что у меня есть до сих пор: Я начал с демонстрационного проекта, представленного на странице django-rest-auth github, и изменил страницу HTML шаблона социального входа, чтобы требовать ввод только "кода", а не как "код", так и "access_token". Когда я поставлю действительный код (полученный отдельным запросом к конечной точке google auth), это работает нормально; API-интерфейс, доступный для просмотра, отображает обычную веб-страницу с ключом "ключ" (токен API приложения для пользователя) в ответе. Проверка администратора django, все сработало - пользователь вошел в систему, электронная почта аутентифицирована и т.д. До сих пор хорошо.
Проблема заключается в том, что отправная точка поставки "кода" - и как я получаю этот код от google в первую очередь. Когда я ранее (успешно) использовал пакет allauth, я мог просто щелкнуть ссылку, которая "невидимо" выполнила бы весь поток OAuth2 (т.е. Запросить код, использовать этот код для получения токена доступа и использовать токен доступа для получить информацию об учетной записи пользователя google).
Чтобы воссоздать этот бесшовный поток (т.е. НЕ начинать с кода), я решил, что могу прервать поток OAuth2 и "перехватить" код, возвращенный из google, а затем POST этот код в социальный логический интерфейс rest-auth. С этой целью я создал пользовательский allauth.socialaccount.providers.oauth2.views.OAuth2CallbackView
, переопределив метод отправки:
class CustomOAuth2CallbackView(OAuth2CallbackView):
def dispatch(self, request):
# gets the code correctly:
code = request.GET['code']
# rp is of type requests.methods.Response
rp = requests.post(<REST-AUTH API ENDPOINT>, data = {'code':code})
return rp
Обычно этот метод вызывается, когда Google отправляет запрос GET на url обратного вызова, который вы первоначально поставляете для конечной точки google. С этим переопределением я могу успешно проанализировать код, возвращенный из Google в этом обратном вызове. Запрос POST работает и имеет пользовательский ключ в поле resp._content. Тем не менее, в конечном итоге он не может создать предполагаемый вид в API-интерфейсе, доступном для просмотра DRF.
На основе погружения в стоп-код, я обнаружил, что rest_framework.views.APIView.dispatch
возвращает объект типа rest_framework.response.Response
. Однако, когда метод requests.post
, использованный выше, завершает, он возвращает экземпляр типа requests.models.Response
. В результате он не имеет надлежащих атрибутов и не работает в промежуточном программном обеспечении django. Например, он не имеет атрибута acceptable_renderer
и не имеет метода get (который используется в django.middleware.clickjacking.py
). Я мог бы, возможно, добавить эти требования к экземпляру requests.models.Response
(rp
), но тогда этот хак становится еще более клочой.
Спасибо за любую помощь, которую вы можете предоставить!