Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
import lombok.RequiredArgsConstructor;
import org.springframework.messaging.handler.annotation.MessageMapping;
import org.springframework.messaging.simp.SimpMessagingTemplate;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;

Expand All @@ -19,16 +21,21 @@ public class ChatController {

private final ChatService chatService;

@GetMapping("/chat/history/{userId}")
public List<ChatResponse> getHistory(@PathVariable Long userId) {
return chatService.getHistory(userId);
}

@MessageMapping("/chat.send") // 클라이언트 → /app/chat.send
public void handleChat(ChatRequest request, @LoginUser Users loginUser) {
public void handleChat(ChatRequest request) {
// 1) 유저 메시지 저장 + 클라이언트에게 에코
ChatResponse chatResponse = chatService.saveUserMessage(loginUser, request);
template.convertAndSend("/sub/" + loginUser.getUserId(), chatResponse);
ChatResponse chatResponse = chatService.saveUserMessage(request);
template.convertAndSend("/sub/" + request.getUserId(), chatResponse);

// 2) LLM 호출 & 응답 저장 + 브로드캐스트 (동기 방식)
List<ChatResponse> llmResponses = chatService.askAI(loginUser, request);
List<ChatResponse> llmResponses = chatService.askAI(request);
llmResponses.forEach(aiResp ->
template.convertAndSend("/sub/" + loginUser.getUserId(), aiResp)
template.convertAndSend("/sub/" + request.getUserId(), aiResp)
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,16 @@
@NoArgsConstructor
public class ChatRequest {

private Long userId;

private String message;

private ChatRequest(String message) {
private ChatRequest(Long userId, String message) {
this.userId = userId;
this.message = message;
}

public static ChatRequest of(String message) {
return new ChatRequest(message);
public static ChatRequest of(Long userId, String message) {
return new ChatRequest(userId, message);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ private LLMRequest(Long userId, String message, List<Chat> history) {
this.history = history;
}

public static LLMRequest of(Users loginUser, ChatRequest request, List<Chat> history) {
return new LLMRequest(loginUser.getUserId(), request.getMessage(), history);
public static LLMRequest of(ChatRequest request, List<Chat> history) {
return new LLMRequest(request.getUserId(), request.getMessage(), history);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -42,8 +42,8 @@ private Chat(Long userId, ChatRole role, String message) {
this.message = message;
}

public static Chat of(Users user, ChatRequest request, ChatRole role) {
return new Chat(user.getUserId(), role, request.getMessage());
public static Chat of(ChatRequest request) {
return new Chat(request.getUserId(), ChatRole.USER, request.getMessage());
}

public static Chat of(ChatResponse response) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,36 +7,46 @@
import MathCaptain.weakness.domain.User.entity.Users;
import MathCaptain.weakness.domain.common.enums.ChatRole;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.UUID;

@Slf4j
@Service
@RequiredArgsConstructor
@Transactional(readOnly = true)
public class ChatService {

public static final ChatRole USER = ChatRole.USER;
private final ChatRepository chatRepository;
private final LLMClient llm;

@Transactional
public ChatResponse saveUserMessage(Users loginUser, ChatRequest request) {
Chat message = Chat.of(loginUser, request, USER);
public ChatResponse saveUserMessage(ChatRequest request) {
log.info("userid {}", request.getUserId());
log.info("message {}", request.getMessage());
Chat message = Chat.of(request);
Chat saved = chatRepository.save(message);
return ChatResponse.of(saved);
}

public List<ChatResponse> askAI(Users loginUser, ChatRequest request) {
List<Chat> history = chatRepository.findAllByUserIdOrderBySendTimeAsc(loginUser.getUserId());
List<Chat> aiChats = llm.call(loginUser, history, request);
public List<ChatResponse> askAI(ChatRequest request) {
List<Chat> history = chatRepository.findAllByUserIdOrderBySendTimeAsc(request.getUserId());
List<Chat> aiChats = llm.call(history, request);
return aiChats.stream()
.map(this::storeAndTransform)
.toList();
}

@Transactional
public List<ChatResponse> getHistory(Long userId) {
List<Chat> history = chatRepository.findAllByUserIdOrderBySendTimeAsc(userId);
return history.stream()
.map(ChatResponse::of)
.toList();
}

private ChatResponse storeAndTransform(Chat message) {
Chat saved = chatRepository.save(message);
return ChatResponse.of(saved);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,9 +31,9 @@ public class LLMClient {
@Value("${llm.server.url}")
private String baseUrl;

public List<Chat> call(Users loginUser, List<Chat> history, ChatRequest request) {
public List<Chat> call(List<Chat> history, ChatRequest request) {
try {
LLMRequest llmRequest = LLMRequest.of(loginUser, request, history);
LLMRequest llmRequest = LLMRequest.of(request, history);

ResponseEntity<ChatResponse[]> response = restTemplate.postForEntity(
// TODO : 엔드포인트 수정
Expand Down