django에서 제공하는 Form 기능에 대해 알아보려고 합니다.
앞서 우리는 로그인 폼을 직접 작성(로그인 과정)하였습니다.
하지만 django에서는 폼의 하위요소를 HTML로 직접 작성하지 않고 django에서 지원하는 기능을 이용하여 폼 요소를 생성하고 각 폼으로 부터 전달되는 값을 검사할 수 있는 기능을 갖고 있습니다.
앞선 로그인 폼을 django에서 지원하는 기능을 이용하여 작성하여 봅시다.
애플리케이션 하위에 loginForm.py라는 이름으로 다음을 만들어 봅시다.
- loginForm.py
- # -*- coding: utf-8 -*-
from django import forms
class LoginForm(forms.Form):
username = forms.CharField(label='사용자 이름', max_length=30, required=True)
password = forms.CharField(label='암호', widget=forms.PasswordInput(), required=True, max_length=127)
생긴 형태가 마치 데이터 모델과 닮았습니다. 하지만 실제 사용되는 것은 많이 다릅니다.
django의 Form은 HTML Form 에 대한 wrapper 클래스를 지원합니다.
자주 사용되는 django Form필드는 forms에 의해 정의되며 다음과 같습니다.
- CharField : 문자열, 기본 widget : Textinput
- IntegerField : 숫자, 기본 widget : Textinput
- DateField : 파이썬의 datetime.date 객체, 기본 widget : Textinput
- DateTimeField : 파이썬의 datetime.datetime 객체, 기본 widget : Textinput
- EmailField : 형식이 정확한 이메일 주소, 기본 widget : Textinput
- URLField : 형식이 정확한 URL, 기본 widget : Textinput
- 참고 : http://docs.djangoproject.com/en/1.2/ref/forms/fields/#ref-forms-fields
사용자로부터 전달될 내용이 위와 같을 경우 이 wrapper 클래스를 통해 비교적 편하게 사용할 수 있습니다.
그리고 위의 기본적인 필드 형식에 추가적으로 다음과 같은 인수를 넣어 보다 세밀한 Form을 생성할 수 있습니다.
- label : 필드의 HTML 코드에서 사용되는이름(HTML의 <label>)
- required : 필수 필드 여부(True/False)
-
widget : 표현될 HTML Form 요소 다음과 같은 widget이 주로 사용된다.
- TextInput : 한줄 글입력 필드 <input type="text" />
- PasswordInput : 비밀번호 입력 필드 <input type="password" />
- HiddenInput : 숨김 필드 <input type="hidden" />
- Textarea : 여러줄 글상자 필드 <textarea></textarea>
- FileInput : 파일선택 필드 <input type="file" />
- 참고 : http://docs.djangoproject.com/en/1.2/ref/forms/widgets/#ref-forms-widgets
- help_text : 필드 설명, 필드 아래에 출력
앞선 예제에서 사용한 django의 Form에 대해 django shell에서 사용해 보도록 합시다.
> python manage.py shell
>>> from myTest.loginForm import *
>>> frm = LoginForm() # 1
>>> print frm.as_table() # 2
<tr><th><label for="id_username">사용자 이름:</label></th><td><input id="id_username" type="text" name="username" maxlength="30" /></td></tr>
<tr><th><label for="id_password">암호:</label></th><td><input id="id_password" type="password" name="password" maxlength="127" /></td></tr>
>>> print frm["username"] # 3
<input id="id_username" type="text" name="username" maxlength="30" />
>>> frm = LoginForm({ #4
... 'username' : 'test1',
... 'password' : 'password123'
... })
>>> frm.is_valid() #5
True
>>> frm = LoginForm({ #6
... 'username' : '',
... 'password' : 'password123'
... })
>>> frm.is_valid()
False
각각에 대한 설명은 다음과 같습니다.
- 앞서 작성한 LogiinForm()을 통해 새로운 Form을 생성합니다.
- Form을 생성한 결과를 HTML Table 형태로 출력합니다.
- 전체 Form 대신 Form의 특정한 하위요소 하나만 출력합니다.
- 작성한 Form을 통해 사용자 입력값을 저장합니다.
- 입력된 값이 유효한지 검사합니다.
- username을 required=True 로 하였으므로 빈값이 들어가면 유효하지 않은 입력이 됩니다.
django에서 제공하는 Form은 위와 같이 Form요소에 대한 wrapper 클래스 뿐만이 아니라 메소드를 추가할 수 있습니다.
예를 들어 LoginForm에 입력값에 대한 검사 메소드를 추가해 보도록 하겠습니다.
제작할 메소드는 username이 존재여부입니다.
- from django.contrib.auth.models import User
from django.core.exceptions import ObjectDoesNotExist - class LoginForm(forms.Form) :
- ...
- def checkUsername(self):
username = self.cleaned_data['username'] # 1
username = username.lstrip().rstrip() # 2
try : # 3
User.objects.get(username=username)
except ObjectDoesNotExist:
raise forms.ValidationError('존재하지 않는 사용자입니다.') # 4
else :
return True
- django의 Form은 사용자 입력값이 없는 빈 폼을 검사(validation)하려고 하면 예외를 발생합니다. 사용자가 입력한 값은 사전형 데이터로 표현된 form.data로 접근할 수 있으며 검사를 통과한 사용자 입력값은 froms.cleaned_data로 접근할 수 있습니다. 즉, 사용자가 입력한 빈 값이 아닌 username을 가져옵니다.
- 입력된 username 문자열의 좌우의 공백문자를 제거합니다.
- 예외 처리구문입니다. User.object.get()은 조건으로 넣어준 값이 없을 경우 ObjectDoesNotExist 예외를 발생시킵니다. 이 #3 구문은 입력된 사용자명이 있는지 검사하여 입력된 사용자가 없으면 ObjectDoesNotExist 예외가 발생됩니다.
- #4에서 예외가 발생되면 다시 Form의 ValidationError()예외를 발생시켜서 Form 입력을 처음으로 되돌립니다.
이상으로부터 django에서 제공하는 Form 기능을 알아보았습니다.
다음 시간에 이 Form을 이용하여 사용자를 추가하는 과정에 대해 알아보도록 하겠습니다.
이 글은 스프링노트에서 작성되었습니다.
댓글 없음:
댓글 쓰기