feat(chat-room): sendMessage 응답 다건 변경 반영
- TalkApi.sendMessage: ApiResponse<List<ServerChatMessage>>로 변경 - ChatRepository.sendMessage: Single<List<ServerChatMessage>>로 변경. 로컬 SENDING→SENT 업데이트 후, 응답 메시지 전체를 DB에 저장 - ChatRoomActivity: 구독부에서 List를 처리하며 mine == false(AI) 메시지들만 순서대로 append. 타이핑 인디케이터는 성공/실패 시 동일하게 제거
This commit is contained in:
@@ -40,7 +40,7 @@ interface TalkApi {
|
||||
@Header("Authorization") authHeader: String,
|
||||
@Path("roomId") roomId: Long,
|
||||
@Body request: SendMessageRequest
|
||||
): Single<ApiResponse<ServerChatMessage>>
|
||||
): Single<ApiResponse<List<ServerChatMessage>>>
|
||||
|
||||
// 점진적 메시지 로딩 API
|
||||
@GET("/api/chat/rooms/{roomId}/messages")
|
||||
|
||||
@@ -30,7 +30,7 @@ class ChatRepository(
|
||||
roomId: Long,
|
||||
localId: String,
|
||||
content: String
|
||||
): Single<ServerChatMessage> {
|
||||
): Single<List<ServerChatMessage>> {
|
||||
return talkApi.sendMessage(
|
||||
authHeader = token,
|
||||
roomId = roomId,
|
||||
@@ -38,18 +38,18 @@ class ChatRepository(
|
||||
)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.map { ensureSuccess(it) }
|
||||
.flatMap { serverMsg ->
|
||||
.flatMap { serverMsgs ->
|
||||
// 1) 로컬에 사용자 메시지 상태를 SENT로 업데이트
|
||||
val updateStatus = Completable.fromAction {
|
||||
kotlinx.coroutines.runBlocking { chatDao.updateStatusByLocalId(roomId, localId, MessageStatus.SENT.name) }
|
||||
}
|
||||
// 2) 서버 응답 메시지를 로컬 DB에 저장(중복 방지: 동일 ID는 REPLACE)
|
||||
val insertServer = Completable.fromAction {
|
||||
val entity = serverMsg.toEntity(roomId)
|
||||
kotlinx.coroutines.runBlocking { chatDao.insertMessage(entity) }
|
||||
// 2) 서버 응답 메시지들을 로컬 DB에 저장(중복 방지: 동일 ID는 REPLACE)
|
||||
val insertServers = Completable.fromAction {
|
||||
val entities = serverMsgs.map { it.toEntity(roomId) }
|
||||
kotlinx.coroutines.runBlocking { chatDao.insertMessages(entities) }
|
||||
}
|
||||
updateStatus.andThen(insertServer)
|
||||
.andThen(Single.just(serverMsg))
|
||||
updateStatus.andThen(insertServers)
|
||||
.andThen(Single.just(serverMsgs))
|
||||
.subscribeOn(Schedulers.io())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -285,15 +285,17 @@ class ChatRoomActivity : BaseActivity<ActivityChatRoomBinding>(
|
||||
content = content
|
||||
)
|
||||
.observeOn(io.reactivex.rxjava3.android.schedulers.AndroidSchedulers.mainThread())
|
||||
.subscribe({ serverMsg ->
|
||||
.subscribe({ serverMsgs ->
|
||||
// 성공: 타이핑 인디케이터 제거 및 상태 업데이트
|
||||
chatAdapter.hideTypingIndicator()
|
||||
updateUserMessageStatus(localId, MessageStatus.SENT)
|
||||
|
||||
// 서버 응답이 AI 메시지인 경우 리스트에 추가
|
||||
val domain = serverMsg.toDomain()
|
||||
if (!domain.mine) {
|
||||
appendMessage(ChatListItem.AiMessage(domain, characterInfo?.name))
|
||||
// 서버 응답이 여러 개인 경우, mine == false(AI)만 순서대로 추가
|
||||
serverMsgs.forEach { msg ->
|
||||
val domain = msg.toDomain()
|
||||
if (!domain.mine) {
|
||||
appendMessage(ChatListItem.AiMessage(domain, characterInfo?.name))
|
||||
}
|
||||
}
|
||||
}, { error ->
|
||||
// 실패: 타이핑 인디케이터 제거 및 FAILED로 업데이트
|
||||
|
||||
Reference in New Issue
Block a user