Conversation
|
The latest updates on your projects. Learn more about Vercel for Git ↗︎
|
Walkthrough새로운 그룹 멤버 목록 UI 기능이 추가되었습니다. 멤버 정보를 위한 타입과 목데이터가 생성되었고, 멤버 리스트와 개별 멤버 아이템을 위한 스타일 컴포넌트와 React 컴포넌트가 구현되었습니다. 그룹 멤버 페이지와 해당 라우트가 생성되어, 실제로 멤버 목록을 확인할 수 있게 되었습니다. Changes
Sequence Diagram(s)sequenceDiagram
participant User
participant Router
participant GroupMembersPage
participant MemberList
participant MemberItem
User->>Router: "group/members" 경로로 이동
Router->>GroupMembersPage: GroupMembers 컴포넌트 렌더링
GroupMembersPage->>MemberList: mockMembers 전달
MemberList->>MemberItem: 각 멤버 데이터로 렌더링
User->>MemberItem: 멤버 클릭 또는 키보드 활성화
MemberItem->>GroupMembersPage: onMemberClick 호출
GroupMembersPage->>Router: 해당 멤버 상세 페이지로 이동
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~15 minutes Suggested labels
Suggested reviewers
Poem
Note 🔌 MCP (Model Context Protocol) integration is now available in Early Access!Pro users can now connect to remote MCP servers under the Integrations page to get reviews and chat conversations that understand additional development context. 📜 Recent review detailsConfiguration used: CodeRabbit UI 📒 Files selected for processing (3)
🚧 Files skipped from review as they are similar to previous changes (3)
✨ Finishing Touches
🧪 Generate unit tests
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. 🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
SupportNeed help? Create a ticket on our support page for assistance with any issues or questions. CodeRabbit Commands (Invoked using PR comments)
Other keywords and placeholders
CodeRabbit Configuration File (
|
There was a problem hiding this comment.
Actionable comments posted: 8
🔭 Outside diff range comments (1)
src/pages/index.tsx (1)
1-91: 라우트 정의 누락:/user/:userId경로 추가 필요
GroupMembers및MemberList컴포넌트에서navigate(`/user/${memberId}`)를 사용하고 있지만,
src/pages/index.tsx에는/user/:userId경로가 정의되어 있지 않습니다. 아래와 같이 누락된 라우트를 추가하세요.파일:
src/pages/index.tsximport Signup from './signup/Signup'; // …생략… import WithdrawDonePage from './mypage/WithdrawDonePage'; import EditPage from './mypage/EditPage'; +import UserPage from './user/UserPage'; // 실제 컴포넌트 경로/이름으로 조정 const Router = () => { const router = createBrowserRouter( createRoutesFromElements( <> <Route path="/" element={<Login />} /> {/* …생략… */} <Route path="notice" element={<Notice />} /> + <Route path="user/:userId" element={<UserPage />} /> </>, ), ); return ( <> <ScrollToTop /> <RouterProvider router={router} /> </> ); }; export default Router;
UserPage컴포넌트가 없다면 새로 생성하거나, 기존 사용자 프로필 페이지 컴포넌트를 사용해 주세요.- 위 변경 이후
GroupMembers및MemberList의 네비게이션 경로가 정상 작동합니다.
🧹 Nitpick comments (12)
src/mocks/members.mock.ts (2)
1-8: 프로필 이미지 필드: 빈 문자열 대신 옵셔널로 처리 권장UI에서 기본 이미지로 폴백할 예정이라면 빈 문자열 센티널 값보다
profileImage?: string로 옵셔널 처리하고, 목데이터에서는 해당 필드를 생략하는 편이 명확합니다.export interface Member { id: string; nickname: string; role: string; - profileImage: string; + profileImage?: string; points: number; - followers: string; + followersCount: number; } export const mockMembers: Member[] = [ { id: '1', nickname: 'Thiper', role: '칭호칭호', - profileImage: '', // 빈 문자열로 기본 이미지 처리 points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, { id: '2', nickname: 'thipthip', role: '공식 인플루언서', - profileImage: '', points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, { id: '3', nickname: 'Thiper', role: '청춘청춘', - profileImage: '', points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, { id: '4', nickname: 'thip01', role: '작가', - profileImage: '', points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, { id: '5', nickname: 'thip01', role: '작가', - profileImage: '', points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, { id: '6', nickname: 'thip01', role: '작가', - profileImage: '', points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, { id: '7', nickname: 'thip01', role: '작가', - profileImage: '', points: 0, - followers: '00명이 띱 하는 중', + followersCount: 0, }, ];Also applies to: 15-15, 23-23, 31-31, 39-39, 47-47, 55-55, 63-63
1-8: 타입 정의를 mocks에서 분리하세요도메인 타입(Member)을 mock 모듈에서 import하는 구조는 확장성/재사용성에 불리합니다.
src/types/member.ts등으로 이동하고, mocks에서는 해당 타입을 import만 하세요.원하시면 타입 파일 생성과 import 경로 일괄 치환 PR 보조 가능합니다.
src/pages/groupMembers/GroupMembers.styled.ts (1)
10-13: 모바일 주소창 이슈 대응을 위해 100dvh 추가 + 폭 명시 추천모바일 Safari 등에서 100vh가 뷰포트 UI에 영향을 받아 점프 현상이 생길 수 있습니다. 100dvh를 함께 선언해 폴백을 두는 걸 권장합니다. 또한 폭을 명시하면 레이아웃 안정성이 좋아집니다.
min-height: 100vh; + min-height: 100dvh; margin: 0 auto; + width: 100%; background-color: ${colors.black.main};src/pages/index.tsx (1)
1-6: (선택) 신규 페이지 라우트는 지연 로딩으로 번들 크기 최적화 가능규모가 커질 경우
React.lazy+Suspense로 GroupMembers를 지연 로딩하면 초기 번들 크기를 줄일 수 있습니다.원하시면 라우트 레이지 로딩 패턴 코드 예시 드리겠습니다.
src/pages/groupMembers/GroupMembers.tsx (1)
20-30: onMemberClick 중복 정의 최소화(선택)MemberList가 기본 내비게이션(fallback)을 제공한다면, 동일한 동작을 이 페이지에서 다시 넘길 필요는 없습니다. 경로 정합성만 맞춘 뒤 onMemberClick을 제거해 단순화할 수 있습니다.
- <Wrapper> - <MemberList members={mockMembers} onMemberClick={handleMemberClick} /> - </Wrapper> + <Wrapper> + <MemberList members={mockMembers} /> + </Wrapper>단, MemberList의 기본 경로가 실제 라우트와 일치하도록 먼저 정리되어야 합니다.
src/components/members/MemberList.tsx (4)
45-45: Chevron 아이콘은 장식용: 스크린리더 노이즈 제거장식 아이콘은 alt를 비우고 aria-hidden을 주는 게 접근성에 유리합니다.
- <ChevronIcon src={rightChevron} alt="이동" /> + <ChevronIcon src={rightChevron} alt="" aria-hidden="true" />
37-45: 프로필 이미지 필드 활용 및 폴백 처리(선택)현재 프로필 이미지를 렌더링하지 않습니다. 값이 있으면 이미지, 없으면 플레이스홀더를 보여주세요.
- <ProfileImage /> + {member.profileImage ? ( + <ProfileImage as="img" src={member.profileImage} alt={`${member.nickname} 프로필`} /> + ) : ( + <ProfileImage aria-hidden="true" /> + )}참고: Emotion styled는
asprop으로 엘리먼트 전환이 가능합니다. 별도 styled.img를 추가하는 방식도 OK입니다.
1-4: 타입 의존성 위치컴포넌트가 mocks에서 타입을 import하는 구조는 재사용성에 불리합니다.
src/types/member.ts등으로 타입을 이동해 이 파일이 types에서 import하도록 바꾸는 걸 권장합니다.원하시면 타입 이동 및 경로 일괄 치환 스크립트 제공하겠습니다.
34-49: 빈 목록 처리(선택)members가 빈 배열일 때의 빈 상태 UI(예: “표시할 멤버가 없습니다”)를 제공하면 UX가 좋아집니다.
필요 시 간단한 빈 상태 블록 추가를 제안드립니다.
src/components/members/MemberList.styled.ts (3)
71-75: 하드코딩된 색상/폰트 크기를 디자인 토큰으로 통일
color: white;와font-size: 11px;는 전역 토큰과 일관성이 떨어집니다. 전역semanticColors및typography토큰을 사용해 주세요.export const MemberStatus = styled.div` - color: white; - font-size: 11px; + color: ${semanticColors.text.primary}; + font-size: ${typography.fontSize['2xs']}; font-weight: ${typography.fontWeight.regular}; `
19-21: 호버 배경 컬러도 의미 기반 토큰 사용 검토현재
colors.darkgrey['50']를 직접 사용 중입니다. 프로젝트 전반의 일관성을 위해 의미 기반 토큰(semantic) 우선 적용을 검토해 주세요. 적절한 토큰이 없다면 디자인 시스템 측면에서 추가 정의를 고려해 보세요.
77-80: 장식용 체브론 아이콘: 드래그/선택 방지 및 접근성 처리 제안아이콘은 장식용일 가능성이 높습니다. 스타일에서 선택 방지를, 컴포넌트에서는
alt=""와aria-hidden="true"를 적용해 스크린 리더 노이즈를 줄이세요.export const ChevronIcon = styled.img` width: 24px; height: 24px; + display: block; + user-select: none; `
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
⛔ Files ignored due to path filters (1)
src/assets/member/right-chevron.svgis excluded by!**/*.svg
📒 Files selected for processing (6)
src/components/members/MemberList.styled.ts(1 hunks)src/components/members/MemberList.tsx(1 hunks)src/mocks/members.mock.ts(1 hunks)src/pages/groupMembers/GroupMembers.styled.ts(1 hunks)src/pages/groupMembers/GroupMembers.tsx(1 hunks)src/pages/index.tsx(2 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (4)
src/pages/groupMembers/GroupMembers.styled.ts (1)
src/styles/global/global.ts (1)
colors(4-53)
src/pages/groupMembers/GroupMembers.tsx (2)
src/pages/groupMembers/GroupMembers.styled.ts (1)
Wrapper(4-13)src/mocks/members.mock.ts (1)
mockMembers(10-67)
src/components/members/MemberList.tsx (2)
src/mocks/members.mock.ts (1)
Member(1-8)src/components/members/MemberList.styled.ts (9)
Container(4-8)MemberItem(10-36)ProfileSection(38-43)ProfileImage(45-51)MemberInfo(53-57)MemberName(59-63)MemberRole(65-69)MemberStatus(71-75)ChevronIcon(77-80)
src/components/members/MemberList.styled.ts (1)
src/styles/global/global.ts (3)
colors(4-53)semanticColors(80-153)typography(56-77)
🔇 Additional comments (1)
src/components/members/MemberList.styled.ts (1)
4-8: 레이아웃 설정은 깔끔합니다세로 플렉스와 가로 100% 컨테이너 구성 적절합니다.
| export const MemberItem = styled.div` | ||
| display: flex; | ||
| align-items: center; | ||
| justify-content: space-between; | ||
| padding: 20px; | ||
| cursor: pointer; | ||
| transition: background-color 0.2s; | ||
| position: relative; | ||
|
|
||
| &:hover { | ||
| background-color: ${colors.darkgrey['50']}; | ||
| } | ||
|
|
||
| &::after { | ||
| content: ''; | ||
| position: absolute; | ||
| bottom: 0; | ||
| left: 20px; | ||
| right: 20px; | ||
| height: 1px; | ||
| background-color: ${colors.darkgrey.dark}; | ||
| } | ||
|
|
||
| &:last-child::after { | ||
| display: none; | ||
| } | ||
| `; |
There was a problem hiding this comment.
💡 Verification agent
🧩 Analysis chain
키보드 포커스 스타일 추가로 접근성 보완 필요
호버 스타일만 있고 포커스 표시가 없습니다. 클릭 가능한 행이라면 키보드 사용자도 인지 가능하도록 :focus-visible 스타일을 추가하세요. 또한 컴포넌트(MemberList.tsx)에서 tabIndex=0, role="button"(또는 실제 버튼) 및 Enter/Space 키 핸들링을 고려해 주세요.
export const MemberItem = styled.div`
display: flex;
align-items: center;
justify-content: space-between;
padding: 20px;
cursor: pointer;
transition: background-color 0.2s;
position: relative;
&:hover {
background-color: ${colors.darkgrey['50']};
}
+
+ &:focus-visible {
+ outline: 2px solid ${semanticColors.text.point.green};
+ outline-offset: -2px;
+ }
&::after {
content: '';
position: absolute;
bottom: 0;
left: 20px;
right: 20px;
height: 1px;
background-color: ${colors.darkgrey.dark};
}
&:last-child::after {
display: none;
}
`MemberList.tsx에서 MemberItem이 실제로 포커스 가능하게 설정되어 있는지 확인해 보겠습니다. 아래 스크립트를 실행해 주세요.
🏁 Script executed:
#!/bin/bash
# MemberList.tsx 파일 경로 찾기
file=$(fd --hidden -e tsx MemberList.tsx)
echo "Found: $file"
# MemberItem 사용 위치 확인
grep -n "MemberItem" -n "$file" || echo "MemberItem 사용이 없습니다."
# 파일 상위 200라인 출력
echo -e "\n===== $file (1~200) ====="
sed -n '1,200p' "$file"
# tabIndex, role, onKeyDown/Enter/Space 핸들러 검색
echo -e "\n===== tabIndex, role, onKeyDown, onKeyPress 검색 ====="
grep -En "tabIndex|role=|onKeyDown|onKeyPress|onKeyUp" "$file" || echo "관련 속성/핸들러 미발견"Length of output: 2135
키보드 접근성 향상을 위한 MemberItem 컴포넌트 업데이트 필요
현재 MemberItem은 onClick만 지원하고 있어 키보드 사용자가 접근·인식할 수 없습니다. 다음을 적용하세요:
• src/components/members/MemberList.styled.ts
:focus-visible스타일 추가 (아웃라인/오프셋)
• src/components/members/MemberList.tsx
<MemberItem>에tabIndex={0}및role="button"속성 추가onKeyDown핸들러로 Enter/Space 키 입력 시handleMemberClick호출
--- a/src/components/members/MemberList.styled.ts
+++ b/src/components/members/MemberList.styled.ts
@@ export const MemberItem = styled.div`
&:hover {
background-color: ${colors.darkgrey['50']};
}
+
+ &:focus-visible {
+ outline: 2px solid ${semanticColors.text.point.green};
+ outline-offset: -2px;
+ }--- a/src/components/members/MemberList.tsx
+++ b/src/components/members/MemberList.tsx
@@ members.map(member => (
- <MemberItem key={member.id} onClick={() => handleMemberClick(member.id)}>
+ <MemberItem
+ key={member.id}
+ role="button"
+ tabIndex={0}
+ onClick={() => handleMemberClick(member.id)}
+ onKeyDown={e => {
+ if (e.key === 'Enter' || e.key === ' ') {
+ e.preventDefault();
+ handleMemberClick(member.id);
+ }
+ }}
+ >📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| export const MemberItem = styled.div` | |
| display: flex; | |
| align-items: center; | |
| justify-content: space-between; | |
| padding: 20px; | |
| cursor: pointer; | |
| transition: background-color 0.2s; | |
| position: relative; | |
| &:hover { | |
| background-color: ${colors.darkgrey['50']}; | |
| } | |
| &::after { | |
| content: ''; | |
| position: absolute; | |
| bottom: 0; | |
| left: 20px; | |
| right: 20px; | |
| height: 1px; | |
| background-color: ${colors.darkgrey.dark}; | |
| } | |
| &:last-child::after { | |
| display: none; | |
| } | |
| `; | |
| file=src/components/members/MemberList.styled.ts | |
| export const MemberItem = styled.div` | |
| display: flex; | |
| align-items: center; | |
| justify-content: space-between; | |
| padding: 20px; | |
| cursor: pointer; | |
| transition: background-color 0.2s; | |
| position: relative; | |
| &:hover { | |
| background-color: ${colors.darkgrey['50']}; | |
| } | |
| &:focus-visible { | |
| outline: 2px solid ${semanticColors.text.point.green}; | |
| outline-offset: -2px; | |
| } | |
| &::after { | |
| content: ''; | |
| position: absolute; | |
| bottom: 0; | |
| left: 20px; | |
| right: 20px; | |
| height: 1px; | |
| background-color: ${colors.darkgrey.dark}; | |
| } | |
| &:last-child::after { | |
| display: none; | |
| } | |
| `; |
| export const MemberItem = styled.div` | |
| display: flex; | |
| align-items: center; | |
| justify-content: space-between; | |
| padding: 20px; | |
| cursor: pointer; | |
| transition: background-color 0.2s; | |
| position: relative; | |
| &:hover { | |
| background-color: ${colors.darkgrey['50']}; | |
| } | |
| &::after { | |
| content: ''; | |
| position: absolute; | |
| bottom: 0; | |
| left: 20px; | |
| right: 20px; | |
| height: 1px; | |
| background-color: ${colors.darkgrey.dark}; | |
| } | |
| &:last-child::after { | |
| display: none; | |
| } | |
| `; | |
| file=src/components/members/MemberList.tsx | |
| members.map(member => ( | |
| <MemberItem | |
| key={member.id} | |
| role="button" | |
| tabIndex={0} | |
| onClick={() => handleMemberClick(member.id)} | |
| onKeyDown={e => { | |
| if (e.key === 'Enter' || e.key === ' ') { | |
| e.preventDefault(); | |
| handleMemberClick(member.id); | |
| } | |
| }} | |
| > | |
| {/* existing member content */} | |
| </MemberItem> | |
| )) |
🤖 Prompt for AI Agents
In src/components/members/MemberList.styled.ts lines 10 to 36, add a
:focus-visible style to MemberItem to improve keyboard accessibility by showing
an outline and offset when focused. In src/components/members/MemberList.tsx,
update the MemberItem component to include tabIndex={0} and role="button"
attributes, and add an onKeyDown handler that calls handleMemberClick when Enter
or Space keys are pressed.
| export const ProfileImage = styled.div` | ||
| width: 48px; | ||
| height: 48px; | ||
| border-radius: 50%; | ||
| background-color: ${colors.grey['400']}; | ||
| flex-shrink: 0; | ||
| `; |
There was a problem hiding this comment.
💡 Verification agent
🧩 Analysis chain
프로필 이미지는 div 대신 img 사용 권장(alt 제공 및 object-fit)
현재 div는 대체 텍스트를 제공할 수 없어 접근성이 떨어집니다. styled.img로 전환하고 object-fit: cover를 적용하면 비율 유지와 자르기가 자연스럽습니다. 컴포넌트에서 alt를 의미 있게 제공하거나 장식용이면 alt=""를 지정하세요.
-export const ProfileImage = styled.div`
+export const ProfileImage = styled.img`
width: 48px;
height: 48px;
border-radius: 50%;
+ object-fit: cover;
background-color: ${colors.grey['400']};
flex-shrink: 0;
`ProfileImage 컴포넌트가 실제로 img 태그로 교체해도 문제가 없는지, 사용 위치와 전달되는 props(src, alt 등)를 확인하기 위해 아래 스크립트를 실행하겠습니다.
🏁 Script executed:
#!/bin/bash
grep -R "ProfileImage" -n srcLength of output: 2953
프로필 이미지가 실제로 src와 alt 같은 props를 받아 렌더링되는지 확인이 필요합니다. 아래 스크립트로 MemberList.tsx 사용 부분을 살펴보겠습니다.
🏁 Script executed:
#!/bin/bash
sed -n '1,200p' src/components/members/MemberList.tsxLength of output: 1382
프로필 URL이 실제로 Member 타입에 포함되어 있는지 확인하기 위해 src/mocks/members.mock.ts를 조회해 보겠습니다.
🏁 Script executed:
#!/bin/bash
sed -n '1,200p' src/mocks/members.mock.tsLength of output: 1160
프로필 이미지를 <img>로 전환하고 src/alt를 전달하세요
현재 ProfileImage는 styled.div로 고정된 회색 원형만 렌더링되어 실제 유저 이미지와 대체 텍스트를 제공하지 않습니다. 접근성과 화면 비율 유지를 위해 다음을 적용해주세요:
• src/components/members/MemberList.styled.ts
styled.div→styled.imgobject-fit: cover추가
-export const ProfileImage = styled.div`
+export const ProfileImage = styled.img`
width: 48px;
height: 48px;
border-radius: 50%;
+ object-fit: cover;
background-color: ${colors.grey['400']};
flex-shrink: 0;
`;• src/components/members/MemberList.tsx
<ProfileImage />사용부에src와 유의미한alt전달
{members.map(member => (
<MemberItem key={member.id} onClick={() => handleMemberClick(member.id)}>
<ProfileSection>
- <ProfileImage />
+ <ProfileImage
+ src={member.profileImage || undefined}
+ alt={member.nickname ? `${member.nickname} 프로필` : ''}
+ />
<MemberInfo>
<MemberName>{member.nickname}</MemberName>
<MemberRole>{member.role}</MemberRole>
</MemberInfo>
</ProfileSection>
<MemberStatus>{member.followers}</MemberStatus>
<ChevronIcon src={rightChevron} alt="이동" />
</MemberItem>
))}🤖 Prompt for AI Agents
In src/components/members/MemberList.styled.ts lines 45 to 51, change
ProfileImage from styled.div to styled.img, add object-fit: cover to maintain
image aspect ratio, and remove background-color since the image will be shown.
Then in src/components/members/MemberList.tsx, update all uses of <ProfileImage
/> to pass appropriate src and alt props for accessibility and correct image
rendering.
| const handleMemberClick = (memberId: string) => { | ||
| // 특정 사용자 페이지로 이동 | ||
| navigate(`/user/${memberId}`); | ||
| }; |
There was a problem hiding this comment.
사용자 페이지 경로 불일치 수정 필요
현재 /user/${memberId}로 이동하지만 라우터에는 해당 경로가 없습니다. 기존 사용자 상세 라우트(otherfeed/:userId)와 맞추시는 걸 권장합니다.
옵션 B를 채택할 경우 다음과 같이 변경하세요.
- navigate(`/user/${memberId}`);
+ navigate(`/otherfeed/${memberId}`);라우트 추가(옵션 A)를 선택한다면 본 변경은 불필요합니다.
📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| const handleMemberClick = (memberId: string) => { | |
| // 특정 사용자 페이지로 이동 | |
| navigate(`/user/${memberId}`); | |
| }; | |
| const handleMemberClick = (memberId: string) => { | |
| // 특정 사용자 페이지로 이동 | |
| navigate(`/otherfeed/${memberId}`); | |
| }; |
🤖 Prompt for AI Agents
In src/pages/groupMembers/GroupMembers.tsx lines 15 to 18, the navigation path
for user pages is incorrect as it uses `/user/${memberId}`, which does not match
any existing route. To fix this, update the navigate call to use the existing
route pattern `/otherfeed/${memberId}` so it aligns with the defined router
paths.
| import EditPage from './mypage/EditPage'; | ||
| import Notice from './notice/Notice'; | ||
| import ParticipatedGroupDetail from './groupDetail/ParticipatedGroupDetail'; | ||
| import GroupMembers from './groupMembers/GroupMembers'; |
There was a problem hiding this comment.
내비게이션 경로 불일치: '/user/:id' 라우트가 없어 클릭 시 404 가능성
MemberList/GroupMembers에서 /user/${memberId}로 이동하지만, 현재 라우터에는 해당 경로가 없습니다. 현 상태로는 클릭 시 404가 날 수 있습니다. 아래 두 가지 중 하나로 정합성을 맞춰주세요.
옵션 A) 사용자 라우트를 추가해 기존 내비게이션을 살립니다.
<Route path="otherfeed/:userId" element={<OtherFeedPage />} />
+ <Route path="user/:userId" element={<OtherFeedPage />} />
<Route path="follow/:type/:userId" element={<FollowerListPage />} />옵션 B) 내비게이션 경로를 기존 사용자 상세 라우트로 통일합니다.
- MemberList:
/user/${memberId}->/otherfeed/${memberId} - GroupMembers: 동일 변경
Also applies to: 57-57
🤖 Prompt for AI Agents
In src/pages/index.tsx at lines 39 and 57, the navigation path '/user/:id' used
in MemberList and GroupMembers does not exist in the router, causing potential
404 errors. To fix this, either add a new user route matching '/user/:id' to the
router (Option A) or update the navigation paths in MemberList and GroupMembers
from '/user/${memberId}' to the existing route '/otherfeed/${memberId}' to
maintain consistency (Option B). Choose one approach and apply it consistently
to both locations.
#️⃣ 연관된 이슈
따로 등록하지 않았습니다.
📝 작업 내용
기존
ParticipatedGroupDetail.tsx에서 독서메이트 클릭 시 이동할 수 있는 독서메이트 목록 화면을 새롭게 개발했습니다.📄 주요 구현 사항
1. 독서메이트 목록 페이지 구현
src/pages/groupmembers/GroupMembers.tsx페이지 생성2. MemberList 컴포넌트 개발
src/components/members/MemberList.tsx컴포넌트 분리/user/${memberId}경로로 이동하도록 구현3. 목업 데이터 및 타입 정의
src/mocks/members.mock.ts에 Member 인터페이스와 mockMembers 배열 생성스크린샷
2025-08-10.1.53.39.mov
💬리뷰 요구사항(선택)
딱히 없습니다!
Summary by CodeRabbit
신규 기능
스타일
테스트/모킹 데이터