2010-08-03 6 views
12

sto cercando una guida su come aggiungere il supporto di autenticazione di Windows in un app Django, particolarmente OSQANtlm/Kerberos in Django

Sono a conoscenza circa http://code.google.com/p/python-ntlm/ E visto anche questo post: http://erny-rev.blogspot.com/2007/11/ntlm-authentication-in-django.html Ma io' m non è un Django-dev, voglio solo distribuire OSQA in ambiente Windows (intranet, quindi ho bisogno di aggiungere l'autenticazione di Windows). Quindi sto cercando una semplice descrizione passo-passo.

(sono riuscito a distribuire un sito OSQA su Windows con SQL Server e che sta funzionando)

UPDATE:
mi piacerebbe ottenere non solo di autenticazione contro dC ma il comportamento SSO-come in IE. Quando un utente accede al mio sito basato su Django in IE, si autenticherà automaticamente con il suo account di dominio.

+0

hai mai capito? –

+0

Actualy, no :( ma ho anche chiesto qui - http://meta.osqa.net/questions/4326/how-to-add-windows-authentication e ora ho notato una risposta con link a http: // jira .osqa.net/browse/OSQA-425 – Shrike

+0

Avevo visto anche quella patch, anche se in quanto non risolvera 'quello che io e te vorremmo e che è autenticabile Questa patch sembra solo aggiungere un nuovo modo per autenticare. –

risposta

4

In genere, se si desidera solo l'autenticazione con Active Directory, l'approccio con maggiore probabilità di successo è l'utilizzo dell'autenticazione LDAP contro il servizio LDAP di Active Directory. L'unico trucco è che diversamente dalla maggior parte dei server LDAP, Active Directory deve avere un utente autenticato (e una password). La maggior parte delle persone finisce con l'instaurare un utente 'ldap-query' con l'hardcode dell'utente per la configurazione della query.

Per esempi, vedere http://djangosnippets.org/snippets/501/ e http://www.google.com/search?q=Django+LDAP+authentication

+0

Mi piacerebbe ottenere non solo un'autorizzazione contro AD, ma un comportamento simile a SSO in IE. Quando un utente accede al mio sito basato su Django in IE, si autenticherà automaticamente con il suo account di dominio. – Shrike

11

È possibile farlo usando Apache, mod_auth_kerb e l'autenticazione REMOTE_USER con Django ospitato come mod_wsgi.

Ecco un esempio di alcune config usiamo:

WSGIDaemonProcess myapp user=myapp group=myapp processes=5 threads=1 
WSGIProcessGroup myapp 
WSGIScriptAlias /myapp /home/wolapp/code/wolapp.wsgi 
<VirtualHost ...> 
    <Location /myapp> 
      AuthType    Kerberos 
      AuthName    "Domain Login" 
      KrbMethodNegotiate  On 
      KrbMethodK5Passwd  On 
      KrbAuthRealms   YOUR.DOMAIN 
      Krb5Keytab    /etc/krb5.keytab 
      KrbServiceName   HTTP/server.your.domain 
      require     valid-user 
    </Location> 
</VirtualHost> 

È quindi necessario impostare questo:

http://docs.djangoproject.com/en/dev/howto/auth-remote-user/

Un paio di avvertimenti da notare:

  1. L'opera fallisce completamente nei nostri test; non può gestire l'intestazione "Negoziare"
  2. IE funziona correttamente se la macchina è nel dominio, ma se non lo è, viene richiesta la password due volte - la prima volta che la macchina utilizza "ITSNAME \ username" che fallisce; la seconda volta il "nome utente" nudo

Spero che questo aiuti.

5

Questo potrebbe non essere così elegante, ma funziona (import/mettere in vista):

import base64 


def get_msg_str(msg,start): 
    msg_len, _, msg_off = struct.unpack("<HHH", msg[start:start + 6]) 
    return msg[msg_off:msg_off + msg_len].replace("\0", '') 


def ntlm_auth(request): 
    """Goes through ntlm stages... 
    Return user_name, response. 
    While response is not none, keep sending it. 
    Then use the user. 
    """ 
    username = None 
    response = None 

    auth = request.META.get('HTTP_AUTHORIZATION') 
    if not auth: 
     response = HttpResponse(status=401) 
     response['WWW-Authenticate'] = "NTLM" 
    elif auth[:4] == "NTLM": 
     msg = base64.b64decode(auth[4:]) 
     # print repr(msg) 
     ntlm_fmt = "<8sb" #string, length 8, 4 - op 
     NLTM_SIG = "NTLMSSP\0" 
     signature, op = struct.unpack(ntlm_fmt, msg[:9]) 
     if signature != NLTM_SIG: 
      print "error header not recognized" 
     else: 
      print "recognized" 
      # print signature, op 
      # print repr(msg) 
      if op == 1: 
       out_msg_fmt = ntlm_fmt + "2I4B2Q2H" 
       out_msg = struct.pack(out_msg_fmt, 
        NLTM_SIG, #Signature 
        2, #Op 
        0, #target name len 
        0, #target len off 
        1, 2, 0x81, 1, #flags 
        0, #challenge 
        0, #context 
        0, #target info len 
        0x30, #target info offset 
       ) 

       response = HttpResponse(status=401) 
       response['WWW-Authenticate'] = "NTLM " + base64.b64encode(out_msg).strip() 
      elif op == 3: 
       username = get_msg_str(msg, 36) 

    return username, response 

Usage:

def my_view(request): 
    username, response = ntlm_auth(request) 
    if response: 
     return response 

Sono sicuro che questo potrebbe essere reso più elegante come decoratore e ci possono essere altri modi - ma l'ho usato e funziona.

+1

Da dove viene l'autentica autenticazione qui? Sembra che accetta solo la risposta del browser (che potrebbe essere falsificata?). –

+0

Questo è vero - nel nostro caso d'uso in realtà non siamo rivolti verso il web, è soprattutto così che una piccola squadra può essere più pigra di digitare un nome utente usando IE SSO. Tuttavia, ho il sospetto che ci siano ulteriori dati dei messaggi con più informazioni sulle credenziali da verificare rispetto al database degli utenti di Django. Sentiti libero di migliorare la mia risposta. –

+0

Sto cercando di utilizzare questo esempio, ma non riesco a farlo funzionare. Invia la risposta iniziale sotto 'non auth', ma nulla dopo. C'è qualche dettaglio che mi manca nel fare questo lavoro? – robbie