120

I'm trying to create a new User in a Django project by the following code, but the highlighted line fires an exception.

def createUser(request):
    userName = request.REQUEST.get('username', None)
    userPass = request.REQUEST.get('password', None)
    userMail = request.REQUEST.get('email', None)

    # TODO: check if already existed

    **user = User.objects.create_user(userName, userMail, userPass)**
    user.save()

    return render_to_response('home.html', context_instance=RequestContext(request))

Any help?

the
  • 21,007
  • 11
  • 68
  • 101
Amr M. AbdulRahman
  • 1,820
  • 3
  • 14
  • 22

6 Answers6

254

The correct way to create a user in Django is to use the create_user function. This will handle the hashing of the password, etc..

from django.contrib.auth.models import User
user = User.objects.create_user(username='john',
                                 email='jlennon@beatles.com',
                                 password='glass onion')
sirFunkenstine
  • 8,135
  • 6
  • 40
  • 57
keithhackbarth
  • 9,317
  • 5
  • 28
  • 33
  • 4
    will this hash the password ? – mp3por Feb 10 '16 at 15:57
  • 11
    @mp3por - Yes. For full documentation, go here https://docs.djangoproject.com/en/1.9/ref/contrib/auth/#django.contrib.auth.models.UserManager.create_user – keithhackbarth Feb 10 '16 at 19:17
  • 2
    how/where do I run this? If I just run that code I get `django.core.exceptions.AppRegistryNotReady: Apps aren't loaded yet.` EDIT: this works `DJANGO_SETTINGS_MODULE=app.settings.dev python manage.py shell < register-user.py` – citynorman Jan 06 '18 at 20:42
  • 15
    As an update for more modern Django, use `from django.contrib.auth import get_user_model` and `user = get_user_model().objects.create_user(...` – Mark Chackerian May 18 '19 at 17:14
  • 1
    @keithhackbarth in which file should I insert this code in the django file structure? – Hangon Jan 14 '20 at 13:05
  • Above documentation link is broken. Here's the source code for `create_user`: https://github.com/django/django/blob/master/django/contrib/auth/models.py#L143 (you can see that it hashes the password) – User Feb 17 '20 at 11:54
  • Django doc: https://docs.djangoproject.com/en/3.0/topics/auth/default/#topics-auth-creating-users – Emily Mar 08 '20 at 00:52
  • Make sure to do ```user.save()``` in the end. – Emily Mar 08 '20 at 01:29
  • @Emily you don't need to call .save(), because .create_user() both instantiate the object AND saves it to db. Additionnaly, you can verify for yourself that the passwords are hashed. If you go to the admin pagem, click Users & clik the user your created, you'll the details of hte hash, salt & algo used to hash the passwor.d – logicOnAbstractions Mar 31 '21 at 18:57
24

Have you confirmed that you are passing actual values and not None?

from django.shortcuts import render

def createUser(request):
    userName = request.REQUEST.get('username', None)
    userPass = request.REQUEST.get('password', None)
    userMail = request.REQUEST.get('email', None)

    # TODO: check if already existed
    if userName and userPass and userMail:
       u,created = User.objects.get_or_create(userName, userMail)
       if created:
          # user was created
          # set the password here
       else:
          # user was retrieved
    else:
       # request was empty

    return render(request,'home.html')
Burhan Khalid
  • 169,990
  • 18
  • 245
  • 284
15

Bulk user creation with set_password

I you are creating several test users, bulk_create is much faster, but we can't use create_user with it.

set_password is another way to generate the hashed passwords:

def users_iterator():
    for i in range(nusers):
        is_superuser = (i == 0)
        user = User(
            first_name='First' + str(i),
            is_staff=is_superuser,
            is_superuser=is_superuser,
            last_name='Last' + str(i),
            username='user' + str(i),
        )
        user.set_password('asdfqwer')
        yield user

class Command(BaseCommand):
    def handle(self, **options):
        User.objects.bulk_create(iter(users_iterator()))

Question specific about password hashing: How to use Bcrypt to encrypt passwords in Django

Tested in Django 1.9.

Community
  • 1
  • 1
Ciro Santilli OurBigBook.com
  • 347,512
  • 102
  • 1,199
  • 985
6

If you creat user normally, you will not be able to login as password creation method may b different You can use default signup form for that

from django.contrib.auth.forms import UserCreationForm

You can extend that also

from django.contrib.auth.forms import UserCreationForm

class UserForm(UserCreationForm):
    mobile = forms.CharField(max_length=15, min_length=10)
    email = forms.EmailField(required=True)
    class Meta:
        model = User
        fields = ['username', 'password', 'first_name', 'last_name', 'email', 'mobile' ]

Then in view use this class

class UserCreate(CreateView):
    form_class = UserForm
    template_name = 'registration/signup.html'
    success_url = reverse_lazy('list')

    def form_valid(self, form):
        user = form.save()
Nids Barthwal
  • 2,205
  • 20
  • 12
1

If you simply use object.save() to create user, the raw password will be directly visiable inside the database. First, not secure. Second, the encryption of the password is not done, causing the decryptor will use the raw password inside your database to decrypto a wrong password, which makes logging in impossible. I guess every time you use authenticate function from django.contrib.auth, you are actually using the decryptor of it. And yes, I guess everytime you signing in, your password need to get decrypted again.

Boyce Cecil
  • 97
  • 2
  • 8
0

You can create a super user from the command line. Make sure you have run migraitons

python manage.py createsuperuser --username=joe --email=joe@example.com

Link to docs: https://docs.djangoproject.com/en/4.2/topics/auth/default/