Pfft ... Bancos de dados de novo?
Existem três relacionamentos principais em um banco de dados relacional:
- Relacionamento um para um;
- Relacionamento um-para-muitos;
- Relacionamento muitos para muitos.
Neste artigo, trataremos do primeiro deles, o relacionamento um-para-um.
Normalmente Django já tem um modelo de usuário que vem com o framework. Ele vem com seus próprios campos, métodos, atributos, etc. A desvantagem desse modelo de usuário é que ele não permite que você adicione campos personalizados além dos padrões já fornecidos no Django. Isso pode ser um problema sério, pois um desenvolvedor pode precisar configurar completamente um perfil de usuário / cliente de um grupo de usuários autenticados. Por exemplo, um site de blog pode precisar de um perfil de autor, que incluirá a foto do usuário, endereço de contato, hobby, nicho, etc. E o modelo de usuário que vem com o Django não permite isso.
Para resolver este problema, os desenvolvedores criam um modelo de perfil customizado e o conectam ao modelo de usuário padrão no Django usando um relacionamento um-para-um. Acontece que o usuário tem a garantia de estar conectado a um perfil e vice-versa. Além disso, essa mecânica permite um melhor controle sobre a personalização do modelo de perfil.
Agora vou mostrar como você pode fazer isso no Django.
1. Use o modelo de usuário Django padrão
No aplicativo onde você deseja criar um perfil, crie um novo arquivo forms.py . Em forms.py, importe os seguintes módulos:
from django.contrib.auth.forms import UserCreationForm
from django.contrib.auth.models import User
Crie uma classe para herdar
UserCreationForm. Dentro desta classe, crie outra metaclasse que terá duas variáveis: modele fields. A variável modelconterá seu modelo de usuário e a variável conterá os fieldscampos do formulário que serão criados.
class createUserForm(UserCreationForm):
class meta:
model = User
fields = ['username', 'password1', 'password2']
O código acima irá criar um formulário com campos para nome de usuário, senha e confirmação de senha.
2. Crie seu modelo de perfil de usuário personalizado.
Em seu arquivo models.py, importe o modelo de usuário padrão.
from django.contrib.auth.models import User
Em seguida, você precisa criar seu próprio modelo de perfil e também criar um campo de usuário com um relacionamento um-para-um com o modelo de usuário padrão no Django.
class Profile(models.Model):
user = models.OneToOneField(User, on_delete=models.CASCADE, null=True,)
name = models.CharField(max_length=200, null=True)
email = models.CharField(max_length=200, null=True)
address = models.CharField(max_length=200, null=True)
def __str__(self):
return self.name
3. Crie uma forma para seu modelo de perfil.
Abra o arquivo form.py e importe seu modelo de perfil de models.py , adicione também algumas outras importações que são úteis ao criar seu formulário de perfil.
from django import forms
from django.utils.translation import ugettext_lazy as _
from .models import Profile
Em seguida, crie uma classe que herdará de
forms.ModelForm. Nesta classe, crie outra metaclasse contendo duas variáveis: modele fields. A variável modelcontém o modelo de perfil e fieldsos campos do formulário que serão criados.
class profileForm(forms.ModelForm):
class Meta:
model = Profile
fields = ['name', 'email', 'address']
#The labels attribute is optional. It is used to define the labels of the form fields created
labels = {
"name": _("Name "),
"email": _("Email Address"),
"address": _("Street Address"),
}
Agora que os formulários estão prontos, definiremos a lógica em views.py antes de renderizá-la aos nossos modelos.
4. Adicione a lógica a views.py .
Para trabalhar com formulários criados em forms.py, você precisa importá-los em nosso views.py e adicionar mais alguns módulos que serão úteis para a criação de lógica.
from django.shortcuts import render, redirect
from django.contrib.auth import authenticate, login,
from django.contrib import messages
from .models import Profile
from .forms import createUserForm, profileForm
Agora vamos criar uma página de registro. Vamos apenas chamá-lo de registerPage . Vamos criar um dicionário de contexto vazio e retornar a renderização.
def registerPage(request):
context = {}
return render(request, 'app_name/register.html', context)
Vamos atribuir valores do formulário a variáveis chamando o método POST. Em seguida, passaremos as variáveis para o dicionário de contexto.
def registerPage(request):
if request.method == 'POST':
form = createUserForm(request.POST)
profile_form = profileForm(request.POST)
context = {'form': form, 'profile_form': profile_form}
return render(request, 'app_name/register.html', context)
Então iremos validar ambos os formulários e salvá-los posteriormente.
def registerPage(request):
if request.method == 'POST':
form = createUserForm(request.POST)
profile_form = profileForm(request.POST)
if form.is_valid() and profile_form.is_valid():
user = form.save()
#we don't save the profile_form here because we have to first get the value of profile_form, assign the user to the OneToOneField created in models before we now save the profile_form.
profile = profile_form.save(commit=False)
profile.user = user
profile.save()
context = {'form': form, 'profile_form': profile_form}
return render(request, 'app_name/register.html', context)
Se os valores do formulário forem validados e salvos, exibiremos uma mensagem de sucesso e redirecionaremos o usuário para a página de login.
def registerPage(request):
if request.method == 'POST':
form = createUserForm(request.POST)
profile_form = profileForm(request.POST)
if form.is_valid() and profile_form.is_valid():
user = form.save()
#we don't save the profile_form here because we have to first get the value of profile_form, assign the user to the OneToOneField created in models before we now save the profile_form.
profile = profile_form.save(commit=False)
profile.user = user
profile.save()
messages.success(request, 'Your account has been successfully created')
return redirect('login')
context = {'form': form, 'profile_form': profile_form}
return render(request, 'app_name/register.html', context)
5. Renderize o modelo
No arquivo,
register.htmlcrie uma tag de formulário usando o método POST e actioncom um valor de string vazio. Na tag de formulário csrf_token, colocaremos no formato de template django, e então iremos renderizar dinamicamente os formulários (formulários de usuário e perfil). Além disso, não vamos esquecer o botão de envio.
<form method="POST" action="">
{% csrf_token %}
<h3>Register Profile</h3>
<div class="form-field">
{{profile_form.name.label_tag}}
{{profile_form.name}}
</div>
<div class="form-field">
{{form.username.errors}}
{{form.username.label_tag}}
{{form.username}}
</div>
<div class="form-field">
{{profile_form.email.label_tag}}
{{profile_form.email}}
</div>
<div class="form-field">
{{profile_form.address.label_tag}}
{{profile_form.address}}
</div>
<div class="form-field">
{{form.password1.errors}}
{{form.password1.label_tag}}
{{form.password1}}
</div>
<div class="form-field">
{{form.password2.errors}}
{{form.password2.label_tag}}
{{form.password2}}
</div>
<hr>
<input id="form-button" class="btn btn-success btn-block" type="submit" value="Create Profile">
<br>
{{form.non_field_errors}}
<p>Already have an account? <a href="{% url 'login' %}">Login</a></p>
</form>
Como após preencher o formulário, validá-lo e salvá-lo, redirecionamos para a página de login, uma mensagem sobre o sucesso da operação será exibida na página de login no canto inferior direito antes da inscrição “Não tem conta? Cadastre-se " .
<form method="POST" action="">
...
<hr>
<input id="form-button" class="btn btn-success btn-block" type="submit" value="Login">
{% for message in messages %}
<p>{{message}}</p>
{% endfor %}
<p>Don't have an account? <a href="{% url 'store:register' %}">Register</a></p>
</form>
É assim que você cria um modelo de perfil para seu site que está vinculado ao seu modelo de usuário em uma relação um para um.