2014-12-17 11 views
14

L'applicazione Django utilizza l'Rest Framework JWT per l'autenticazione. Funziona benissimo e molto elegante.Come eseguire l'autenticazione Token Web Django JSON senza forzare l'utente a digitare nuovamente la propria password?

Tuttavia, ho un caso d'uso che sto cercando di costruire. Ho già programmato una soluzione funzionante per il flusso di lavoro "Password dimenticata". Consentire a un utente non autenticato di reimpostare la propria password se e solo se fa clic su un collegamento segreto che invierò al suo indirizzo email. Tuttavia, vorrei modificare questa soluzione in modo tale che dopo che il flusso di lavoro di reimpostazione della password sia stato completato con successo, l'utente è connesso automaticamente a senza dover ridigitare il nome utente e la (nuova) password. Mi piacerebbe farlo per rendere l'esperienza dell'utente il più semplice possibile.

Il problema è che non so come farlo funzionare senza che l'utente ridigita la sua password (o la memorizza in chiaro nel DB che è ovviamente molto male). Di seguito è riportato l'attuale modo in cui ottengo il token JWT. Puoi vedere che nella riga 12, ho bisogno della password chiara dell'utente. Io non ce l'ho. Ho solo la password crittografata memorizzata in my_user.password.

Come posso utilizzare la password crittografata in my_user.password anziché la password di cancellazione per ottenere il JWT? Se non riesco a utilizzarlo, come viene raggiunto questo flusso di lavoro utilizzando il JWT di Rest Framework?

from rest_framework_jwt.views import ObtainJSONWebToken 
from rest_framework status 
from django.contrib.auth.models import User 

my_user = User.objects.get(pk=1) 
ojwt = ObtainJSONWebToken() 

if "_mutable" in dir(request.DATA): 
    mutable = request.DATA._mutable 
    request.DATA._mutable = True 
request.DATA['username'] = my_user.username 
request.DATA['password'] = "<my_user's clear password>" 
if "_mutable" in dir(request.DATA): 
    request.DATA._mutable = mutable 


token_response = ojwt.post(request) 
if status.is_success(token_response.status_code): 
    # Tell the user login succeeded!! 
else: 
    # Tell the user login failed. 
    # But hopefully, this shouldn't happen 

risposta

19

Quando si lavora con Django REST quadro JWT, esso è tipicamente previsto che l'utente sta generando il token da soli. Poiché stai generando il token per conto dell'utente, non puoi utilizzare nessuna delle viste standard per farlo funzionare.

Avrete bisogno di generare il token da soli, simile a how DRF JWT does it nelle viste. Questo significa usare qualcosa di simile a quanto segue per il codice di vista

from rest_framework_jwt.settings import api_settings 
from datetime import datetime 


jwt_payload_handler = api_settings.JWT_PAYLOAD_HANDLER 
jwt_encode_handler = api_settings.JWT_ENCODE_HANDLER 

my_user = User.objects.get(pk=1) # replace with your existing logic 

payload = jwt_payload_handler(my_user) 

# Include original issued at time for a brand new token, 
# to allow token refresh 
if api_settings.JWT_ALLOW_REFRESH: 
    payload['orig_iat'] = timegm(
     datetime.utcnow().utctimetuple() 
    ) 

return { 
    'token': jwt_encode_handler(payload) 
} 

Ciò dovrebbe consentire di generare manualmente il token all'interno della vista, senza dover conoscere la password dell'utente.

+0

Risposta eccezionale! Grazie. Ho apportato una modifica secondaria: mancava una dichiarazione di importazione. –

+0

Grazie mille per questo Kevin. La tua risposta colpisce il posto! È particolarmente utile quando esegui OAuthing su dispositivi mobili e utilizzi un'API protetta con un token. Ho integrato Python Social Auth + DRF + JWT – msaad

+1

Per chiunque abbia problemi a far funzionare questo, [qui] (https://codepal.herokuapp.com/how-to-add-facebook-login-to-django-using -json-web-tokens /) è un tutorial passo-passo sull'implementazione dell'autenticazione basata su JWT per le app Django. – dvc

Problemi correlati