django-volt-dashboard
django-volt-dashboard copied to clipboard
Creating a working form based on the vanilla profile settings page for Volt Django
Hi - I am working to build a vanilla profile page from the settings.html template in Volt Django Pro.
I think that you have a different app for user profile, but I prefer a cleaner form. The page has profile Save input, photos input, and another form also so I wondered how best to code the forms to work with your users' authentication assumptions.
If I build a simple views, forms, and models from your template, I get no error on clicking save, but no data is saved and returned to the form
views.py def is as follows:
def profile(request):
if request.method == 'POST':
form = ProfileNewForm(request.POST)
if form.is_valid():
form.save()
return redirect('pages/apps/profile.html') # Replace with your URL
else:
form = ProfileNewForm()
context = {
'parent' : 'account',
'segment' : 'profile',
'form': form
}
return render(request, 'pages/apps/profile.html', context)
I also tried the following without success ...
def profile(request):
profile = get_object_or_404(Profile, user=request.user)
form = ProfileNewForm(instance=profile)
if request.method == 'POST':
if request.POST.get('email'):
request.user.email = request.POST.get('email')
request.user.save()
for attribute, value in request.POST.items():
print (attribute, value)
if attribute == 'csrfmiddlewaretoken':
continue
setattr(profile, attribute, value)
profile.save()
messages.success(request, 'Profile updated successfully')
return redirect(request.META.get('HTTP_REFERER'))
context = {
'segment': 'profile',
'parent' : 'account',
'form': form,
# 'sales': sales,
}
return render(request, 'pages/apps/profile.html', context)
with users/forms.py:
class ProfileNewForm(forms.ModelForm):
class Meta:
model = Profile
exclude = ('role', 'avatar', 'bio')
def __init__(self, *args, **kwargs):
super(ProfileNewForm, self).__init__(*args, **kwargs)
for field_name, field in self.fields.items():
self.fields[field_name].widget.attrs['placeholder'] = field.label
self.fields[field_name].widget.attrs['class'] = 'form-control'
self.fields[field_name].widget.attrs['required'] = False
# def __str__(self):
# return f"{self.first_name} {self.last_name}"
def get_full_name(self):
return f"{self.first_name} {self.last_name}"
def get_short_name(self):
return self.first_name
and models.py:
class Profile(models.Model):
user = models.OneToOneField(User, on_delete=models.CASCADE)
role = models.CharField(max_length=20, choices=ROLE_CHOICES, default='user')
first_name = models.CharField(max_length=26, null=True, blank=True)
last_name = models.CharField(max_length=32, null=True, blank=True)
full_name = models.CharField(max_length=60, null=True, blank=True)
title = models.CharField(max_length=90, null=True, blank=True)
birthday = models.DateField(null=True, blank=True)
country = models.CharField(max_length=255, null=True, blank=True)
city = models.CharField(max_length=255, null=True, blank=True)
zip_code = models.CharField(max_length=255, null=True, blank=True)
address = models.CharField(max_length=255, null=True, blank=True)
phone = models.CharField(max_length=255, null=True, blank=True)
avatar = models.ImageField(upload_to=avatar_with_id, null=True, blank=True)
bio = QuillField(default=convert_to_quill())
gender = models.CharField(max_length=10, choices=[
('male', 'Male'),
('female', 'Female'),
], null=True, blank=True)
greeting = models.CharField(max_length=10, choices=[
('Mr', 'Mr.'),
('Mrs', 'Mrs.'),
('Ms', 'Ms.'),
('doctor', 'Dr.'),
], null=True, blank=True)
def __str__(self):
return self.user.username
Profile.html 👍
<div class="row">
<div class="col-12 col-xl-8">
<div class="card card-body border-0 shadow mb-4">
<h2 class="h5 mb-4">General information</h2>
<form method="POST" action="{%url 'profile' %}">
{% csrf_token %}
{{ profile_form.as_p }}
<div class="row">
<div class="col-md-6 mb-3">
<div>
<label for="first_name">First Name</label>
<input class="form-control" id="first_name" type="text" placeholder="Enter your first name" required>
</div>
</div>
<div class="col-md-6 mb-3"> ... etc...