Django ModelAdmin - custom name of items in drop down list - django

I want to change a names of items (users) in drop down list in Django Admin Model. I want to do it without any changes in basic models.
I just want to field 'user'(admin.py) refers to 'user' in Worker model(office.py) through username (just without Firstname and Lastname)
admin.py
from .models import Token
class TokenAdmin(admin.ModelAdmin):
model = Token
fieldsets = (
(None, {
'fields': ('name', 'key', 'user')
}),
models.py
from office.models import Worker
class Token(models.Model):
user = models.ForeignKey(
Worker,
related_name='auth_token',
verbose_name=_("api.models.token.user")
)
office.py
class Worker(models.Model):
user = models.OneToOneField(settings.AUTH_USER_MODEL, verbose_name=_("User"))
firstname = models.CharField(
_("Firstname"), blank=False, null=False, max_length=50)
lastname = models.CharField(
_("Lastname"), blank=False, null=False, max_length=50)
def __str__(self):
return "%s %s" % (self.lastname, self.firstname)

I have solved it!
admin.py
class UserChoiceField(forms.ModelChoiceField):
def label_from_instance(self, obj):
return obj.user
class TokenAdmin(admin.ModelAdmin):
def formfield_for_foreignkey(self, db_field, request=None, **kwargs):
if db_field.name == 'user':
kwargs['form_class'] = UserChoiceField
return super(TokenAdmin, self).formfield_for_foreignkey(db_field, request, **kwargs)

Related

Django Forn Not Saving Extra Information

I extended the Django AbstratUser so that users can use email to sign in and signup, these work perfectly. The problem I am facing, however, is that the extra information on the extended model is not storing the information in the database, even though the user gets created. Once I hit the submit button, the user and extended model get created, and while the user model stores the information, the extended model is always empty.
I have tried using both signals and #transaction_atomic, yet, I have not been able to figure it out. Maybe I am missing out something, I do not know.
Models.py
class Company(models.Model):
user = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, primary_key=True)
name= models.CharField(_('Company name'), max_length=250)
...
#more information
...
class Meta:
verbose_name = _('Company')
verbose_name_plural = _('Companies')
def __str__(self):
return self.name
forms.py
class CompanySignUpForm(CustomUserCreationForm):
name = forms.CharField(widget=TextInput(attrs={'placeholder': 'Company name'}))
...
#more fields
...
class Meta(CustomUserCreationForm.Meta):
model = User
#transaction.atomic
def save(self):
user = super().save(commit=False)
user.is_company = True
user.save()
company = Company.objects.create(user=user)
company.name = self.cleaned_data.get('name')
...
#more information
...
return user
Views.py
def company_signup(request):
if request.method == 'POST':
form = CompanySignUpForm(request.POST)
if form.is_valid():
form.save()
return render(request, 'accounts/templates/company_success.html')
else:
form = CompanySignUpForm()
return render(request, 'accounts/templates/company_signup.html', context={
'title': _('Create a Company Account'),
'form': form,
})
Edit:
Thanks to #Mandrup, I was able to extend his solution to fit my need.
forms.py
class CompanySignUpForm(CustomUserCreationForm):
name = forms.CharField(widget=TextInput(attrs={'placeholder': 'Company name'}))
number_of_employees = forms.CharField(widget=NumberInput(attrs={'placeholder': 'Number of employees'}))
phone = forms.CharField(widget=TextInput(attrs={'placeholder': 'Contact Number'}))
country = forms.ModelChoiceField(queryset=Country.objects.all(), required=True, empty_label="Country")
class Meta(CustomUserCreationForm.Meta):
model = User
#transaction.atomic
def save(self, commit=True):
user = super(CompanySignUpForm, self).save(commit=False)
if commit:
user.is_company = True
user.save()
name = self.cleaned_data.get('name')
number_of_employees = self.cleaned_data.get('number_of_employees')
phone = self.cleaned_data.get('phone')
country = self.cleaned_data.get('country')
company = Company(user=user, name=name, number_of_employees=number_of_employees, phone=phone, country=country)
company.save()
return user
Edit:
This worked for me when i tried to create an extended user profile. I changed it to fit your needs.
Model:
class Company(models.Model):
user = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, primary_key=True)
name= models.CharField(max_length=250)
...
#more information
...
def __str__(self):
return self.name
Form:
class RegisterUserForm(UserCreationForm):
class Meta:
model = User
fields = ["username", "email", "password1", "password2"]#add whatever fields you want to here
def save(self, commit=True):
user = super(RegisterUserForm, self).save(commit=False)
if commit:
user.save()
company = Company(user=user, name='Company name')
company.save()
return user

Nested AbstractUser model failing during update operation with "null value in column "user_id" violates not-null constraint"

I am creating nested abstract user "Teacher from User", My use case is "Create User" -> "Then make user to teacher"
I am able to create user and make the user to Teacher, but I am unable to update the field, In below case want to update "teacher_cost"
Model.py
from django.contrib.postgres.fields import JSONField
from django.db import models
from django.contrib.auth.models import AbstractUser
class User(AbstractUser):
uid = models.AutoField(verbose_name='ID',
serialize=False,
auto_created=True,
primary_key=True)
TEACHER = "Teacher"
STUDENT = "Student"
user_type = models.CharField(max_length=30, default=STUDENT)
contact_number = models.CharField(max_length=20, null=True, blank=True)
address = models.TextField(null=True, blank=True)
photo = models.ImageField(null=True, blank=True)
image = models.ImageField(upload_to='users/',
default='default/avatar.png')
approved = models.BooleanField(default=True)
def save(self, *args, **kwargs):
if self.user_type == User.TEACHER and self._state.adding:
self.approved = False
super().save(*args, **kwargs)
#property
def dishes(self):
ret = self.teacher.dish_set.all()
if ret:
return ret
else:
return ''
class Teacher(models.Model):
uid = models.AutoField(verbose_name='ID',
serialize=False,
auto_created=True,
primary_key=True)
user = models.OneToOneField(User, on_delete=models.CASCADE)
bio = models.TextField(null=True, blank=True)
teacher_cost = models.DecimalField(
max_digits=5, decimal_places=2, null=True, blank=True)
languages = models.CharField(
max_length=50, null=True, blank=True)
address = models.TextField(null=True, blank=True)
def __str__(self):
return self.user.username
Serializer.py
from rest_framework import serializers, exceptions
from django.contrib.auth.forms import PasswordResetForm
from django.conf import settings
from .models import *
from rest_auth import serializers as rest_auth_serializers
from django.utils.translation import ugettext_lazy as _
class UserDetailsSerializer(serializers.ModelSerializer):
"""
User model w/o password
"""
class Meta:
model = User
fields = ('pk', 'username', 'email',
'first_name', 'last_name', 'contact_number', 'user_type', 'photo', 'address')
read_only_fields = ('email', )
class UserTeacher(serializers.ModelSerializer):
class Meta:
model = User
fields = ('teacher',)
class TeacherDetails(serializers.ModelSerializer):
class Meta:
model = Teacher
fields = '__all__'
class TeacherFullDetails(serializers.ModelSerializer):
user_id = serializers.CharField(source='user.uid')
username = serializers.CharField(source='user.username')
first_name = serializers.CharField(source='user.first_name')
last_name = serializers.CharField(source='user.last_name')
photo = serializers.ImageField(
source='user.photo', max_length=None, use_url=True)
class Meta:
model = Teacher
fields = ('user_id', 'username', 'first_name', 'last_name', 'photo', 'teacher_cost')
class TeacherBriefDetails(serializers.ModelSerializer):
uid = serializers.CharField(source='user.uid')
first_name = serializers.CharField(source='user.first_name')
last_name = serializers.CharField(source='user.last_name')
class Meta:
model = Teacher
fields = ('uid', 'first_name', 'last_name',)
class TeacherProfileDetails(serializers.ModelSerializer):
contact_number = serializers.CharField(source='user.contact_number', required=False)
first_name = serializers.CharField(source='user.first_name', required=False)
last_name = serializers.CharField(source='user.last_name', required=False)
email = serializers.CharField(source='user.email', required=False)
photo = serializers.ImageField(
source='user.photo', max_length=None, use_url=True, required=False)
user = UserDetailsSerializer(read_only=True)
teacher_cost = serializers.CharField()
class Meta:
model = Teacher
fields = ('user', 'first_name', 'last_name', 'contact_number', 'email', 'photo',
'bio', 'teacher_cost')
class TeacherProfileSerializer(serializers.ModelSerializer):
user = UserDetailsSerializer()
class Meta:
model = Teacher
fields = ("bio", "teacher_cost", "user")
view.py
from rest_framework import generics, viewsets, status, permissions
from .models import *
from .serializers import *
from rest_framework.response import Response
from django.db.models import Q
from .permissions import IsAuthenticatedAndOwner, IsTeacher
from django.shortcuts import get_object_or_404
from django.utils.datastructures import MultiValueDictKeyError
from rest_framework.views import APIView
import json
import logging
class TeacherProfile(viewsets.ModelViewSet):
permission_classes = [permissions.IsAuthenticatedOrReadOnly]
lookup_field = "username"
def get_object(self):
if self.action == "partial_update":
return get_object_or_404(User, username=self.kwargs['username'])
return get_object_or_404(Teacher, user__username=self.kwargs['username'])
def get_serializer_class(self):
if self.action == "partial_update":
return UserDetailsSerializer
else:
return TeacherProfileDetails
class TeacherListCreateAPIView(APIView):
logger = logging.getLogger(__name__)
def get(self, request, *args, **kwargs):
teacherList = Teacher.objects.filter(user__username=kwargs["username"])
self.logger.info("Printing teacher list")
self.logger.info(teacherList)
serializers = TeacherProfileDetails(teacherList, many=True)
return Response(serializers.data)
def post(self, request, *args, **kwargs):
self.logger.info("-----------------put ------------")
serializers = TeacherProfileDetails(data=request.data)
# photo = request.FILES['file']
if serializers.is_valid():
serializers.save()
return Response(serializers.data, status=status.HTTP_201_CREATED)
return Response(serializers.errors, status=status.HTTP_400_BAD_REQUEST)
def put(self, request, *args, **kwargs):
serializers = TeacherProfileDetails(data=request.data, many=True)
self.logger.info(serializers)
if serializers.is_valid():
serializers.save()
return Response(serializers.data, status=status.HTTP_201_CREATED)
return Response(serializers.errors, status=status.HTTP_400_BAD_REQUEST)
# /user/<str:username>/profile
class UserProfile(viewsets.ModelViewSet):
permission_classes = [permissions.IsAuthenticatedOrReadOnly]
lookup_field = "username"
def get_object(self):
return get_object_or_404(User, username=self.kwargs['username'])
def get_serializer_class(self):
return UserDetailsSerializer
urls.py
from django.urls import path
from .views import *
urlpatterns = [
path('teacher/<str:username>/profile',
TeacherProfile.as_view({'get': 'retrieve', 'delete': 'destroy', 'patch': 'partial_update'})),
path('teacherlist/<str:username>/',
TeacherListCreateAPIView.as_view(), name="teacher-list"),
]
Getting below error while calling post command to update the user profile
post
http://localhost:8002/api/v1/teacherlist/rayees/
Form json data
{
"teacher_cost": "25.00"
}
Getting below error
IntegrityError at /api/v1/teacherlist/rayees/
null value in column "user_id" violates not-null constraint
DETAIL: Failing row contains (2, null, 25.00, null, null, null).
Request Method: POST
Request URL: http://localhost:8002/api/v1/teacherlist/rayees/
Django Version: 2.2.4
since in model Teacher user is required fields, and you are sending the post request, it will create the new teacher with that user.If you want create new teacher then you should use the post, for that you need the user
if you want update the details of the user you can use patch method, checkout the put method code
class TeacherListCreateAPIView(APIView):
logger = logging.getLogger(__name__)
def get(self, request, *args, **kwargs):
teacherList = Teacher.objects.filter(user__username=kwargs["username"])
self.logger.info("Printing teacher list")
self.logger.info(teacherList)
serializers = TeacherProfileDetails(teacherList, many=True)
return Response(serializers.data)
def post(self, request, *args, **kwargs):
""" creating new user """
serializers = TeacherProfileDetails(data=request.data)
# photo = request.FILES['file']
if serializers.is_valid():
serializer.validated_data['user'] = User.objects.filter(username=kwarsg['username'])
serializers.save()
return Response(serializers.data, status=status.HTTP_201_CREATED)
return Response(serializers.errors, status=status.HTTP_400_BAD_REQUEST)
def patch(self, request, *args, **kwargs):
teacher = TeacherProfileDetails.objects.get(user__username=kwargs['username'])
serializers = TeacherProfileDetails(data=request.data, instance=teacher)
self.logger.info(serializers)
if serializers.is_valid():
serializers.save()
return Response(serializers.data, status=status.HTTP_201_CREATED)
return Response(serializers.errors, status=status.HTTP_400_BAD_REQUEST)
now you can make patch request on http://localhost:8002/api/v1/teacherlist/rayees/
with given data it will update the record.

Updating User model and saving new model - Django

I am trying to save a model by using User model as a ForeignKey, but when I try to save the model I get a RecursionError: maximum recursion depth exceeded.
My code is:
from django.db import models
from django.contrib.auth.models import (User, Group)
from phonenumber_field.modelfields import PhoneNumberField
class AuthenticatorModel(models.Model):
id = models.IntegerField(auto_created=True, default=1, primary_key=True, serialize=False)
user_id = models.ForeignKey(User, related_name='auth_user', null=True)
first_name = models.CharField(default='First Name', max_length=50)
last_name = models.CharField(default='Last Name', max_length=50)
phone_number = PhoneNumberField()
email_id = models.CharField(default='email ID', help_text='Enter the email ID used to register the Django user',
max_length=50)
def save(self, force_insert=False, force_update=False, using=None, update_fields=None):
try:
obj = User.objects.get(id=self.id)
obj2 = AuthenticatorModel.objects.get_or_create(id=self.id)
except User.DoesNotExist:
return
obj.first_name = self.first_name
obj.last_name = self.last_name
obj2.phone_number = self.phone_number
obj.email = self.email_id
obj.save()
return super(AuthenticatorModel, self).save()
I am not sure whats wrong in this. How would I create content for AuthenticatorModel and update first_name, last_name and email?
You are manually calling get_or_create() in the save() method, but get_or_create() itself is also calling save(). There is no need to create obj2, since you are calling the super method at the end.
You could just do this:
def save(...):
try:
obj = User.objects.get(id=self.id)
except User.DoesNotExist:
return
obj.first_name = self.first_name
obj.last_name = self.last_name
obj.email = self.email_id
obj.save()
return super(AuthenticatorModel, self).save()

User has no dcf_profile : RelatedObjectDoesNotExist

After extending an existing user model, I get RelatedObjectDoesNotExist exception with a value User has no dcf_profile. I seems that dcf_profile isn't created automatically for each user.
Please take a look at my model, view and form below and tell me how can I correct my views file?
My models.py :
class CustomUser(models.Model):
auth_user_ptr = models.OneToOneField(
User,
parent_link=True,
related_name='dcf_profile',
primary_key=True
)
phone = models.CharField(_('phone'), max_length=30, null=True, blank=True)
receive_news = models.BooleanField(_('receive news'), default=True, db_index=True)
class Meta:
app_label = 'dcf'
def allow_add_item(self):
if self.item_set.count() > settings.DCF_ITEM_PER_USER_LIMIT:
return False
else:
return True
class Item(models.Model):
slug = models.SlugField(blank=True, null=True, max_length=100)
user = models.ForeignKey(User, on_delete=models.CASCADE)
group = models.ForeignKey(Group, verbose_name=_('group'))
title = models.CharField(_('title'), max_length=100)
description = models.TextField(_('description'))
price = models.DecimalField(_('price'), max_digits=10, decimal_places=2)
phone = models.CharField(_('phone'), max_length=30)
is_active = models.BooleanField(_('display'), default=True, db_index=True)
updated = models.DateTimeField(_('updated'), auto_now=True, db_index=True)
posted = models.DateTimeField(_('posted'), auto_now_add=True)
def __unicode__(self):
return self.title
class Meta:
verbose_name = _('item')
verbose_name_plural = _('items')
ordering = ('-updated', )
def get_absolute_url(self):
return reverse('item', kwargs={
'pk': self.pk,
'slug': self.slug
})
def get_title(self):
return u'%s' % self.title
def get_description(self):
return u'%s' % self.description[:155]
def get_keywords(self):
# TODO need more optimal keywords selection
return ",".join(set(self.description.split()))
def get_related(self):
# TODO Need more complicated related select
return Item.objects.exclude(pk=self.pk)[:settings.DCF_RELATED_LIMIT]
def save(self, *args, **kwargs):
if self.slug is None:
self.slug = slugify(unidecode(self.title))
super(Item, self).save(*args, **kwargs)
My views.py :
class ItemCreateView(FormsetMixin, CreateView):
is_update_view = False
model = Item
form_class = ItemCreateEditForm
formset_class = inlineformset_factory(Item, Image, extra=3, fields=('file', ))
#method_decorator(login_required)
def dispatch(self, *args, **kwargs):
if not self.request.user.dcf_profile.allow_add_item():
messages.error(self.request, _('You have reached the limit!'))
return redirect(reverse('my'))
return super(ItemCreateView, self).dispatch(*args, **kwargs)
def form_valid(self, form, formset):
form.instance.user = self.request.user
form.save()
return super(ItemCreateView, self).form_valid(form, formset)
My forms.py
class ItemCreateEditForm(forms.ModelForm):
class Meta:
model = Item
fields = ('group', 'title', 'description', 'price', 'phone', 'is_active')
Just to share with you a solution that worked, I have created a proxy model of the User model and updated my views.py :
Updated models.py
class DcfUser(User):
class Meta:
proxy = True
def allow_add_item(self):
if self.item_set.count() > settings.DCF_ITEM_PER_USER_LIMIT:
return False
else:
return True
Updated views.py
#method_decorator(login_required)
def dispatch(self, *args, **kwargs):
user = self.request.user
my_user = DcfUser.objects.get(username=user)
if not my_user.allow_add_item():
messages.error(self.request, _('You have reached the limit!'))
return redirect(reverse('my'))
Thank you

How to customize user profile when using django-allauth

I have a django project with the django-allauth app. I need to collect additional data from the user at signup. I came across a similar question here but unfortunately, no one answered the profile customization part.
Per the documentation provided for django-allauth:
ACCOUNT_SIGNUP_FORM_CLASS (=None)
A string pointing to a custom form class (e.g. ‘myapp.forms.SignupForm’) that is used during signup to ask the user for additional input (e.g. newsletter signup, birth date). This class should implement a ‘save’ method, accepting the newly signed up user as its only parameter.
I am new to django and am struggling with this. Can someone provide an example of such a custom form class? Do I need to add a model class as well with a link to the user object like this ?
Suppose you want to ask the user for his first/last name during signup. You'll need to put these fields in your own form, like so:
class SignupForm(forms.Form):
first_name = forms.CharField(max_length=30, label='Voornaam')
last_name = forms.CharField(max_length=30, label='Achternaam')
def signup(self, request, user):
user.first_name = self.cleaned_data['first_name']
user.last_name = self.cleaned_data['last_name']
user.save()
Then, in your settings point to this form:
ACCOUNT_SIGNUP_FORM_CLASS = 'yourproject.yourapp.forms.SignupForm'
Note that SignupForm cannot be defined in the same file as form overrides through ACCOUNT_FORMS or SOCIALACCOUNT_FORMS, because that would lead to a circular import error.
That's all.
Using the solution suggested by pennersr I was getting a DeprecationWarning:
DeprecationWarning: The custom signup form must offer a def signup(self, request, user) method DeprecationWarning)
This is because as of version 0.15 the save method has been deprecated in favour of a def signup(request, user) method.
So to solve this, the code of the example should be like this:
class SignupForm(forms.Form):
first_name = forms.CharField(max_length=30, label='Voornaam')
last_name = forms.CharField(max_length=30, label='Achternaam')
def signup(self, request, user):
user.first_name = self.cleaned_data['first_name']
user.last_name = self.cleaned_data['last_name']
user.save()
Here's what worked for me combining a few of the other answers (none of them are 100% complete and DRY).
In yourapp/forms.py:
from django.contrib.auth import get_user_model
from django import forms
class SignupForm(forms.ModelForm):
class Meta:
model = get_user_model()
fields = ['first_name', 'last_name']
def signup(self, request, user):
user.first_name = self.cleaned_data['first_name']
user.last_name = self.cleaned_data['last_name']
user.save()
And in settings.py:
ACCOUNT_SIGNUP_FORM_CLASS = 'yourapp.forms.SignupForm'
This way it uses the model forms so that it's DRY, and uses the new def signup. I tried putting 'myproject.myapp.forms.SignupForm' but that resulted in a error somehow.
#Shreyas: The below solution may not be the cleanest, but it works. Please let me know if you have any suggestions to clean it up any further.
To add information that does not belong to the default user profile, first create a model in yourapp/models.py. Read the general django docs to learn more about it, but basicly:
from django.db import models
class UserProfile(models.Model):
user = models.OneToOneField(User, related_name='profile')
organisation = models.CharField(organisation, max_length=100, blank=True)
Then create a form in yourapp/forms.py:
from django import forms
class SignupForm(forms.Form):
first_name = forms.CharField(max_length=30, label='Voornaam')
last_name = forms.CharField(max_length=30, label='Achternaam')
organisation = forms.CharField(max_length=20, label='organisation')
def signup(self, request, user):
user.first_name = self.cleaned_data['first_name']
user.last_name = self.cleaned_data['last_name']
# Replace 'profile' below with the related_name on the OneToOneField linking back to the User model
up = user.profile
up.organisation = self.cleaned_data['organisation']
user.save()
up.save()
In your users/forms.py you put:
from django.contrib.auth import get_user_model
class SignupForm(forms.ModelForm):
class Meta:
model = get_user_model()
fields = ['first_name', 'last_name']
def save(self, user):
user.save()
In settings.py you put:
ACCOUNT_SIGNUP_FORM_CLASS = 'users.forms.SignupForm'
In this way you don't break DRY principle by multiplicity User models fields definition.
I've tried many different tutorials and all of them is missing something, repeating unnecessary code or doing weird things, bellow follows my solution that joins all the options that I've found, it's working, I have already put it in production BUT it still not convincing me because I would expect to receive first_name and last_name inside the functions that I attached to Users create to avoid creating a profile inside the form but I couldn't, by the away I think it will help you.
Models.py
class Profile(models.Model):
user = models.OneToOneField(User, on_delete=models.CASCADE)
bio = models.TextField(max_length=500, blank=True)
nationality = models.CharField(max_length=2, choices=COUNTRIES)
gender = models.CharField(max_length=1, choices=GENDERS)
def __str__(self):
return self.user.first_name
#receiver(post_save, sender=User)
def create_user_profile(sender, instance, created, **kwargs):
if created:
Profile.objects.create(user=instance)
#receiver(post_save, sender=User)
def save_user_profile(sender, instance, **kwargs):
instance.profile.save()
Forms.py
class SignupForm(forms.ModelForm):
first_name = forms.CharField(max_length=100)
last_name = forms.CharField(max_length=100)
class Meta:
model = Profile
fields = ('first_name', 'last_name', 'nationality', 'gender')
def signup(self, request, user):
# Save your user
user.first_name = self.cleaned_data['first_name']
user.last_name = self.cleaned_data['last_name']
user.save()
user.profile.nationality = self.cleaned_data['nationality']
user.profile.gender = self.cleaned_data['gender']
user.profile.save()
Settings.py
ACCOUNT_SIGNUP_FORM_CLASS = 'apps.profile.forms.SignupForm'
#models.py
from django.conf import settings
class UserProfile(models.Model):
user = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.CASCADE)
image = models.ImageField(default='users/default.png', upload_to='users')
fields = models.ForeignKey('Field' ,null=True ,on_delete=models.SET_NULL)
category = models.ForeignKey('Category' ,null=True ,on_delete=models.SET_NULL)
description = models.TextField()
interests = models.ManyToManyField('Interests')
...
def save(self, *args, **kwargs):
super().save(*args, **kwargs)
...
def userprofile_receiver(sender, instance, created, *args, **kwargs):
if created:
userprofile = UserProfile.objects.create(user=instance)
else:
instance.userprofile.save()
post_save.connect(userprofile_receiver, sender=settings.AUTH_USER_MODEL)
#forms.py
class SignupForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super(SignupForm, self).__init__(*args, **kwargs)
self.fields['first_name'].widget = forms.TextInput(attrs={'placeholder': 'Enter first name'})
self.fields['last_name'].widget = forms.TextInput(attrs={'placeholder': 'Enter last name'})
first_name = forms.CharField(max_length=100)
last_name = forms.CharField(max_length=100)
interests = forms.ModelMultipleChoiceField(widget=forms.CheckboxSelectMultiple, help_text="Choose your interests", queryset=Interests.objects.all())
image = forms.ImageField(help_text="Upload profile image ")
fields = forms.ChoiceField(help_text="Choose your fields ")
category = forms.ChoiceField(help_text="Choose your category")
class Meta:
model = UserProfile
fields = ('first_name', 'last_name', 'name', 'image', 'fields', 'category', 'description', 'phone', 'facebook', 'twitter', 'skype', 'site', 'address', 'interests' ,'biography')
widgets = {
...
'description': forms.TextInput(attrs={'placeholder': 'Your description'}),
'address': forms.TextInput(attrs={'placeholder': 'Enter address'}),
'biography': forms.TextInput(attrs={'placeholder': 'Enter biography'}),
....
}
def signup(self, request, user):
# Save your user
user.first_name = self.cleaned_data['first_name']
user.last_name = self.cleaned_data['last_name']
user.save()
user.userprofile.image = self.cleaned_data.get('image')
user.userprofile.fields = self.cleaned_data['fields']
user.userprofile.category = self.cleaned_data['category']
user.userprofile.description = self.cleaned_data['description']
interests = self.cleaned_data['interests']
user.userprofile.interests.set(interests)
user.userprofile.save()
# settings.py or base.py
ACCOUNT_SIGNUP_FORM_CLASS = 'nameApp.forms.SignupForm'
That is it. (:
Create a Profile Model with user as OneToOneField
class Profile(models.Model):
user = models.OneToOneField(User, verbose_name=_('user'), related_name='profiles')
first_name=models.CharField(_("First Name"), max_length=150)
last_name=models.CharField(_("Last Name"), max_length=150)
mugshot = ImageField(_('mugshot'), upload_to = upload_to, blank=True)
phone= models.CharField(_("Phone Number"), max_length=100)
security_question = models.ForeignKey(SecurityQuestion, related_name='security_question')
answer=models.CharField(_("Answer"), max_length=200)
recovery_number= models.CharField(_("Recovery Mobile Number"), max_length=100)
city=models.ForeignKey(City,related_name='city', blank=True, null=True, help_text=_('Select your City'))
location=models.ForeignKey(Country,related_name='location', blank=True, null=True, help_text=_('Select your Location'))