💡 URECA/🗒️ 스터디 노트

[URECA] Day 80 LabbitLog 블로그 만들기 #4

코딩하세현 2025. 5. 27. 23:35
728x90

댓글 기능, 좋아요 기능, 글 수정 및 상세보기, UX 개선까지 포함된 의미 있는 날🔥

댓글 기능 전반 구현

1. 백엔드: comments 컬렉션 설계

MongoDB에 comments 컬렉션을 새로 만들고, Post와 User를 참조하는 구조로 설계했다.

// models/Comment.js
const commentSchema = new mongoose.Schema({
  postId: {
    type: mongoose.Schema.Types.ObjectId,
    ref: 'Post',
    required: true
  },
  userId: {
    type: mongoose.Schema.Types.ObjectId,
    ref: 'User',
    required: true
  },
  content: {
    type: String,
    required: true
  },
  createdAt: {
    type: Date,
    default: Date.now
  }
});

2. REST API 설계

메서드 경로 설명
POST /comments 댓글 작성
GET /comments/:postId 해당 게시물 댓글 목록 조회
PUT /comments/:commentId 댓글 수정
DELETE /comments/:commentId 댓글 삭제

3. 프론트엔드 연동

  • useEffect로 댓글 리스트 요청
  • 댓글 없을 경우 "댓글이 없습니다" 메시지 표시
  • 댓글 작성 후 리스트 자동 업데이트
useEffect(() => {
  const fetchComments = async () => {
    const res = await getComments(postId);
    setComments(res);
  };
  fetchComments();
}, [postId]);

📌 핵심 포인트

postId 기반 조회로, 각 게시글마다 댓글이 독립적으로 연결


좋아요 기능 추가 + Redux 상태 유지

1. 기본 동작 흐름

  • 게시글 카드에 좋아요 버튼 표시
  • 버튼 클릭 시 좋아요 상태 토글 (toggleLike)
  • 좋아요 수 + 사용자 상태 반영

2. Redux Store로 상태 관리

// redux/likesSlice.js
const initialState = {
  likedPosts: []
};

export const likesSlice = createSlice({
  name: 'likes',
  initialState,
  reducers: {
    toggleLike: (state, action) => {
      const postId = action.payload;
      if (state.likedPosts.includes(postId)) {
        state.likedPosts = state.likedPosts.filter(id => id !== postId);
      } else {
        state.likedPosts.push(postId);
      }
    }
  }
});

 

  • 앱 전역에서 좋아요 상태를 유지하려고 Redux 도입
  • 새로고침 시에도 상태 유지를 위해 로컬스토리지 또는 서버 상태 동기화 고려 중

📌 핵심 포인트

단순 클릭 기능이 아니라 UX와 직접 연결된 부분. Redux 도입으로 상태 관리 일관성을 확보

글 수정 기능 & 상세 보기 페이지 연결

1. 카드 클릭 → 상세 페이지 이동

const handleClick = () => {
  navigate(`/posts/${postId}`);
};

 

 

  • React Router로 카드 클릭 시 postId 기반 URL로 이동
  • 상세 페이지에서는 해당 게시글 내용을 useEffect로 불러옴

2. 글 수정하기

  • 수정 페이지 진입 시 기존 내용을 input에 세팅
  • 수정 완료 시 DB 반영 + 리다이렉션 처리

📌 핵심 포인트

사용자 입장에서 “게시글을 클릭 → 확인 → 수정” 흐름이 자연스러워지도록 설계

✨ UX 개선 사항

회원가입 실패 메시지 표시 오류 해결

  • 기존엔 상태 변수를 잘못 관리해서 메시지가 표시되지 않음
  • 조건 분기와 상태 초기화를 통해 해결 완료

스크롤 이슈 해결

  • 게시글 리스트에서 스크롤이 작동하지 않던 문제
  • overflow-y: auto 및 부모 요소의 max-height 설정으로 해결

글 작성 시 DB 반영 버그 수정

  • 폼 전송 후 실제로 DB에 저장되지 않던 버그
  • onSubmit 내에서 API 호출 누락되어 있었던 부분 수정

🎠회고

더보기

이번 작업을 하면서 단순히 기능만 구현하는 데서 그치는 게 아니라, 백엔드 API와 프론트엔드 UI가 어떻게 연결돼야 자연스러운 사용자 경험을 만들 수 있는지에 대해 더 깊이 고민해볼 수 있었다.

특히 댓글 기능이나 좋아요 기능처럼 사용자의 행동이 바로바로 화면에 반영돼야 하는 경우에는, 그냥 동작만 되면 되는 게 아니라 사용자가 보기에도 "오, 잘 작동하네!"라고 느낄 수 있는 피드백이 중요하다는 걸 확실히 느꼈다.

예를 들어, 댓글을 쓴 직후 리스트가 바로 갱신되지 않으면 '내가 제대로 작성한 게 맞나?' 싶은 불안감이 생길 수 있다. 그래서 그런 부분을 개선하기 위해 useEffect와 상태 갱신 로직을 잘 연결했고, 오류가 생겼을 때도 사용자 입장에서 알 수 있도록 메시지를 보여주도록 처리했다. 단순히 데이터를 주고받는 걸 넘어서, 사용자 흐름이 끊기지 않도록 설계하는 게 얼마나 중요한지 깨달았던 시간이었다.

또 하나, 이번에 처음으로 Redux를 적용해보면서 앱 전체 구조를 생각하는 눈도 조금 트인 것 같다. 좋아요 기능처럼 여러 컴포넌트에서 같은 데이터를 공유해야 하는 상황에서, props로 넘기고 관리하던 방식에는 확실히 한계가 있었다. Redux를 도입하고 나서는 전역 상태를 한 곳에서 깔끔하게 관리하면서, 필요한 컴포넌트에서 쉽게 꺼내 쓸 수 있는 흐름이 잡히는 경험을 할 수 있었다.
이 과정에서 Store를 어떻게 구성할지, action과 reducer는 어떤 역할을 하는지, 그리고 상태가 바뀌었을 때 전체 앱이 어떻게 반응하는지를 직접 다뤄보며 전보다 더 구조적인 사고를 할 수 있게 되었다.

정리하자면, 오늘의 작업은 단순히 "댓글 기능 만들었다", "좋아요 기능 완성했다"로 끝나는 날이 아니었다.
사용자 경험을 고려해서 UI를 구성하고, 백엔드와 프론트엔드가 자연스럽게 이어지도록 설계하고, 상태 관리에 대해 고민하며 앱 전체의 흐름을 생각해본 날이었다.

앞으로는 코드를 짤 때 단순히 '작동하냐'보다도,

"사용자는 이걸 보면서 어떤 생각이 들까?"
"이 흐름은 자연스러울까?"

이런 질문들을 더 자주 떠올리는 개발자가 되고 싶다.

728x90