Skip to content

Latest commit

 

History

History
1298 lines (1112 loc) · 38.9 KB

File metadata and controls

1298 lines (1112 loc) · 38.9 KB

채팅 API 문서

개요

Socket.io를 사용한 실시간 채팅 시스템과 REST API를 제공합니다.

기본 정보

  • Base URL: http://localhost:3001
  • 인증: JWT 인증 필요 (모든 API)
  • 응답 형식: JSON (공통 응답 포맷)

1. 채팅방 목록 조회

GET /chats

내가 포함된 채팅방 목록을 반환합니다.

Path Parameters

파라미터 타입 설명
- - 경로 파라미터 없음

Query Parameters

파라미터 타입 필수 설명
cursor number 옵션 페이징을 위한 커서 (마지막으로 본 채팅방 ID)
limit number 옵션 한 번에 가져올 채팅방 수 (기본값: 15, 최대값: 50)

Request Body

없음

Response Fields

필드 타입 설명
[].id number 채팅방 고유 ID
[].name string? 채팅방 이름 (그룹 채팅방만, null: 1:1 채팅방)
[].type string 채팅방 타입 ("private" 또는 "group")
[].avatar_url string? 채팅방 아바타 이미지 URL (base URL 포함, 없으면 null)
[].created_at string 채팅방 생성 시간 (ISO 8601)
[].memberCount number 채팅방 총 멤버 수
[].unread_count number 읽지 않은 메시지 개수 (자신이 보낸 메시지는 제외)
[].lastMessage object? 마지막 메시지 정보 (없으면 null)
[].lastMessage.id number 마지막 메시지 ID
[].lastMessage.content string 메시지 내용
[].lastMessage.type string 메시지 타입 ("text", "image", "video")
[].lastMessage.sender_id number 발신자 ID
[].lastMessage.created_at string 메시지 발신 시간 (ISO 8601)
[].other_users[] array 나를 제외한 멤버들 (그룹 채팅방)
[].other_users[].id number 멤버 ID
[].other_users[].nickname string 멤버 닉네임
[].other_users[].avatar_url string? 멤버 프로필 이미지 URL
[].other_user object? 상대방 정보 (1:1 채팅방)
[].other_user.id number 상대방 ID
[].other_user.nickname string 상대방 닉네임
[].other_user.avatar_url string? 상대방 프로필 이미지 URL

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 목록 조회 성공",
  "data": {
    "chat_rooms": [
      {
        "id": 1,
        "name": "개발팀",
        "type": "group",
        "avatar_url": "http://localhost:3001/uploads/2024/01/15/avatar.jpg",
        "created_at": "2024-01-01T00:00:00.000Z",
        "memberCount": 3,
        "unread_count": 5,
        "lastMessage": {
          "id": 100,
          "content": "안녕하세요!",
          "type": "text",
          "sender_id": 2,
          "created_at": "2023-12-15T10:30:00.000Z"
        }
        "other_users": [
          {
            "id": 2,
            "nickname": "김철수",
            "avatar_url": "http://localhost:3001/uploads-profile/2024/01/15/user2.jpg"
          }
        ]
      }
    ],
    "hasNext": true,
    "nextCursor": 1
  }
}

HTTP 상태 코드

코드 설명
200 성공
401 인증 실패
500 서버 오류

비고

  • 삭제되고 메모리에서 해제된 채팅방은 제외됩니다.
  • 사용자가 나간 채팅방 (status: 'left')은 목록에서 제외됩니다.
  • 채팅방은 마지막 메시지 시간 기준으로 역순 정렬됩니다 (최신 대화 순).
  • 마지막 메시지가 없는 새 채팅방은 생성 시간으로 자연스럽게 포함됩니다.
  • 1:1 채팅방의 name은 항상 null입니다.
  • avatar_url은 설정되지 않은 경우 null입니다.
  • 페이징을 지원하며 첫 페이지는 chat 만 호출하고 다음 페이지는 ?cursor={nextCursor}를 사용하여 조회합니다.
  • hasNext: false이면 더 이상 페이지가 없음을 의미합니다.

2. 채팅방 읽음 처리

PATCH /chats/{chatRoomId}/read

사용자가 채팅방의 모든 메시지를 읽음 처리합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

없음

Response Fields

필드 타입 설명
success boolean 작업 성공 여부 (항상 true)

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 읽음 처리 성공",
  "data": {
    "success": true
  }
}

HTTP 상태 코드

코드 설명
200 성공
400 잘못된 채팅방 ID
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • 채팅방의 가장 최근 메시지 ID를 last_read_message_id로 업데이트합니다.
  • 채팅방 목록 조회 시 읽지 않은 메시지 개수가 0으로 표시됩니다.

3. 읽지 않은 메시지 총 개수 조회

GET /chats/unread-count

사용자가 읽지 않은 메시지의 총 개수를 반환합니다. 헤더의 알림 표시 등에 사용됩니다.

Path Parameters

파라미터 타입 설명
- - 경로 파라미터 없음

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

없음

Response Fields

필드 타입 설명
unread_count number 읽지 않은 메시지의 총 개수 (자신이 보낸 메시지 제외)

성공 응답 예시

{
  "code": 200,
  "message": "읽지 않은 메시지 총 개수 조회 성공",
  "data": {
    "unread_count": 3
  }
}

HTTP 상태 코드

코드 설명
200 성공
401 인증 실패
500 서버 오류

오류 응답 예시

401 인증 실패

{
  "code": 401,
  "message": "인증이 필요합니다."
}

500 서버 오류

{
  "code": 500,
  "message": "읽지 않은 메시지 총 개수 조회에 실패했습니다."
}

비고

  • 사용자가 속한 채팅방의 모든 읽지 않은 메시지 개수를 합산하여 총 개수를 반환합니다.
  • 각 채팅방별 last_read_message_id보다 큰 ID를 가진 메시지를 카운트합니다.
  • 자신이 보낸 메시지는 제외하고 계산합니다.

2. 1:1 채팅방 생성

POST /chats/private

두 명의 사용자 간 개인 채팅방을 생성합니다.

Path Parameters

파라미터 타입 설명
- - 경로 파라미터 없음

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

{
  "userId": 2
}

Request Body Fields

필드 타입 필수 설명
userId number 필수 상대방 사용자 ID

Response Fields

필드 타입 설명
chatRoomId number 채팅방 ID
isNewlyCreated boolean 새로 생성된 채팅방인지 여부 (true: 새로 생성됨, false: 기존 채팅방 재활용)

새 채팅방 생성 - 성공 응답 예시

{
  "code": 201,
  "message": "1:1 채팅방 생성 성공",
  "data": {
    "chatRoomId": 1,
    "isNewlyCreated": true
  }
}

기존 채팅방 재활용 - 성공 응답 예시

{
  "code": 200,
  "message": "기존 채팅방을 활용합니다",
  "data": {
    "chatRoomId": 5,
    "isNewlyCreated": false
  }
}

오류 응답 예시

{
  "code": 400,
  "message": "잘못된 요청입니다.",
  "errors": [
    {
      "field": "userId",
      "message": "올바른 사용자 ID를 입력해주세요."
    }
  ]
}

HTTP 상태 코드

코드 설명
201 생성 성공
400 유효성 검사 실패
401 인증 실패
500 서버 오류

비고

  • 이미 존재하는 1:1 채팅방의 경우 기존 방의 ID를 반환합니다.
  • 생성된 채팅방은 자동으로 private 타입으로 설정됩니다.
  • 요청자와 대상 사용자가 자동으로 멤버로 추가됩니다.

3. 채팅 이미지 업로드

POST /chats/image-upload

채팅 메시지로 보낼 이미지를 업로드합니다.

Path Parameters

파라미터 타입 설명
- - 경로 파라미터 없음

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body (multipart/form-data)

필드 타입 필수 설명
image file 필수 업로드할 이미지 파일 (JPG, PNG, GIF, WebP 등)

Response Fields

필드 타입 설명
image_path string 업로드된 이미지의 경로 (DB 저장용)
url string 완전한 이미지 접근 URL
filename string 생성된 고유 파일명
size number 파일 크기 (bytes)

성공 응답 예시

{
  "code": 200,
  "message": "이미지가 업로드되었습니다.",
  "data": {
    "image_path": "/uploads-chat/2024/10/10/image123_1703123456789_abc123.jpg",
    "url": "http://localhost:3001/uploads-chat/2024/10/10/image123_1703123456789_abc123.jpg",
    "filename": "image123_1703123456789_abc123.jpg",
    "size": 245760
  }
}

HTTP 상태 코드

코드 설명
200 업로드 성공
400 잘못된 파일 형식 또는 파일 없음
401 인증 실패
413 파일 크기 초과 (10MB)
500 서버 오류

비고

  • 지원되는 파일 형식: JPG, JPEG, PNG, GIF, WebP, HEIC, HEIF
  • 최대 파일 크기: 10MB
  • 파일은 uploads-chat/image/년/월/일/ 폴더에 저장됩니다.
  • 스토리지 분기: STORAGE_DRIVER 환경변수에 따라 저장소가 결정됩니다
    • 'local': 프로젝트 루트의 로컬 파일시스템에 저장
    • 'naver-cloud': 네이버 클라우드 Object Storage에 저장
  • image_path는 DB에 저장할 경로로, 클라이언트에서 baseUrl + image_path로 완전한 URL을 구성합니다.
  • 두 스토리지 타입 모두 동일한 URL 포맷을 유지하여 API 응답의 일관성을 보장합니다.
  • 업로드된 이미지는 소켓을 통해 type: 'image', content: image_path로 채팅 메시지로 전송될 수 있습니다.

3.5. 채팅 비디오 업로드

POST /chats/video-upload

채팅 메시지로 보낼 비디오를 업로드합니다. 선택적으로 편집(trim/crop)할 수 있습니다.

Path Parameters

파라미터 타입 설명
- - 경로 파라미터 없음

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body (multipart/form-data)

필드 타입 필수 설명
video file 필수 업로드할 비디오 파일 (MP4, MOV, AVI, WebM 등)
trimStart number 선택 자르기 시작 시간 (밀리초)
trimEnd number 선택 자르기 종료 시간 (밀리초)
cropArea string 선택 크롭 영역 JSON (예: {"x":0.1,"y":0.1,"width":0.8,"height":0.8})

Request Body Fields (cropArea JSON)

필드 타입 필수 설명
x number 필수 크롭 시작 X 좌표 (0-1, 비디오 너비의 비율)
y number 필수 크롭 시작 Y 좌표 (0-1, 비디오 높이의 비율)
width number 필수 크롭 너비 (0-1, 비디오 너비의 비율)
height number 필수 크롭 높이 (0-1, 비디오 높이의 비율)

Response Fields

필드 타입 설명
video_path string 업로드된 비디오의 경로 (DB 저장용)
thumbnail_path string 생성된 썸네일의 경로 (DB 저장용)
video_url string 완전한 비디오 접근 URL
thumbnail_url string 완전한 썸네일 접근 URL
size number 비디오 파일 크기 (bytes)

성공 응답 예시 (일반 업로드)

{
  "code": 200,
  "message": "비디오가 업로드되었습니다.",
  "data": {
    "video_path": "/uploads-chat-video/2024/11/12/video_1703123456789_abc123.mp4",
    "thumbnail_path": "/uploads-chat-thumbnail/2024/11/12/thumb_1703123456789_abc123.jpg",
    "video_url": "http://localhost:3001/uploads-chat-video/2024/11/12/video_1703123456789_abc123.mp4",
    "thumbnail_url": "http://localhost:3001/uploads-chat-thumbnail/2024/11/12/thumb_1703123456789_abc123.jpg",
    "size": 5242880
  }
}

성공 응답 예시 (편집 후 업로드)

{
  "code": 200,
  "message": "비디오가 업로드되고 편집되었습니다.",
  "data": {
    "video_path": "/uploads-chat-video/2024/11/12/edited_1703123456789_def456.mp4",
    "thumbnail_path": "/uploads-chat-thumbnail/2024/11/12/thumb_edited_1703123456789_def456.jpg",
    "video_url": "http://localhost:3001/uploads-chat-video/2024/11/12/edited_1703123456789_def456.mp4",
    "thumbnail_url": "http://localhost:3001/uploads-chat-thumbnail/2024/11/12/thumb_edited_1703123456789_def456.jpg",
    "size": 3145728
  }
}

HTTP 상태 코드

코드 설명
200 업로드 성공
400 잘못된 파일 형식, 파라미터 오류
401 인증 실패
413 파일 크기 초과 (75MB)
500 서버 오류

비고

  • 지원되는 파일 형식: MP4, MOV, AVI, WebM, MKV, FLV
  • 최대 파일 크기: 75MB
  • 비디오는 uploads-chat/video/년/월/일/ 폴더에 저장됩니다.
  • 썸네일은 uploads-chat/video-thumbnail/년/월/일/ 폴더에 자동 생성됩니다.
  • 스토리지 분기: STORAGE_DRIVER 환경변수에 따라 저장소가 결정됩니다
    • 'local': 프로젝트 루트의 로컬 파일시스템에 저장
    • 'naver-cloud': 네이버 클라우드 Object Storage에 저장
  • 두 스토리지 타입 모두 동일한 URL 포맷을 유지하여 API 응답의 일관성을 보장합니다.
  • 편집 파라미터가 제공되면 FFmpeg를 사용해 비디오를 실시간 편집합니다.
  • video_paththumbnail_path는 DB에 저장할 경로입니다.
  • 업로드된 비디오는 소켓을 통해 type: 'video', content: video_path로 채팅 메시지로 전송될 수 있습니다.
  • 편집 시 스케일링(720p 제한), 크롭, 트림이 동시에 적용됩니다.

4. 그룹 채팅방 생성

POST /chats/group

여러 명의 사용자가 참여할 수 있는 그룹 채팅방을 생성합니다.

Path Parameters

파라미터 타입 설명
- - 경로 파라미터 없음

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

{
  "name": "개발팀",
  "memberIds": [2, 3, 4]
}

Request Body Fields

필드 타입 필수 설명
name string 필수 채팅방 이름 (1-100자)
memberIds number[] 필수 초대할 멤버 ID 배열 (1-50명)

Response Fields

필드 타입 설명
chatRoomId number 생성된 채팅방 ID
isNewlyCreated boolean 새로 생성된 채팅방인지 여부 (true: 새로 생성됨, false: 기존 채팅방 재활용)

성공 응답 예시

{
  "code": 201,
  "message": "그룹 채팅방 생성 성공",
  "data": {
    "chatRoomId": 2
  }
}

HTTP 상태 코드

코드 설명
201 생성 성공
400 유효성 검사 실패
401 인증 실패
500 서버 오류

비고

  • 생성된 채팅방은 자동으로 group 타입으로 설정됩니다.
  • 요청자는 자동으로 멤버에 포함됩니다.
  • 중복된 멤버 ID는 허용되지 않습니다.

4. 채팅방 나가기

DELETE /chats/{chatRoomId}/members/me

현재 로그인한 사용자가 채팅방에서 나갑니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

없음

Response Fields

필드 타입 설명
success boolean 작업 성공 여부 (항상 true)

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 나가기 성공",
  "data": {
    "success": true
  }
}

HTTP 상태 코드

코드 설명
200 성공
400 잘못된 채팅방 ID
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • 1:1 채팅방에서 나가면 status가 'left'로 변경되어 목록에서 숨겨지지만 데이터는 유지됩니다 (재참여 가능).
  • 그룹 채팅방에서 나가면 완전히 삭제됩니다.
  • 그룹 채팅방에서 마지막 멤버가 나가면 채팅방이 자동 삭제됩니다.
  • 그룹 채팅방에서 나갈 때: 시스템 메시지(type: 'system')가 자동 생성되어 채팅방에 브로드캐스트됩니다.
    • 메시지 내용: {나가는 사용자 닉네임}님이 채팅방에서 나가셨습니다.
    • 마지막 멤버가 나가는 경우는 시스템 메시지가 생성되지 않습니다.

4.5. 채팅방에 사용자 초대

POST /chats/{chatRoomId}/invite

기존 채팅방에 새로운 사용자를 초대합니다. 초대 성공 시 시스템 메시지가 채팅방에 자동으로 생성됩니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

{
  "user_id": 3
}

Request Body Fields

필드 타입 필수 설명
user_id number 필수 초대할 사용자 ID

Response Fields

필드 타입 설명
success boolean 작업 성공 여부 (항상 true)

성공 응답 예시

{
  "code": 200,
  "message": "김철수님이 채팅방에 초대되었습니다.",
  "data": {
    "success": true
  }
}

오류 응답 예시

{
  "code": 400,
  "message": "잘못된 요청입니다.",
  "errors": [
    {
      "field": "user_id",
      "message": "올바른 사용자 ID를 입력해주세요."
    }
  ]
}

HTTP 상태 코드

코드 설명
200 초대 성공
400 유효성 검사 실패
401 인증 실패
403 권한 없음 (채팅방 멤버가 아님)
404 채팅방 없음
500 서버 오류

비고

  • 그룹 채팅방만 초대 가능 (1:1 채팅방은 별도 생성)
  • 초대자는 채팅방 멤버여야 함
  • 대상 사용자가 이미 멤버인 경우 초대 불가
  • 초대 성공 시 시스템 메시지(type: 'system')가 자동 생성되어 브로드캐스트됨
  • 클라이언트에서는 시스템 메시지를 특별한 UI로 표시

5. 채팅방 상세 조회

GET /chats/{chatRoomId}

채팅방 상세 정보를 조회합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

없음

Response Fields

필드 타입 설명
id number 채팅방 ID
name string? 채팅방 이름
type string 채팅방 타입
avatar_url string? 채팅방 아바타 URL (base URL 포함)
created_at string 생성 시간 (ISO 8601)
latest_notices[] array 최근 공지사항 목록 (최대 3개)
latest_notices[].notice_id number 공지사항 ID
latest_notices[].content string 공지 내용
latest_notices[].user_nickname string 작성자 닉네임
latest_notices[].created_at string 공지 작성 시간 (ISO 8601)
chat_room_images_videos[] array 채팅방 최근 이미지/비디오 목록 (최대 5개)
chat_room_images_videos[].message_id number 메시지 ID
chat_room_images_videos[].type string 메시지 타입 ("image" 또는 "video")
chat_room_images_videos[].content string 메시지 내용 (이미지/비디오 URL 등)
chat_room_images_videos[].created_at string 메시지 발신 시간 (ISO 8601)
members[] array 채팅방 멤버 목록
members[].id number ChatMember 테이블 ID
members[].user_id number User 테이블 사용자 ID
members[].joined_at string 참가 시간 (ISO 8601)
members[].user object 사용자 정보
members[].user.id number 사용자 ID
members[].user.nickname string 사용자 닉네임
members[].user.profile_img string? 프로필 이미지 URL

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 상세 조회 성공",
  "data": {
    "id": 1,
    "name": "개발팀",
    "type": "group",
    "avatar_url": "http://localhost:3001/uploads/avatar.jpg",
    "created_at": "2024-01-01T00:00:00.000Z",
    "latest_notices": [
      {
        "notice_id": 5,
        "content": "채팅방 규칙을 꼭 확인해주세요.",
        "user_nickname": "관리자",
        "created_at": "2024-09-18T02:00:00.000Z"
      },
      {
        "notice_id": 4,
        "content": "내일 팀 미팅 있습니다.",
        "user_nickname": "팀장",
        "created_at": "2024-09-17T10:30:00.000Z"
      }
    ],
    "chat_room_images_videos": [
      {
        "message_id": 100,
        "type": "image",
        "content": "http://localhost:3001/uploads-chat/2024/11/12/image123.jpg",
        "created_at": "2024-09-18T01:00:00.000Z"
      },
      {
        "message_id": 98,
        "type": "video",
        "content": "{\"video_url\":\"http://localhost:3001/uploads-chat-video/2024/11/12/video456.mp4\",\"thumbnail_url\":\"http://localhost:3001/uploads-chat-thumbnail/2024/11/12/thumb456.jpg\"}",
        "created_at": "2024-09-17T23:00:00.000Z"
      }
    ],
    "members": [
      {
        "id": 1,
        "user_id": 1,
        "joined_at": "2024-01-01T00:00:00.000Z",
        "user": {
          "id": 1,
          "nickname": "사용자1",
          "profile_img": "http://localhost:3001/uploads-profile/2024/01/15/user1.jpg"
        }
      }
    ]
  }
}

HTTP 상태 코드

코드 설명
200 성공
400 잘못된 채팅방 ID
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • latest_notices는 최대 3개의 최근 공지사항을 최신순으로 표시합니다.
  • chat_room_images_videos는 채팅방 내 image/video 타입 메시지 중 가장 최근 5개를 표시합니다.
  • 공지사항이나 미디어 파일이 없는 경우 빈 배열로 반환됩니다.
  • 멤버 목록에는 나 자신도 포함됩니다.

5.5. 채팅방 미디어 조회

GET /chats/{chatRoomId}/media

채팅방에서 최근 30일 이내의 미디어 메시지(이미지/비디오)를 최대 30개까지 조회합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
limit number 선택 최대 조회 개수 (1-30, 기본값: 30)

Request Body

없음

Response Fields

필드 타입 설명
media[] array 미디어 메시지 목록
media[].message_id number 메시지 ID
media[].type string 미디어 타입 ("image" 또는 "video")
media[].content string 미디어 파일 URL (base URL 포함)
media[].created_at string 메시지 발신 시간 (ISO 8601)
media[].sender object 발신자 정보
media[].sender.id number 발신자 ID
media[].sender.nickname string 발신자 닉네임
total_count number 전체 미디어 메시지 개수 (페이징 등에 활용)

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 미디어 조회 성공",
  "data": {
    "media": [
      {
        "message_id": 150,
        "type": "image",
        "content": "http://localhost:3001/uploads-chat/2024/11/11/image123.jpg",
        "created_at": "2024-11-11T14:30:00.000Z",
        "sender": {
          "id": 2,
          "nickname": "김철수"
        }
      },
      {
        "message_id": 145,
        "type": "video",
        "content": "{\"video_url\":\"http://localhost:3001/uploads-chat-video/2024/11/10/video456.mp4\",\"thumbnail_url\":\"http://localhost:3001/uploads-chat-thumbnail/2024/11/10/thumb456.jpg\"}",
        "created_at": "2024-11-10T09:15:00.000Z",
        "sender": {
          "id": 3,
          "nickname": "이영희"
        }
      }
    ],
    "total_count": 45
  }
}

HTTP 상태 코드

코드 설명
200 성공
400 잘못된 채팅방 ID
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • 최근 30일 이내의 미디어 메시지만 조회합니다.
  • 최대 30개까지 조회 가능하며, 기본값은 30개입니다.
  • 미디어 메시지는 최신순으로 정렬되어 반환됩니다.
  • total_count는 전체 미디어 메시지 개수를 제공하여 클라이언트에서 페이징이나 추가 로드 여부를 판단할 수 있습니다.
  • 채팅방 멤버만 조회할 수 있습니다.

6. 채팅 메시지 목록 조회

GET /chats/{chatRoomId}/messages

채팅방의 메시지 목록을 페이징으로 조회합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
cursor number 선택 페이징 커서 (기본값: 없음)
limit number 선택 가져올 개수 (1-50, 기본값: 20)

Request Body

없음

Response Fields

필드 타입 설명
messages[] array 메시지 목록
messages[].id number 메시지 ID
messages[].chat_room_id number 채팅방 ID
messages[].sender_id number 발신자 ID
messages[].type string 메시지 타입
messages[].content string? 메시지 내용
messages[].created_at string 메시지 발신 시간 (ISO 8601)
messages[].sender object 발신자 정보
messages[].sender.id number 발신자 ID
messages[].sender.nickname string 발신자 닉네임
messages[].sender.profile_img string? 발신자 프로필 이미지 URL
messages[].mentions[] array 멘션 목록
messages[].mentions[].id number 멘션 ID
messages[].mentions[].mentioned_user_id number 멘션된 사용자 ID
messages[].mentions[].mentionedUser object 멘션된 사용자 정보
messages[].mentions[].mentionedUser.id number 멘션된 사용자 ID
messages[].mentions[].mentionedUser.nickname string 멘션된 사용자 닉네임
hasNext boolean 다음 페이지 존재 여부
nextCursor number? 다음 페이지 커서 (없으면 null)

성공 응답 예시

{
  "code": 200,
  "message": "메시지 목록 조회 성공",
  "data": {
    "messages": [
      {
        "id": 100,
        "chat_room_id": 1,
        "sender_id": 2,
        "type": "text",
        "content": "안녕하세요!",
        "created_at": "2024-01-01T12:00:00.000Z",
        "sender": {
          "id": 2,
          "nickname": "김철수",
          "profile_img": "http://localhost:3001/uploads-profile/2024/01/15/user2.jpg"
        },
        "mentions": []
      },
      {
        "id": 99,
        "chat_room_id": 1,
        "sender_id": 3,
        "type": "image",
        "content": "http://localhost:3001/uploads-chat/2024/11/12/image123_1703123456789_abc123.jpg",
        "created_at": "2024-01-01T11:30:00.000Z",
        "sender": {
          "id": 3,
          "nickname": "이영희",
          "profile_img": "http://localhost:3001/uploads-profile/2024/01/15/user3.jpg"
        },
        "mentions": []
      },
      {
        "id": 98,
        "chat_room_id": 1,
        "sender_id": 2,
        "type": "video",
        "content": "{\"video_url\":\"http://localhost:3001/uploads-chat-video/2024/11/12/video_1703123456789_def456.mp4\",\"thumbnail_url\":\"http://localhost:3001/uploads-chat-thumbnail/2024/11/12/thumb_1703123456789_def456.jpg\"}",
        "created_at": "2024-01-01T11:00:00.000Z",
        "sender": {
          "id": 2,
          "nickname": "김철수",
          "profile_img": "http://localhost:3001/uploads-profile/2024/01/15/user2.jpg"
        },
        "mentions": []
      }
    ],
    "hasNext": true,
    "nextCursor": 97
  }
}

HTTP 상태 코드

코드 설명
200 성공
400 잘못된 파라미터
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • 메시지는 최신순으로 정렬되어 반환됩니다.
  • cursor가 없는 경우 가장 최신 메시지부터 조회합니다.
  • nextCursor로 다음 페이지를 조회할 수 있습니다.

7. 채팅방 공지사항 목록 조회

GET /chats/{chatRoomId}/notices

채팅방의 모든 공지사항을 조회합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

없음

Response Fields

필드 타입 설명
[].chat_room_id number 채팅방 ID
[].user_nickname string 작성자 닉네임
[].content string 공지 내용
[].created_at string 작성 시간 (ISO 8601)
[].updated_at string 수정 시간 (ISO 8601)

성공 응답 예시

{
  "code": 200,
  "message": "공지사항 목록 조회 성공",
  "data": [
    {
      "chat_room_id": 1,
      "user_nickname": "관리자",
      "content": "공지사항 내용입니다.",
      "created_at": "2024-09-18T02:00:00.000Z",
      "updated_at": "2024-09-18T02:00:00.000Z"
    }
  ]
}

HTTP 상태 코드

코드 설명
200 성공
400 잘못된 채팅방 ID
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • 공지사항은 최신순으로 정렬되어 반환됩니다.
  • 채팅방 멤버만 조회할 수 있습니다.

9. 채팅 공지사항 등록

POST /chats/{chatRoomId}/notices

채팅 내용을 채팅방의 공지사항으로 등록합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

{
  "content": "공지사항으로 등록할 채팅 내용"
}

Request Body Fields

필드 타입 필수 설명
content string 필수 공지사항 내용 (1-1000자)

Response Fields

필드 타입 설명
notice_id number 등록된 공지사항 ID
success boolean 작업 성공 여부 (항상 true)

성공 응답 예시

{
  "code": 201,
  "message": "채팅 공지사항 등록 성공",
  "data": {
    "notice_id": 5,
    "success": true
  }
}

오류 응답 예시

{
  "code": 400,
  "message": "잘못된 요청입니다.",
  "errors": [
    {
      "field": "content",
      "message": "공지사항 내용은 빈 값일 수 없습니다."
    }
  ]
}

HTTP 상태 코드

코드 설명
201 등록 성공
400 유효성 검사 실패
401 인증 실패
403 채팅방 멤버가 아님
404 채팅방 없음
500 서버 오류

비고

  • 공지사항은 자신만 등록할 수 있습니다.
  • 채팅방 멤버만 공지사항을 등록할 수 있습니다.
  • 이전 공지사항들은 유지되고, 새로운 공지사항이 추가됩니다.

10. 채팅방 수정 (그룹 채팅방만)

PUT /chats/{chatRoomId}

그룹 채팅방의 정보를 수정합니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body

{
  "name": "수정된 팀명",
  "avatar_url": "http://example.com/new-avatar.jpg"
}

Request Body Fields

필드 타입 필수 설명
name string 선택 채팅방 이름 (1-100자)
avatar_url string 선택 채팅방 아바타 URL (255자 이내)

Response Fields

필드 타입 설명
success boolean 작업 성공 여부 (항상 true)

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 수정 성공",
  "data": {
    "success": true
  }
}

HTTP 상태 코드

코드 설명
200 성공
400 유효성 검사 실패
401 인증 실패
403 권한 없음 (1:1 채팅방 또는 멤버 아님)
404 채팅방 없음
500 서버 오류

비고

  • 1:1 채팅방(private)은 수정할 수 없습니다.
  • 최소 하나의 수정 항목이 필요합니다.
  • 기존 아바타 이미지가 있는 경우 자동으로 삭제됩니다.

10.5. 채팅방 아바타 업로드

POST /chats/{chatRoomId}/avatar-upload

그룹 채팅방의 아바타 이미지를 업로드하고 설정합니다. 기존 아바타가 있는 경우 자동으로 삭제됩니다.

Path Parameters

파라미터 타입 설명
chatRoomId number 채팅방 ID

Query Parameters

파라미터 타입 필수 설명
- - - 쿼리 파라미터 없음

Request Body (multipart/form-data)

필드 타입 필수 설명
avatar file 필수 업로드할 아바타 이미지 파일 (JPG, PNG, GIF, WebP 등)

Response Fields

필드 타입 설명
avatar_url string 업로드된 아바타 이미지의 완전한 URL
path string DB에 저장된 경로
filename string 생성된 고유 파일명
size number 파일 크기 (bytes)

성공 응답 예시

{
  "code": 200,
  "message": "채팅방 아바타가 설정되었습니다.",
  "data": {
    "avatar_url": "http://localhost:3001/uploads-chat-avatars/2025/01/15/avatar_1703123456789_abc123.jpg",
    "path": "/uploads-chat-avatars/2025/01/15/avatar_1703123456789_abc123.jpg",
    "filename": "avatar_1703123456789_abc123.jpg",
    "size": 245760
  }
}

HTTP 상태 코드

코드 설명
200 업로드 성공
400 잘못된 파일 형식 또는 파일 없음
401 인증 실패
403 권한 없음 (그룹 채팅방 아님 또는 멤버가 아님)
404 채팅방 없음
413 파일 크기 초과 (10MB)
500 서버 오류

비고

  • 그룹 채팅방(group)만 아바타 설정 가능
  • 채팅방 멤버만 업로드 권한 있음
  • 지원되는 파일 형식: JPG, JPEG, PNG, GIF, WebP, HEIC, HEIF
  • 최대 파일 크기: 10MB
  • 파일은 uploads-chat-avatars/년/월/일/ 폴더에 저장됩니다.
  • 스토리지 분기: STORAGE_DRIVER 환경변수에 따라 저장소가 결정됩니다
    • 'local': 프로젝트 루트의 로컬 파일시스템에 저장
    • 'naver-cloud': 네이버 클라우드 Object Storage에 저장
  • 기존 아바타 이미지가 있는 경우 자동으로 스토리지에서 삭제됩니다.
  • 두 스토리지 타입 모두 동일한 URL 포맷을 유지하여 API 응답의 일관성을 보장합니다.

Common HTTP States

상태 코드 설명
200 성공
201 생성 성공
400 잘못된 요청 (유효성 검사 실패 등)
401 인증 실패 (유효하지 않은 토큰)
403 권한 없음 (채팅방 멤버가 아님 등)
404 리소스 없음 (채팅방 없음)
500 서버 오류

채팅방 타입별 특징

private - 1:1 채팅방

  • 최대 2명의 멤버만 참여 가능
  • name 필드는 항상 null
  • 채팅방 수정 불가
  • 나가기 시 status가 'left'로 변경되어 목록에서 사라지지만 데이터 유지 (재참여 가능)

group - 그룹 채팅방

  • 3명 이상 참여 가능
  • name 필드 필수 입력
  • 채팅방 수정 가능

인증 및 권한

  • 모든 API는 JWT 토큰 인증 필요
  • 대체로 채팅방 멤버만 접근 가능
  • 1:1 채팅방 생성 시 상대방 사용자 존재 확인 필요

스토리지 설정 (환경변수)

채팅 파일 업로드 시 스토리지 타입은 환경변수에 따라 결정됩니다.

STORAGE_DRIVER

설명 필수 환경변수
'local' 로컬 파일시스템에 저장 BASE_URL
'naver-cloud' 네이버 클라우드 Object Storage에 저장 BASE_URL, NCP_ACCESS_KEY, NCP_SECRET_KEY, NCP_REGION, NCP_ENDPOINT, NCP_BUCKET

환경변수 상세

환경변수 타입 설명 예시
STORAGE_DRIVER string 스토리지 타입 ('local' 또는 'naver-cloud') 'naver-cloud'
BASE_URL string 파일 접근을 위한 기본 URL 'http://localhost:3001'
NCP_ACCESS_KEY string 네이버 클라우드 액세스 키 (네이버 클라우드 전용) 'your-access-key'
NCP_SECRET_KEY string 네이버 클라우드 시크릿 키 (네이버 클라우드 전용) 'your-secret-key'
NCP_REGION string 네이버 클라우드 리전 (네이버 클라우드 전용) 'kr-standard'
NCP_ENDPOINT string 네이버 클라우드 엔드포인트 (네이버 클라우드 전용) 'https://kr.object.ncloudstorage.com'
NCP_BUCKET string 네이버 클라우드 버킷 이름 (네이버 클라우드 전용) 'your-bucket-name'

스토리지별 특징

  • 로컬 스토리지: 프로젝트 루트 디렉토리에 직접 파일 저장
  • 네이버 클라우드: Object Storage에 파일 저장, 고가용성 및 확장성 제공
  • URL 일관성: 두 스토리지 타입 모두 동일한 URL 포맷 사용으로 클라이언트 변경 불필요