2011-11-05 11 views
40

Estoy creando algunos usuarios de forma predeterminada en mi fixtures/initial_data.json para tener algunos "sujetos" de prueba. El problema que estoy experimentando es la generación de contraseñas. Podría establecer la contraseña en los campos '', pero eso no va a generar un hash de la contraseña:Usuarios en el dispositivo de datos inicial

[ 
    { "model": "auth.user", 
     "pk": 1, 
     "fields": { 
      "username": "user1", 
      "password": "password" 
     } 
    } 
] 

necesito una manera de generar la contraseña del usuario. ¿Debo hacer esto manualmente y generar una cadena como {hash_method}${salt}${hashed_password} como lo hace Django?

Respuesta

78

¿Qué podría ser más fácil en este caso (y si sólo necesita unos pocos usuarios) es la creación de cuentas de algunos falso usuario a través de la administración (incluyendo contraseñas) y luego volcar los usuarios a un accesorios de archivo usando dumpdata:

$ python manage.py dumpdata auth.User --indent 4 > users.json 

, que crea automáticamente los accesorios para usted y puede ser utilizado más tarde con loaddata

(se podía crear una cuenta falsa y usar el hash en el resto de sus accesorios si usted necesita una gran cantidad de usuarios de prueba)

https://docs.djangoproject.com/en/dev/ref/django-admin/#dumpdata-appname-appname-appname-model

+0

Hmm - tratando de hacer esto por mí resulta en un vertedero en blanco aquí. –

+1

Está bien - funciona desde un db sqlite local, pero no el db mysql principal. ¿Es esto una característica de seguridad? –

+2

"Simplemente podría crear una cuenta falsa y usar el hash en el resto de sus dispositivos si necesitara muchos usuarios de prueba" -> ¡este consejo me ha salvado! Muchas gracias :) – daveoncode

0

bastante seguro de que hacer. no debería ser tan difícil. La forma más fácil sería mirar la función user.set_password, creo que es, y ver cómo lo hacen. ¡probablemente puedas llamar a la función desde un terminal python y luego copiarla en tus datos iniciales!

13

OK, estoy de acuerdo con las respuestas, pero permítame responder a las preguntas originales.

¿Cómo obtener la contraseña "como Django lo habría hasheado"?

Veamos un fichero django/contrib/auth/hashers.py:

def make_password(password, salt=None, hasher='default'): 
    """ 
    Turn a plain-text password into a hash for database storage 

    Same as encode() but generates a new random salt. If 
    password is None or blank then UNUSABLE_PASSWORD will be 
    returned which disallows logins. 
    """ 
    # ... 

ver este ejemplo de sesión:

./manage.py shell 

>>> from django.contrib.auth.hashers import make_password, HASHERS 
>>> make_password('test') 
'pbkdf2_sha256$10000$vkRy7QauoLLj$ry+3xm3YX+YrSXbri8s3EcXDIrx5ceM+xQjtpLdw2oE=' 

# fix salt: 
>>> make_password('test', 'abc') 
'pbkdf2_sha256$10000$abc$MqJS5OAgSmf9SD9mfoY8fgLo8sSKmEcef0AjjMp1Q7w=' 

# use different (maybe faster, maybe unsafe!) hasher 

In [12]: HASHERS 
Out[12]: 
{'bcrypt': <django.contrib.auth.hashers.BCryptPasswordHasher object at 0x29c6d50>, 
'crypt': <django.contrib.auth.hashers.CryptPasswordHasher object at 0x29c6f50>, 
'md5': <django.contrib.auth.hashers.MD5PasswordHasher object at 0x29c6e10>, 
'pbkdf2_sha1': <django.contrib.auth.hashers.PBKDF2SHA1PasswordHasher object at 0x29c6bd0>, 
'pbkdf2_sha256': <django.contrib.auth.hashers.PBKDF2PasswordHasher object at 0x29c6cd0>, 
'sha1': <django.contrib.auth.hashers.SHA1PasswordHasher object at 0x29c6dd0>, 
'unsalted_md5': <django.contrib.auth.hashers.UnsaltedMD5PasswordHasher object at 0x29c6ed0>, 
'unsalted_sha1': <django.contrib.auth.hashers.UnsaltedSHA1PasswordHasher object at 0x29c6e50>} 

In [14]: [make_password('test', hasher=name) for name in HASHERS] 
Out[14]: 
['sha1$LdKsAbJRjlVP$2eb2346387cc510f576f2f11eebdfe18b20d1be1', 
'pbkdf2_sha256$10000$Ck8gtWQJnJ9x$M/OqP548d5KcPqFuVRgXb84unjYbYDH6oyimbDndE3k=', 
'pbkdf2_sha1$10000$BJqRu5OwylVF$hUvMLIzBujt9kPbML/dei1vLiMQ=', 
'crypt$$d9grSeqDhMFek', 
'098f6bcd4621d373cade4e832627b4f6', 
'sha1$$a94a8fe5ccb19ba61c4c0873d391e987982fbbd3', 
'bcrypt$$2a$12$WlJP5zm2lmdJ4g/pSE1xF.d/8w.XRT5mo/vGlkKdglBtzcxKw7XJS', 
'md5$txHYmSYJKhD4$69286d4a1abd348fbddc9df7687e2ed4'] 

También puede utilizar manualmente el método de la hasher encode, pero la función de utilidad anterior tiene cubierto en una Manera más fácil.

7

Me encontré con el mismo problema al escribir aparatos para las pruebas. Así es como estoy manejando esto en pruebas unitarias.

Creando datos desde el administrador y volcándolos en los trabajos de fijación, pero no me gusta mucho depender de hacerlo manualmente. Así que esto es lo que hago:

Cree el dispositivo tal como lo hizo y luego en el método setUp, set_password s para los usuarios.

user_fixture.json

[ 
    { "model": "auth.user", 
     "pk": 1, 
     "fields": { 
      "username": "user1", 
      "password": "password" 
     } 
    } 
] 

test_user.py

def setUp(self): 
    self.User = get_user_model() 

    # Fix the passwords of fixtures 
    for user in self.User.objects.all(): 
     user.set_password(user.password) 
     user.save() 

De esta manera limpia Puedo escribir las contraseñas en la fijación y referirse a ellos cuando lo necesite y crear más aparatos simplemente editando el archivo de datos.

2

Agregando a la respuesta de @GauravButola, creé un comando de administración personalizado para cargar el dispositivo y arreglar las contraseñas en un solo paso. Esto es útil cuando no se utiliza un marco de prueba para configurar la configuración de las contraseñas. El ejemplo está funcionando con django 1.11 y probablemente con versiones anteriores.

En su aplicación para proporcionar el accesorio añadir el comando de gestión (esto es python3 veces, por lo que omite el pys init):

yourapp/ 
    models.py 
    fixtures/ 
     initial_data.json 
    management/ 
     commands/ 
      initdata.py 

Con initdata.py con este aspecto:

from django.core.management import BaseCommand, call_command 
from django.contrib.auth.models import User 
# from yourapp.models import User # if you have a custom user 


class Command(BaseCommand): 
    help = "DEV COMMAND: Fill databasse with a set of data for testing purposes" 

    def handle(self, *args, **options): 
     call_command('loaddata','initial_data') 
     # Fix the passwords of fixtures 
     for user in User.objects.all(): 
      user.set_password(user.password) 
      user.save() 

Ahora puede cargar sus initial_data y tener contraseñas válidas llamando al:

./manage.py initdata 
0

Dump Users information fro m Base de datos:

$ python manage.py dumpdata auth.User --indent 4 > users.json 

Importar/cargar datos JSON especific accesorio:

$ python manage.py loaddata users.json 
Cuestiones relacionadas