Django 활용 2 - UI를 리액트로 변경하기

박경현·2024년 9월 9일
1
post-thumbnail

전에는 장고 내에서 UI도 만들었지만 실제 서비스를 만들게 되면 백엔드와 프론트를 독립적으로 구분해야 서로 수정했을때 영향을 적게 미치기 때문에
프론트를 리액트로 변경했습니다.

이렇게 UI부분이 달라지면 항상 고민해야하는게 CORS문제인데요. Django는 크게 어렵지 않게 해결할 수 있었습니다.

순서

  1. 장고 - CORS 방지 설정해두기
  2. 장고 - 블로그 글 모델 만들기
  3. 장고 - API 구현하기
  4. 리액트 - API 요청 및 처리 부분 구현
  5. 리액트 - 각 페이지별 UI 만들기

지금은 UI 보다 장고와 리액트 연동에 신경을 써서 style은 없는 상태입니다.

장고

장고 CORS문제 해결

먼저 장고 프로젝트를 만들고 posts라는 글 어플리케이션을 추가해줍니다.

django-admin startproject config .
python manage.py startapp posts

RESTful API를 쉽게 만들어주는 라이브러리와 CORS문제 해결을 위한 라이브러리를 설치해줘야합니다.

pip install djangorestframework
pip install django-cors-headers

그리고 config/settings.py에 가서 몇가지를 작성해주면 됩니다.

INSTALLED_APPS = [
...
'corsheaders',
'rest_framework', # restful api를 위한 설정
'posts' # 내가 만든 어플리케이션 이름
]

MIDDLEWARE = [
	'corsheaders.middleware.CorsMiddleware', # cors문제 해결
	...  
	]
CORS_ORIGIN_ALLOW_ALL = True 

장고 블로그 CRUD API 만들기

이제 모델과 api 요청 처리를 적어주면 됩니다.
이때 특이한 기능이 바로 serializer였는데 이게 모델을 json으로 변환이나 역변환을 자동으로 해줍니다.

먼저 모델 먼저 만들어줍니다.

from django.db import models

class Post(models.Model):
	title = models.CharField(max_length=100)
    content = models.TextField()
    create_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now_add=True)

그리고 모델을 sqlLite에 추가해줍니다.

python3 manage.py makemigrations
python3 manage.py migrate

이제 api요청을 위한 기본 초석인 serializer를 설정합니다.
posts/serializers.py

from rest_framework import serializers
from .model import Post
class PostSerializer(serializers.ModelSerializer):
	class Meta:
    	model = Post
        fields = '__all__'

serializers.ModelSerializer -> 모델필드에 해당하는 시리얼라이저 필드를 자동으로 생성
class Meta -> Meta클래스는 시리얼라이저의 메타데이터를 정의하는 내부 클래스
model = Post -> 모델은 우리가 만든 post사용
fileds = all => 모델의 모든 필드를 시리얼라이즈에 연결

그리고 이제 views.py에서 요청에 대한 처리를 합니다.
posts/views.py

from .models import Post
from rest_framework import viewsets
from .serializers import PostSerializer


class PostViewSet(viewsets.ModelViewSet):
	queryset = Post.objects.all()
    serializer_class = PostSerializer

import viewsets -> 여러 http메소드(get,post,delete,put)를 처리해줌ㅡ 이때 코드 중복 줄여주는 클래스 기반 뷰
class PostViewSet(viewsets.ModelViewSet):-> 새로운 postviewsSet을 만듦
queryset = Post.objects.all() -> 기본 쿼리셋을 정의, API가 모든 게시글에 대해 CRUD가 가능함
serializer_class = PostSerializer -> 사용할 시리얼라이저 클래스를 지정함

GET /posts/: 모든 게시글을 조회합니다.
POST /posts/: 새로운 게시글을 생성합니다.
GET /posts/{id}/: 특정 ID의 게시글을 조회합니다.
PUT /posts/{id}/: 특정 ID의 게시글을 수정합니다.
DELETE /posts/{id}/: 특정 ID의 게시글을 삭제합니다.

이제 마지막으로 url만 설정을 해주면 되는데 내부 url을 적어주고 전체 url에 지정하면된다!!

내부 url -> posts/urls.py


from django.urls import path, include
from rest_framework.routers import DefaultRouter
from .views import PostViewSet

router = DefaultRouter()
router.register(r'posts', PostViewSet)

urlpatterns = [
	path('api/', include(router.urls))
]

외부 url -> config/urls.py

from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', include('posts.urls'))
]

리액트

차고로 리액트 작성 전 Postman으로 장고 잘 돌아가는지 확인을 꼭 해야합니다!!

api 요청 처리 -> postApi.js
전체 글 조회 화면 -> PostList.jsx
글 상세 화면 -> PostDetail.jsx
글 작성 및 수정 -> PostForm.jsx

리액트 API 요청 및 처리하기

src/api/postApi.js

const API_URL = "http:127.0.0.1:8000/api/posts/"

// 모든 게시글 조회
export const fetchPosts = async() => {
	const response = await fetch(API_URL)
    return response.json()
}

// 특정 게시글 조회
export const fetchPost = async() => {
	const response = await = fetch(`${API_URL}${id}/`)
    return response.json()
}
// 게시글 생성
export const createPost = async (post) => {
    const response = await fetch(API_URL, {
        method: "POST",
        headers: {
            "Content-Type" : "application/json"
        },
        body : JSON.stringify(post),
    })
    return response.json()
}

// 게시글 수정
export const updatePost = async (id, post) => {
    const response = await fetch(`${API_URL}${id}/`, {
        method: "PUT",
        headers: {
            "Content-Type" : "application/json"
        },
        body : JSON.stringify(post),
    })
    return response.json()
}

// 게시글 삭제
export const deletePost = async (id) => {
    await fetch(`${API_URL}${id}/`, {
        method: "DELETE"
    })
}

앞으로 더 나아갈 방향

AI를 적용해보려고 하는데 제목과 내용을 보고 이미지 섬네일을 생성해주는? 걸 만들어보려고 한다.

  1. CSS 적용
  2. 로그인 및 회원가입 만들기 -> 해당 회원이 자신것만 삭제 가능하게!
  3. AI로 섬네일 만들기 적용
profile
SW로 문제를 해결하려는 열정만 있는 대학생

0개의 댓글