Registro Django

Resumo : neste tutorial, você aprenderá como criar um formulário de registro do Django que permite aos usuários se inscreverem.

Este tutorial começa onde o  tutorial de login/logout do Django  parou.

Criando um formulário de registro do Django

Primeiro, defina uma URL de registro no urls.pyaplicativo users:

from django.urls import path
from . import views

urlpatterns = [
    path('login/', views.sign_in, name='login'),
    path('logout/', views.sign_out, name='logout'),
    path('register/', views.sign_up, name='register'),
]
Linguagem de código:  Python  ( python )

Segundo, defina uma RegisterFormclasse no forms.pyarquivo users.py:

from django import forms
from django.contrib.auth.models import User
from django.contrib.auth.forms import UserCreationForm


class LoginForm(forms.Form):
    username = forms.CharField(max_length=65)
    password = forms.CharField(max_length=65, widget=forms.PasswordInput)
    

class RegisterForm(UserCreationForm):
    class Meta:
        model=User
        fields = ['username','email','password1','password2'] 
   
Linguagem de código:  Python  ( python )

O RegisterFormusa o modelo integrado Usere inclui quatro campos, incluindo username, email, password1e password2, que o usuário precisa preencher para registro.

Terceiro, defina a sign_up()função de visualização no views.pyaplicativo users:

from django.shortcuts import render, redirect
from django.contrib import messages
from django.contrib.auth import login, authenticate, logout
from .forms import LoginForm, RegisterForm

def sign_up(request):
    if request.method == 'GET':
        form = RegisterForm()
        return render(request, 'users/register.html', { 'form': form})   
Linguagem de código:  Python  ( python )

A sign_up()função view cria o RegisterFormobjeto e o renderiza no register.htmlmodelo.

Quarto, crie um register.htmlmodelo no templates/usersdiretório da usersaplicação:

{% extends 'base.html' %}

{% block content %}

<form method="POST" novalidate>
	{% csrf_token %}
	<h2>Sign Up</h2>
	{{ form.as_p }}		
	<input type="submit" value="Register" />
</form>

{% endblock content%}Linguagem de código:  HTML, XML  ( xml )

O registerl.htmlestende o base.htmlmodelo do projeto. Ele renderiza o RegisterForm(formulário).

Observe que a novalidatepropriedade remove a validação HTML5. Depois de concluir o projeto, você pode remover esta propriedade para habilitar a validação HTML5.

Por fim, abra o URL de registro:

http://127.0.0.1:8000/register/Linguagem de código:  texto simples  ( texto simples )

…você verá o formulário de registro da seguinte forma:

formulário de registro djang - padrão

Personalize o formulário de registro do Django

O formulário de inscrição possui quatro campos com muitas informações. Essas informações vêm do Usermodelo padrão.

Se quiser personalizar as informações exibidas no formulário, você pode modificar o register.htmlmodelo da seguinte forma:

{% extends 'base.html' %}

{% block content %}
<form method="POST" novalidate>
	{% csrf_token %}
	<h2>Sign Up</h2>
		
	{% for field in form %}
	<p>
		{% if field.errors %}
		<ul class="errorlist">
			{% for error in field.errors %}
			<li>{{ error }}</li>
			{% endfor %}
		</ul>
		{% endif %}
	 	{{ field.label_tag }} {{ field }}
	</p>
	{% endfor %}
	<input type="submit" value="Register" />
</form>
{% endblock content%}Linguagem de código:  HTML, XML  ( xml )

O modelo itera nos campos do formulário e gera cada campo individualmente. Para cada campo, exibe a lista de erros caso a validação falhe.

O novo formulário ficará assim:

formulário de registro djang - personalizar

Se você preencher as informações e clicar em registrar, receberá um erro porque não adicionamos o código que trata a solicitação HTTP POST.

Lidando com a lógica de registro

Para lidar com a solicitação HTTP POST, você modifica a sign_up()função no views.pyarquivo do usersaplicativo:

def sign_up(request):
    if request.method == 'GET':
        form = RegisterForm()
        return render(request, 'users/register.html', {'form': form})    
   
    if request.method == 'POST':
        form = RegisterForm(request.POST) 
        if form.is_valid():
            user = form.save(commit=False)
            user.username = user.username.lower()
            user.save()
            messages.success(request, 'You have singed up successfully.')
            login(request, user)
            return redirect('posts')
        else:
            return render(request, 'users/register.html', {'form': form})
Linguagem de código:  Python  ( python )

Como funciona.

Primeiro, crie uma nova instância do RegisterForm:

form = RegisterForm(request.POST)Linguagem de código:  Python  ( python )

Se o formulário for válido, salvamos o formulário, mas não o armazenamos imediatamente no banco de dados. Isso é feito passando o argumento commit=Falsepara o save()método do objeto de formulário.

O motivo é que queremos deixar o nome do usuário em letras minúsculas antes de salvá-lo no banco de dados:

user.username = user.username.lower()
user.save()Linguagem de código:  Python  ( python )

Após salvar o usuário, criamos uma mensagem flash , logamos o usuário e o redirecionamos para a página da lista de postagens:

messages.success(request, 'You have singed up successfully.')
login(request, user)
return redirect('posts')Linguagem de código:  Python  ( python )

Se o formulário não for válido, renderizamos novamente o formulário com os valores inseridos anteriormente, passando o objeto form para a render()função:

return render(request, 'users/register.html', {'form': form})Linguagem de código:  Python  ( python )

O exemplo a seguir ilustra como inscrever um usuário com o nome de usuário jane:

Adicionando os links

Primeiro, inclua o link de registro modificando o base.htmlmodelo. Além disso, inclua os links My Postse New Postse o usuário estiver logado:

{%load static %}
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <link rel="stylesheet" href="{% static 'css/style.css' %}" />
    <script src="{% static 'js/app.js' %}" defer></script>
    <title>My Site</title>
  </head>
  <body>
  	<header>
  		{%if request.user.is_authenticated %}
  			<a href="{% url 'posts' %}">My Posts</a>
  			<a href="{% url 'post-create' %}">New Post</a>
  			<span>Hi {{ request.user.username | title }}</span>
  			<a href="{% url 'logout' %}">Logout</a>
  		{%else%}
  			<a href="{% url 'login' %}">Login</a>
  			<a href="{% url 'register' %}">Register</a>
  		{%endif%}
  	</header>
  	<main>
	  	{% if messages %}
			<div class="messages">
			{% for message in messages %}
				<div class="alert {% if message.tags %}alert-{{ message.tags }}"{% endif %}>
					{{ message }}
				</div>
			{% endfor %}
			</div>
		{% endif %}
		    
	    {%block content%} 
	    {%endblock content%}
  	</main>
	
  </body>
</html>
Linguagem de código:  HTML, XML  ( xml )

Segundo, inclua o link de registro no login.htmlmodelo:

{% extends 'base.html' %}

{% block content %}
<form method="POST" novalidate>
	{% csrf_token %}
	<h2>Login</h2>
	{{form.as_p}}
	<input type="submit" value="Login" />
	<p>Don't have an account? <a href="{%url 'register' %}">Register</a></p>
</form>

{% endblock content%}
Linguagem de código:  HTML, XML  ( xml )

Terceiro, adicione o link de login à register.htmlpágina:

{% extends 'base.html' %}

{% block content %}
<form method="POST" novalidate>
	{% csrf_token %}
	<h2>Sign Up</h2>
		
	{% for field in form %}
	<p>
		{% if field.errors %}
		<ul class="errorlist">
			{% for error in field.errors %}
			<li>{{ error }}</li>
			{% endfor %}
		</ul>
		{% endif %}
	 	{{ field.label_tag }} {{ field }}
	</p>
	{% endfor %}
	<input type="submit" value="Register" />
	<p>Already has an account? <a href="{%url 'login' %}">Login</a></p>
</form>
{% endblock content%}
Linguagem de código:  HTML, XML  ( xml )

Impedir que um usuário edite/exclua postagens de outros usuários

Normalmente, um usuário não deve poder editar ou excluir uma postagem de outros usuários. No entanto, o usuário pode visualizar as postagens de outros usuários.

Para implementar esta função, precisamos verificar se o autor da postagem é o mesmo do usuário logado no momento. Se sim, renderizamos os formulários de edição/exclusão. Caso contrário, podemos redirecionar os usuários para uma página 404.

Além disso, precisamos ocultar os links de edição e exclusão da página da lista de postagens se as postagens não pertencerem ao usuário.

Primeiro, modifique o views.pydo blogaplicativo:

from django.shortcuts import render,redirect, get_object_or_404
from django.contrib import messages
from django.contrib.auth.decorators import  login_required
from .models import Post
from .forms import PostForm

@login_required
def delete_post(request, id):
    queryset = Post.objects.filter(author=request.user)
    post = get_object_or_404(queryset, pk=id)
    context = {'post': post}    
    
    if request.method == 'GET':
        return render(request, 'blog/post_confirm_delete.html',context)
    elif request.method == 'POST':
        post.delete()
        messages.success(request,  'The post has been deleted successfully.')
        return redirect('posts')        

@login_required    
def edit_post(request, id):
    queryset = Post.objects.filter(author=request.user)
    post = get_object_or_404(queryset, pk=id)

    if request.method == 'GET':
        context = {'form': PostForm(instance=post), 'id': id}
        return render(request,'blog/post_form.html',context)
    
    elif request.method == 'POST':
        form = PostForm(request.POST, instance=post)
        if form.is_valid():
            form.save()
            messages.success(request, 'The post has been updated successfully.')
            return redirect('posts')
        else:
            messages.error(request, 'Please correct the following errors:')
            return render(request,'blog/post_form.html',{'form':form})

@login_required
def create_post(request):
    if request.method == 'GET':
        context = {'form': PostForm()}
        return render(request,'blog/post_form.html',context)
    elif request.method == 'POST':
        form = PostForm(request.POST)
        if form.is_valid():
            form.save()
            messages.success(request, 'The post has been created successfully.')
            return redirect('posts')
        else:
            messages.error(request, 'Please correct the following errors:')
            return render(request,'blog/post_form.html',{'form':form})          
    

def home(request):
    posts = Post.objects.all()
    context = {'posts': posts  }
    return render(request,'blog/home.html', context)   
Linguagem de código:  Python  ( python )

Tanto em delete quanto em update, filtramos a postagem pelo usuário atual antes de passá-la para a get_object_or_404()função.

Se você fizer login como Jane e tentar editar uma postagem que não pertence a Jane, receberá um erro 404. Por exemplo:

A página 404:

Segundo, modifique o home.htmlmodelo para ocultar os links de edição e exclusão.

{% extends 'base.html' %}
	
{% block content %}
<h1>My Posts</h1>
	{% for post in posts %}
		<h2>{{ post.title }}</h2>
		<small>Published on {{ post.published_at | date:"M d, Y" }} by {{ post.author | title}}</small>
		<p>{{ post.content }}</p>
		
		{% if request.user.is_authenticated and request.user == post.author %}
		<p>
			<a href="{% url 'post-edit' post.id %}">Edit</a> 
			<a href="{% url 'post-delete' post.id%}">Delete</a>
		</p>
		{% endif %}
		
	{% endfor %}
{% endblock content %}Linguagem de código:  HTML, XML  ( xml )

Removendo o autor do formulário de criação de postagem

Primeiro, remova o authorcampo da fieldsclasse PostForm:

from django.forms import ModelForm
from .models import Post

class PostForm(ModelForm):
    class Meta:
        model = Post
        fields = ['title','content']    
Linguagem de código:  Python  ( python )

O formulário pós-criação ficará assim:

Segundo, modifique a create_post()função no views.pyaplicativo blogpara atualizar o autor da postagem para o usuário conectado no momento:

@login_required
def create_post(request):
    if request.method == 'GET':
        context = {'form': PostForm()}
        return render(request,'blog/post_form.html',context)
    elif request.method == 'POST':
        form = PostForm(request.POST)
        if form.is_valid():
            user = form.save(commit=False)
            user.author = request.user
            user.save()
            messages.success(request, 'The post has been created successfully.')
            return redirect('posts')
        else:
            messages.error(request, 'Please correct the following errors:')
            return render(request,'blog/post_form.html',{'form':form})  
Linguagem de código:  Python  ( python )

Resumo

  • Subclasse de UserCreationFormpara criar um formulário de registro personalizado do Django.

Deixe um comentário

O seu endereço de email não será publicado. Campos obrigatórios marcados com *