본문 바로가기
Web Programming/django

[Django] Model기반 form 형식 지정

by 테리는당근을좋아해 2020. 6. 22.

목표

- model 기반의 form 형식을 지정할 수 있다.

 

 

form 태그

form 태그는 웹 애플리케이션에서 데이터를 입력받는 태그이다.

 

Model

class Patient(models.Model):
    name = models.CharField(max_length=100)
    age = models.IntegerField()
    height = models.FloatField()
    weight = models.FloatField()
    blood = models.CharField(max_length=10)
    description = models.TextField()

만약, 위 코드에서 처럼 Model에 Patient라는 클래스가 있다면

 

우리는 이러한 데이터를 웹 애플리케이션에서 입력받기위해 template과 view에서 각각의 아래와 같은 코드를 작성해주어야한다.

 

 

template

<form method="POST" action="{% url 'regist' %}">
    {% csrf_token %}
    <p>이름</p>
    <input type="text" name="name">
    <p>나이</p>
    <input type="number" name="age">
    <p>키</p>
    <input type="text" name="height">
    <p>몸무게</p>
    <input type="text" name="weight">
    <p>혈액형</p>
    <input type="text" name="blood">
    <p>세부사항</p>
    <input type="text" name="description">
    <input type="submit" value="작성하기">
</form>

 

 

view

def regist(request):
    if(request.method == 'POST'):
        patient = Patient()
        patient.name = request.POST['name']
        patient.age = request.POST['age']
        patient.height = float(request.POST['height'])
        patient.weight = float(request.POST['weight'])
        patient.blood = request.POST['blood']
        patient.description = request.POST['description']
        patient.save()
        return redirect('/')
    else:
        return render(request, 'regist.html')

 

만약 클래스의 필드가 더 늘어나거나 여러 템플릿에서 입력을 받는 form을 구성해야할 경우,

코드의 양은 늘어나게 될 것이고, 불필요한 시간을 소모하게 될 수 있다.

 

Django에서 이러한 문제점을 해결하기 위해 Model을 기반으로 Form 형식을 지정해주는 방법을 알아보자

 

 

form.py

form의 형식을 지정해줄 form.py를 앱 디렉터리 내에 하나 생성해준다.

 

form.py에 아래와 같은 코드를 작성한다.

from django import forms
from .models import Patient

# form 형식을 지정해주는 클래스
class PostForm(forms.ModelForm):
    # form 형식을 지정할 클래스의 메타데이터
    class Meta:
        # form 형식을 지정해줄 클래스를 Model에서 가져온다.
        model = Patient
        # 지정해줄 필드명을 리스트에 명시한다.
        fields = ['name', 'age', 'height', 'weight', 'blood', 'description']

 

view

from .form import PatientForm

...

def regist(request):
    # POST 요청이 들어왔을 떄
    if(request.method == 'POST'):
        # form 객체에 POST 요청으로 전달된 PatientForm을 저장한다.
        form = PatientForm(request.POST)
        # form이 유효한 데이터일 경우
        if form.is_valid():
            # 데이터베이서에 저장ㅎ하지 않은 상태로 반환
            post = form.save(commit=False)
            # 데이터베이스에 저장
            post.save()
        return redirect('/')
    # GET 요청이 들어왔을 때
    else:
        # 데이터를 입력받을 빈 form 생성
        form = PatientForm()
        # 딕셔너리 형태로 template에 전달
        return render(request, 'regist.html', {'form' : form})

 

template

<form method="POST" action="{% url 'regist' %}">
    {% csrf_token %}
    <table>
        {{form}}
    </table>
    <input type="submit" value="작성하기">
</form>

views.py 에서 넘겨받은 form을 사용해 입력을 위한 Component를 구성한다.

 

 

model에 필드와 일치하는 form 형식을 볼 수 있다.

 

템플릿에서 직접 form형식을 지정하다 보면

코드가 길어지는 문제점 말고도 input내의 name이나 type 속성값을 잘 못 지정하는 등의 여러가지 실수가 발생할 수 있는데,

 model 기반의 form 형식을 지정해 이러한 문제점들을 해결할 수 있다.

댓글