본문 바로가기
DEV/Web 개발

Web 개발 :: 파이썬 django 인스타그램 클론 코딩, aullauth _TIL#24

by 올커 2022. 10. 5.

■ JITHub 개발일지 24일차

□  TIL(Today I Learned) ::

django 클론코딩

1. 비밀번호 변경 코드

  - Side navigations bar

<div id="side-navbar">
    <div class="menu" style="margin-top: 40px">
      <div id="nav_div"><a id="nav_a" href="{% url 'profile-update' %}">프로필 편집</a></div>
      <div id="nav_div"><a id="nav_a" href="{% url 'account_change_password' %}">비밀번호 변경</a></div>
      <div id="nav_div"><a id="nav_a" href="{% url 'account_delete' %}">계정 비활성화</a></div>
    </div>
  </div>

  - profile img & name

<!-- Profile img & name -->
    <div class="title" style="width: 100%;height: 70px; padding-left: 120px;float: left;">
      <div class="profile-pic cp-avatar large"
        style="background-image: url('{{ user.profile_image.url }}'); width:40px; height:40px;float: left;"></div>
      <div style="font-size: 25px;float: left;padding-left: 20px;">{{user.username}}</div>
    </div>

 

  - 비밀번호 입력란 : form 템플릿을 사용, 이전 비밀번호, 새비밀번호, 새 비밀번호 확인을 아래와 같은 폼으로 작성하였다.

    전체를 Form 태그로 감싸고 비밀번호 변경은 버튼타입을 submit으로 주어 데이터를 전달하였다.

<!-- contents -->
    <div>
      <form method="post">{% csrf_token %}
        <div style="width: 150px; height:50px;float: left;">
          <p style="font-size: 17px; text-align: right;">이전 비밀번호</p>
        </div>

        <div style="width: 75%; float: left;padding-left:30px">
          <div style="width:450px; height:50px;">
            {{ form.oldpassword|add_class:"form-control"|attr:"placeholder:이전 비밀번호"|add_error_class:"error"}}
            {% for error in form.oldpassword.errors %}
            <div class="error-message">{{ error }}</div>
            {% endfor %}
          </div>
        </div>
        
        ...
        <div style="width: 100%;min-width: 500px; height: 200px; float: left;padding: 20px 0px 0px 180px">
          <div>
            <button type="submit" class="btn btn-primary"
              style="margin-bottom:20px;background-color:rgb(0, 149, 247);">비밀번호 변경</button>
            <br>
          </div>
          <a href="{% url 'account_reset_password' %}" style="text-decoration : none;color:rgb(0, 149, 247)">비밀번호를
            잊으셨나요?</a>
        </div>
      </form>

※ models.py

from django.db import models
from django.contrib.auth.models import AbstractUser 
from .validators import validate_no_special_characters #유효성 검사 커스터마이징 import

# Create your models here.
#User model에서 username과 profile_image, intro, following 정의
class User(AbstractUser):
    username = models.CharField(
        max_length=15, #최대 15자
        unique=True, #중복 허용 x
        null=True, #null값 허용
        validators=[validate_no_special_characters], #비밀번호 유효성 검사 
        error_messages={"unique":"이미 사용중인 닉네임입니다."}, #중복일 때 error메시지 뜨게함
        )
    
    profile_image = models.ImageField(
        default="default_profile_pic.jpg",upload_to="profile_pics" 
        )
    
    intro = models.CharField(max_length=60, blank=True)
    
    following = models.ManyToManyField('self', symmetrical=False, blank=True, related_name= 'followers')
    
    def __str__(self):
        return self.email

 

2. 회원 정보 변경 코드

<!-- contents -->
    <div>
      <form method="post" enctype="multipart/form-data" autocomplete="off">{% csrf_token %}

        <div style="width: 150px; height:50px;float: left;">
          <p style="font-size: 17px; text-align: right;">이름</p>
        </div>

        <div style="width: 75%; float: left;padding-left:30px">
          <div class="mb-3" style="width:450px; height:50px;">
            {{ form.username|add_class:"form-control"|attr:"placeholder:이름"|attr:"style:width:300px"|add_error_class:"error"}}
          {% for error in form.username.errors %}
          <div class="error-message">{{ error }}</div>
          {% endfor %}
          </div>

        </div>

        <div style="width: 150px; height:50px; float: left;">
          <p style="font-size: 17px; text-align: right;">프로필 사진</p>
        </div>

        <div style="width: 75%; float: left;padding-left:30px">
          <div type="file">
            {{ form.profile_image}}
          </div>

        </div>
        
        
        <div style="width: 150px; height:50px; float: left;">
          <p style="font-size: 17px; text-align: right;margin-top: 30px">소개</p>
        </div>
        
        <div class="mb-3"style="width: 75%; float: left;margin-top: 30px; padding-left:30px">
          {{ form.intro|add_class:"form-control"|add_error_class:"error"|attr:"placeholder:소개"|attr:"rows:3" }}
          {% for error in form.intro.errors %}
          <div class="error-message">{{ error }}</div>
          {% endfor %}
        </div>


        <div style="width: 100%;min-width: 500px; height: 200px; float: left;padding:0px 0px 0px 180px">
          <div class="buttons">
            <button type="submit" class="btn btn-primary"
            style="margin-bottom:20px;background-color:rgb(0, 149, 247);width: 80px">제출</button>
            <button onclick="{% url 'profile' user.id %}" class="btn btn-secondary"
            style="margin-bottom:20px;;width: 80px">취소</button>
          </div>
        </div>
      </form>

    </div>

 

※ forms.py

from django import forms
from .models import Post, Comment
from user.models import User

from django.contrib.auth.hashers import check_password

#PostForm
class PostForm(forms.ModelForm):
    class Meta:
        model = Post
        fields = [
            "image",
            "content",
        ]

#ProfileForm
class ProfileForm(forms.ModelForm):
    class Meta:
        model = User
        fields = [
            "username",
            "profile_image",
            "intro",
        ]
        widgets = {
            "intro": forms.Textarea,
        }

#Form
class CommentForm(forms.ModelForm):
    class Meta:
        model = Comment
        fields = [
            'content',
        ]
        
        widgets = {
            'content': forms.TextInput,
        }

※  urls.py

#profile urls
    path("users/<int:user_id>/", views.ProfileView.as_view(), name="profile"),
    path("set-profile/",views.ProfileSetView.as_view(), name="profile-set"),
    path("edit-profile/",views.ProfileUpdateView.as_view(), name="profile-update"),

※ views.py

#profile 수정
class ProfileUpdateView(LoginRequiredMixin, UpdateView):
    model = User
    form_class = ProfileForm
    template_name = "post/profile_update_form.html"
    
    def get_object(self, queryset=None):
        return self.request.user
    
    def get_success_url(self):
        return reverse("profile", kwargs=({"user_id": self.request.user.id}))

 


□  TIF(Today I Felt) ::

  - 장고를 활용하여 인스타 클론코딩을 진행중이다.

  - 아직 어려운 점들이 너무 많다. 프로젝트 마치고서라도 다시 코드에 대한 복기가 필요할 듯 하다.

 

반응형

댓글