from django.db import models
from django.contrib.auth.models import AbstractUser
class CustomUser(AbstractUser):
email = models.EmailField()
self_prove = models.CharField(max_length=50)
self_prove_answer = models.CharField(max_length=50)
def __str__(self):
return self.username
AbstractUser와 AbstractBaseUser는 장고에서 제공하는 User model이다. 둘의 차이점은 AbstractUser는 User model이 제공하는 field를 사용하면서 새로운 fields, function을 추가를 시킬 수 있는 것이고 AbstractBaseUser는 처음부터 끝까지 작성해야되는 empty model이라고 생각하면 된다.
AbstractBaseUser에서 상속 가능한 요소
AbstractUser에서는 기본적으로 AbstractBaseUser 외 추가적인 요소를 상속할 수 있다.
해당 프로젝트에서는 AbstractUser model을 기본으로 사용하고 필요한 데이터(email, 본인확인질문, 답)를 추가하는 것으로 결정했다.
AbstractUser를 상속받았을 경우, settings.py에 아래 코드를 추가해줘야 한다.
AUTH_USER_MODEL = 'appname.modelName'
회원가입 시스템을 만들때 필요한 form을 app폴더에 form.py를 만들어서 작성한다
장고에는 기본적으로 제공하는 회원가입 form인 UserCreationForm이 존재한다.
username
password1
password2
validate_password()를 통해 password 적합성을 체크한다
set_password()를 통해 적합한 password를 설정한다.
기본 form을 유지하고 추가적으로 field를 더하기 위해 UserForm을 새로 만들어 줄 수 있다. Form을 통해 유저들이 html에 데이터를 입력할 수 있게 된다.
class UserForm(UserCreationForm):
last_name = forms.CharField(label="성")
first_name = forms.CharField(label="이름")
email = forms.EmailField(label="이메일")
self_prove = forms.CharField(label='본인인증 질문')
self_prove_answer = forms.CharField(label='본인인증 질문 정답')
class Meta:
model = CustomUser
fields = (
"username",
"last_name",
"first_name",
"password1",
"password2",
"email",
"self_prove",
"self_prove_answer"
)
def save(self):
user = super(UserForm, self).save(commit=False)
user.save()
try:
student = Group.objects.get(name='student')
student.user_set.add(user)
except Group.DoesNotExist:
student = Group.objects.create(name='student')
student.user_set.add(user)
return
class Meta에는 fields 외의 것을 수정, 작성할 때 사용되는 class이다.
Form 작성 이후에는 해당 form과 UserManager작성이 가능하나 장고에서 기본적으로 제공하는 것이 충분하여서 따로 커스터마이징을 하지 않았다.
def signup(request):
if request.method == 'POST': # request 들어온 것이 post방식이면
if request.POST['teacher_code'] in ['A0001', 'A0002']:
form = StaffForm(request.POST)
else:
form = UserForm(request.POST) # form에 UserForm post version으로 저장한다
if form.is_valid(): # form이 valid하면
form.save()
return redirect('../login')
else:
form = UserForm() # 계정 생성 화면 리턴
return render(request, './common/signup.html', {'form': form})
<div class="container my-3">
<div class="row my-3">
<div class="col-4">
<h4>계정생성</h4>
</div>
</div>
<form method="post" class="post-form" action="{% url 'common:signup' %}">
{% csrf_token %}
<div class="form-group">
<label for="username">아이디</label>
<input type="text" class="form-control" name="username" id="username"
value="{{ form.username.value|default_if_none:'' }}">
</div>
<div class="form-group">
<label for="password1">비밀번호</label>
<input type="password" class="form-control" name="password1" id="password1"
value="{{ form.password1.value|default_if_none:'' }}">
</div>
<div class="form-group">
<label for="password2">비밀번호 재확인</label>
<input type="password" class="form-control" name="password2" id="password2"
value="{{ form.password2.value|default_if_none:'' }}">
</div>
<div class="form-group">
<label for="last_name">성(Last Name)</label>
<input type="text" class="form-control" name="last_name" id="last_name"
value="{{ form.last_name.value|default_if_none:'' }}"> <div class="form-group">
</div>
<label for="first_name">이름(First Name)</label>
<input type="text" class="form-control" name="first_name" id="first_name"
value="{{ form.first_name.value|default_if_none:'' }}">
</div>
<div class="form-group">
<label for="email">이메일</label>
<input type="text" class="form-control" name="email" id="email"
value="{{ form.email.value|default_if_none:'' }}">
</div>
<div class="form-group">
<label for="teacher_code">강사코드</label>
<input type="text" name="teacher_code" id="teacher_code" value="강사님만 입력">
</div>
<input type="submit" value="가입하기">
<input type="button" onclick="location.href='{% url 'common:login' %}'" value="login화면으로">
</form>
</div>
위의 코드는 로그인 Form을 HTML로 구현한 코드이다. 이를 꾸며주는 CSS는 보다 나은 설명을 위해 잠시 빼두었다.
<form id="registerForm" method="post" action="{% url 'common:signup' %}">
{% csrf_token %}
{% include "form_errors.html" %}
클라이언트와 서버는 서로 http프로토콜의 GET과 POST를 사용하여 데이터를 주고 받는다.
이때, 클라이언트가 서버로 데이터를 보낼 때 간편하게 사용 가능한 것이 Form이다. Form으로 사용자로부터 데이터를 수집하여 서버에 보내는 형식으로 사용된다.
위 코드의 의미는,
아래 구현된 코드로 이용자에게 정보를 받아 POST방식으로 common 앱의 signup이라는 이름이 주어진 URL에 보낸다는 의미이다.<div class="form-group">
<label for="username">아이디</label>
<input type="text" class="form-control" name="username" id="username"
value="{{ form.username.value|default_if_none:'' }}">
</div>
<input type="submit" value="가입하기">
해당 form에 필요한 input을 이용자가 작성 가능하게끔 구현한 코드이다. 해당 코드의 input데이터는 text형식으로 데이터를 받아와 username이라 명명하고 id를 주는 코드이다. 데이터 입력 완료 후, 가입하기 버튼을 누르면 form을 제출하게끔 되어 있다.