<commit_before>---
layout: post
title: Day45 - Insta-api (Class-based view, FormView, DeleteView), Javascript
categories: wps
tags: [fastcampus, api, javascript, code]
---

## 폼

### View로 구현

```
PostForm 사용
    fields
        content
        photos
POST 요청을 받았을 때,
1. 해당 request.user를 author로 하는 Post 인스턴스 생성
2. 만약 form.cleaned_data['content']가 빈 값이 아니면 PostComment 인스턴스 생성
3. request.FILES.getlist('photos')를 loop하며 PostPhoto 인스턴스 생성
4. return redirect('post:post-list')
```

#### post/form.py

```python
from django import forms


class PostForm(forms.Form):
    content = forms.CharField(required=False)
    photos = forms.ImageField(
        widget=forms.ClearableFileInput(
            attrs={
                'multiple': True
            }
        )
    )
```

#### post/ursl/views.py

```python
urlpatterns = [
    url(r'^create/$', views.PostCreate.as_view(), name='post-create'),
]
```

#### post/views/post.py

```python
class PostCreate(View):
    form_class = PostForm
    template_name = 'post/post_create.html'

    def get(self, request, *args, **kwargs):
        form = self.form_class()
        context = {
            'form': form
        }
        return render(request, self.template_name, context)

    def post(self, request, *args, **kwargs):
        # print(request.POST)
        # print(request.FILES)
        author = request.user
        post = Post.objects.create(author=author)
        form = self.form_class(request.POST, request.FILES)
        if form.is_valid():
            content = form.cleaned_data.get('content', '').strip()
            if content != '':
                PostComment.objects.create(
                    post=post,
                    author=author,
                    content=content
                )
            for file in request.FILES.getlist('photos'):
                PostPhoto.objects.create(
                    post=post,
                    photo=file
                )

            return redirect('post:post-list')
        else:
            return HttpResponse(form.errors)
```



### FromView로 리팩토링

```
attributes
	template_name
	form_class
	success_url

method
	form_valid(self, form)
		request는 self.request로 접근 가능
		form.cleand_date는 바로 사용 가능
		redirect는 정의해줄 필요 없음
```

#### post/views/post.py

```python
class PostCreate(FormView):
    form_class = PostForm
    template_name = 'post/post_create.html'
    success_url = '/post/'

    def form_valid(self, form):
        # print(form.cleaned_data)
        # print(form)
        author = self.request.user
        post = Post.objects.create(author=author)
        content = form.cleaned_data.get('content', '').strip()
        photos = self.request.FILES.getlist('photos')
        if content != '':
            PostComment.objects.create(
                post=post,
                author=author,
                content=content
            )
        for file in photos:
            PostPhoto.objects.create(
                post=post,
                photo=file
            )
        return super().form_valid(form)a
```



## PostDelete 구현

### DeleteView로 구현

#### post/views/post.py

```python
class PostDelete(DeleteView):
    model = Post
    success_url = reverse_lazy('post:post-list')
```

#### templates/post/include/post.html

```html
<!-- Post delete form start -->
{% if user == post.author %}
<form action="{% url 'post:post-delete' pk=post.pk %}" method="POST" class="inline">{% csrf_token %}
  <button type="submit" class="btn">Delete</button>
</form>
{% endif %}
<!-- Post delete form end -->
```

#### post/urls/views.py

```python
url(r'^(?P<pk>[0-9]+)/delete/$', views.PostDelete.as_view(), name='post-delete')<commit_msg>Fixed template tag<commit_after>---
layout: post
title: Day45 - Insta-api (Class-based view, FormView, DeleteView), Javascript
categories: wps
tags: [fastcampus, api, javascript, code]
---

## 폼

### View로 구현

```
PostForm 사용
    fields
        content
        photos
POST 요청을 받았을 때,
1. 해당 request.user를 author로 하는 Post 인스턴스 생성
2. 만약 form.cleaned_data['content']가 빈 값이 아니면 PostComment 인스턴스 생성
3. request.FILES.getlist('photos')를 loop하며 PostPhoto 인스턴스 생성
4. return redirect('post:post-list')
```

#### post/form.py

```python
from django import forms


class PostForm(forms.Form):
    content = forms.CharField(required=False)
    photos = forms.ImageField(
        widget=forms.ClearableFileInput(
            attrs={
                'multiple': True
            }
        )
    )
```

#### post/ursl/views.py

```python
urlpatterns = [
    url(r'^create/$', views.PostCreate.as_view(), name='post-create'),
]
```

#### post/views/post.py

```python
class PostCreate(View):
    form_class = PostForm
    template_name = 'post/post_create.html'

    def get(self, request, *args, **kwargs):
        form = self.form_class()
        context = {
            'form': form
        }
        return render(request, self.template_name, context)

    def post(self, request, *args, **kwargs):
        # print(request.POST)
        # print(request.FILES)
        author = request.user
        post = Post.objects.create(author=author)
        form = self.form_class(request.POST, request.FILES)
        if form.is_valid():
            content = form.cleaned_data.get('content', '').strip()
            if content != '':
                PostComment.objects.create(
                    post=post,
                    author=author,
                    content=content
                )
            for file in request.FILES.getlist('photos'):
                PostPhoto.objects.create(
                    post=post,
                    photo=file
                )

            return redirect('post:post-list')
        else:
            return HttpResponse(form.errors)
```



### FromView로 리팩토링

```
attributes
	template_name
	form_class
	success_url

method
	form_valid(self, form)
		request는 self.request로 접근 가능
		form.cleand_date는 바로 사용 가능
		redirect는 정의해줄 필요 없음
```

#### post/views/post.py

```python
class PostCreate(FormView):
    form_class = PostForm
    template_name = 'post/post_create.html'
    success_url = '/post/'

    def form_valid(self, form):
        # print(form.cleaned_data)
        # print(form)
        author = self.request.user
        post = Post.objects.create(author=author)
        content = form.cleaned_data.get('content', '').strip()
        photos = self.request.FILES.getlist('photos')
        if content != '':
            PostComment.objects.create(
                post=post,
                author=author,
                content=content
            )
        for file in photos:
            PostPhoto.objects.create(
                post=post,
                photo=file
            )
        return super().form_valid(form)a
```



## PostDelete 구현

### DeleteView로 구현

#### post/views/post.py

```python
class PostDelete(DeleteView):
    model = Post
    success_url = reverse_lazy('post:post-list')
```

#### templates/post/include/post.html

```html{%raw%}
<!-- Post delete form start -->
{% if user == post.author %}
<form action="{% url 'post:post-delete' pk=post.pk %}" method="POST" class="inline">{% csrf_token %}
  <button type="submit" class="btn">Delete</button>
</form>
{% endif %}
<!-- Post delete form end -->
```

#### post/urls/views.py

```python
url(r'^(?P<pk>[0-9]+)/delete/$', views.PostDelete.as_view(), name='post-delete')
{'fraction_non_alphanumeric': 0.14079520697167755, 'fraction_numerical': 0.002178649237472767, 'mean_word_length': 2.2572062084257207, 'pattern_counts': {'":': 0, '<': 17, '<?xml version=': 0, '>': 17, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3682399', 'n_tokens_mistral': 2464, 'n_tokens_neox': 2430, 'n_words': 481}