From 08ced510449f3da928d0f927201de47f9eaaa732 Mon Sep 17 00:00:00 2001 From: okod Date: Sun, 9 Jun 2024 03:50:43 +0900 Subject: [PATCH 1/5] fix: Modify S3 Filename to randomUUID --- src/main/java/vom/spring/domain/album/AlbumService.java | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/main/java/vom/spring/domain/album/AlbumService.java b/src/main/java/vom/spring/domain/album/AlbumService.java index a3f753e..8444b56 100644 --- a/src/main/java/vom/spring/domain/album/AlbumService.java +++ b/src/main/java/vom/spring/domain/album/AlbumService.java @@ -16,6 +16,7 @@ import java.io.IOException; import java.time.LocalDateTime; import java.util.List; +import java.util.UUID; import java.util.stream.Collectors; @Service @@ -41,19 +42,21 @@ public void setS3Client(AmazonS3Client amazonS3Client) { @Transactional public void uploadAlbum(Long memberId, MultipartFile multipartFile) throws IOException { Homepy homepy = homepyRepository.findByMember_id(memberId); + String originalFilename = multipartFile.getOriginalFilename(); + String uniqueFilename = UUID.randomUUID().toString(); ObjectMetadata metadata = new ObjectMetadata(); metadata.setContentLength(multipartFile.getSize()); metadata.setContentType(multipartFile.getContentType()); - amazonS3Client.putObject(bucket, originalFilename, multipartFile.getInputStream(), metadata); + amazonS3Client.putObject(bucket, uniqueFilename, multipartFile.getInputStream(), metadata); albumRepository.save( Album.builder() .homepy(homepy) .name(originalFilename) - .img_url(amazonS3Client.getUrl(bucket, originalFilename).toString()) + .img_url(amazonS3Client.getUrl(bucket, uniqueFilename).toString()) .createdAt(LocalDateTime.now()) .build() ); From 2c729693183b23125ba2dcd8944580e3e73c3a86 Mon Sep 17 00:00:00 2001 From: Ojimin Date: Sun, 9 Jun 2024 19:51:22 +0900 Subject: [PATCH 2/5] =?UTF-8?q?feat:=20webcam=20=EB=B0=A9=EC=83=9D?= =?UTF-8?q?=EC=84=B1=20=EC=88=98=EC=A0=95=20=EB=B0=8F=20=EB=B0=A9=EC=82=AD?= =?UTF-8?q?=EC=A0=9C=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../webcam/controller/WebcamController.java | 23 ++- .../spring/domain/webcam/domain/Message.java | 4 +- .../domain/webcam/dto/WebcamRequestDto.java | 8 + .../repository/MemberWebcamRepository.java | 6 +- .../webcam/repository/WebcamRepository.java | 6 + .../domain/webcam/service/WebcamServcie.java | 1 + .../webcam/service/WebcamServiceImpl.java | 13 ++ .../spring/global/config/StompPreHandler.java | 162 +++++++++--------- 8 files changed, 135 insertions(+), 88 deletions(-) diff --git a/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java b/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java index bd20e35..c2cd124 100644 --- a/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java +++ b/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java @@ -16,10 +16,7 @@ import org.springframework.messaging.simp.SimpMessageHeaderAccessor; import org.springframework.messaging.simp.SimpMessagingTemplate; import org.springframework.web.ErrorResponse; -import org.springframework.web.bind.annotation.PostMapping; -import org.springframework.web.bind.annotation.RequestBody; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.bind.annotation.*; import vom.spring.domain.webcam.domain.Message; import vom.spring.domain.webcam.dto.WebcamRequestDto; import vom.spring.domain.webcam.dto.WebcamResponseDto; @@ -111,4 +108,22 @@ public void PeerHandleAnswer(@Payload Message message, SimpMessageHeaderAccessor // public String sendKey(@Payload String message) { // return message; // } + + /** + * 방 삭제 + */ + @Operation(summary = "화상채팅 방을 삭제합니다", description = "화상채팅 방을 삭제합니다", + responses = { + @ApiResponse(responseCode = "200", description = "화상채팅 방을 삭제했습니다."), + @ApiResponse(responseCode = "400", description = "채팅 방을 삭제하지 못했습니다.", + content = @Content(schema = @Schema(implementation = ErrorResponse.class))), + @ApiResponse(responseCode = "404", description = "채팅 방을 찾지 못했습니다", + content = @Content(schema = @Schema(implementation = ErrorResponse.class))) + }) + @DeleteMapping("/api/webcam") + public ResponseEntity deleteWebcamRoom(@RequestBody WebcamRequestDto.DeleteWebcamDto request) { + System.out.print("방id: " + request.getRoomId()); + webcamServcie.deleteWebcamRoom(request); + return ResponseEntity.status(HttpStatus.OK).build(); + } } diff --git a/src/main/java/vom/spring/domain/webcam/domain/Message.java b/src/main/java/vom/spring/domain/webcam/domain/Message.java index 67a91cf..7d035d3 100644 --- a/src/main/java/vom/spring/domain/webcam/domain/Message.java +++ b/src/main/java/vom/spring/domain/webcam/domain/Message.java @@ -14,8 +14,8 @@ public class Message { @Enumerated(EnumType.STRING) private Type type; - private String webcamId; - private String sender; + private Long webcamId; + private Long sender; private Object offer; private Object answer; private Object ice; diff --git a/src/main/java/vom/spring/domain/webcam/dto/WebcamRequestDto.java b/src/main/java/vom/spring/domain/webcam/dto/WebcamRequestDto.java index f820180..80e3cb1 100644 --- a/src/main/java/vom/spring/domain/webcam/dto/WebcamRequestDto.java +++ b/src/main/java/vom/spring/domain/webcam/dto/WebcamRequestDto.java @@ -10,4 +10,12 @@ public class WebcamRequestDto { public static class CreateWebcamDto { private Long toMemberId; //화상 채팅 요청받은 유저의 id } + + @Builder + @Getter + @NoArgsConstructor(access = AccessLevel.PRIVATE) + @AllArgsConstructor(access = AccessLevel.PRIVATE) + public static class DeleteWebcamDto { + private Long roomId; + } } diff --git a/src/main/java/vom/spring/domain/webcam/repository/MemberWebcamRepository.java b/src/main/java/vom/spring/domain/webcam/repository/MemberWebcamRepository.java index 34f2966..a0844e9 100644 --- a/src/main/java/vom/spring/domain/webcam/repository/MemberWebcamRepository.java +++ b/src/main/java/vom/spring/domain/webcam/repository/MemberWebcamRepository.java @@ -2,7 +2,11 @@ import org.springframework.data.jpa.repository.JpaRepository; import vom.spring.domain.webcam.domain.MemberWebcam; +import vom.spring.domain.webcam.domain.Webcam; + +import java.util.List; +import java.util.Optional; public interface MemberWebcamRepository extends JpaRepository { - + void deleteByWebcam(Webcam webcam); } diff --git a/src/main/java/vom/spring/domain/webcam/repository/WebcamRepository.java b/src/main/java/vom/spring/domain/webcam/repository/WebcamRepository.java index 9c55ba5..a3dde98 100644 --- a/src/main/java/vom/spring/domain/webcam/repository/WebcamRepository.java +++ b/src/main/java/vom/spring/domain/webcam/repository/WebcamRepository.java @@ -3,5 +3,11 @@ import org.springframework.data.jpa.repository.JpaRepository; import vom.spring.domain.webcam.domain.Webcam; +import java.util.Optional; + public interface WebcamRepository extends JpaRepository { + + Optional findById(Long webcamId); + + void deleteById(Long webcamId); } diff --git a/src/main/java/vom/spring/domain/webcam/service/WebcamServcie.java b/src/main/java/vom/spring/domain/webcam/service/WebcamServcie.java index 570500f..a72aa22 100644 --- a/src/main/java/vom/spring/domain/webcam/service/WebcamServcie.java +++ b/src/main/java/vom/spring/domain/webcam/service/WebcamServcie.java @@ -5,4 +5,5 @@ public interface WebcamServcie { WebcamResponseDto.CreateWebcamDto createWebcamRoom(WebcamRequestDto.CreateWebcamDto request); + void deleteWebcamRoom(WebcamRequestDto.DeleteWebcamDto request); } diff --git a/src/main/java/vom/spring/domain/webcam/service/WebcamServiceImpl.java b/src/main/java/vom/spring/domain/webcam/service/WebcamServiceImpl.java index a8ff246..f8ba1d8 100644 --- a/src/main/java/vom/spring/domain/webcam/service/WebcamServiceImpl.java +++ b/src/main/java/vom/spring/domain/webcam/service/WebcamServiceImpl.java @@ -42,4 +42,17 @@ public WebcamResponseDto.CreateWebcamDto createWebcamRoom(WebcamRequestDto.Creat memberWebcamRepository.save(toMemberWebcam); return WebcamResponseDto.CreateWebcamDto.builder().webcamId(newWebcam.getId()).build(); } + + @Transactional + @Override + public void deleteWebcamRoom(WebcamRequestDto.DeleteWebcamDto request) { + String email = SecurityContextHolder.getContext().getAuthentication().getName(); //현재 접속 유저 정보 가져오기 + Member fromMember = memberRepository.findByEmail(email).orElseThrow(() -> new RuntimeException("존재하지 않은 유저입니다")); + //해당 방 찾기 + Webcam webcam = webcamRepository.findById(request.getRoomId()).orElseThrow(() -> new IllegalArgumentException("존재하지 않은 방입니다")); + //해당 방 관련 연관관계 삭제 + memberWebcamRepository.deleteByWebcam(webcam); + //해당 방 삭제 + webcamRepository.deleteById(webcam.getId()); + } } diff --git a/src/main/java/vom/spring/global/config/StompPreHandler.java b/src/main/java/vom/spring/global/config/StompPreHandler.java index f067789..0309ce2 100644 --- a/src/main/java/vom/spring/global/config/StompPreHandler.java +++ b/src/main/java/vom/spring/global/config/StompPreHandler.java @@ -1,81 +1,81 @@ -//package vom.spring.global.config; -// -//import com.fasterxml.jackson.core.JsonProcessingException; -//import io.jsonwebtoken.MalformedJwtException; -//import lombok.RequiredArgsConstructor; -//import lombok.extern.slf4j.Slf4j; -//import org.springframework.context.annotation.Configuration; -//import org.springframework.messaging.Message; -//import org.springframework.messaging.MessageChannel; -//import org.springframework.messaging.MessageDeliveryException; -//import org.springframework.messaging.simp.stomp.StompCommand; -//import org.springframework.messaging.simp.stomp.StompHeaderAccessor; -//import org.springframework.messaging.support.ChannelInterceptor; -//import org.springframework.messaging.support.MessageHeaderAccessor; -//import org.springframework.security.authentication.UsernamePasswordAuthenticationToken; -//import org.springframework.security.core.Authentication; -//import org.springframework.security.core.context.SecurityContextHolder; -//import vom.spring.global.jwt.JwtTokenProvider; -// -//@Configuration -//@RequiredArgsConstructor -//@Slf4j -//public class StompPreHandler implements ChannelInterceptor { -// -// private final JwtTokenProvider jwtTokenProvider; -// private String token; -// private Long memberId = 0L; -// @Override -// public Message preSend(Message message, MessageChannel channel) { -// try { -// StompHeaderAccessor headerAccessor = MessageHeaderAccessor.getAccessor(message, StompHeaderAccessor.class); -// String authorizationHeader = String.valueOf(headerAccessor.getNativeHeader("Authorization")); -// StompCommand command = headerAccessor.getCommand(); -// if (command.equals(StompCommand.UNSUBSCRIBE) || command.equals(StompCommand.MESSAGE) || command.equals(StompCommand.CONNECTED) || command.equals(StompCommand.SEND)) -// return message; -// else if (command.equals(StompCommand.ERROR)) { -// log.error("메시지 에러"); -// throw new MessageDeliveryException("error"); -// } -// if (authorizationHeader == null) { -// log.info("chat header가 없는 요청입니다."); -// throw new MalformedJwtException("jwt"); -// } -// // 토큰 추출 -// token = ""; -// String authorizationHeaderStr = authorizationHeader.replace("[","").replace("]",""); -// if (authorizationHeaderStr.startsWith("Bearer ")) { -// token = authorizationHeaderStr.replace("Bearer ", ""); -// } else { -// log.error("Authorization 헤더 형식이 틀립니다. : {}", authorizationHeader); -// throw new MalformedJwtException("jwt"); -// } -// //memberId 추출 -// try { -// memberId = jwtTokenProvider.getMemberId(token); -// -// } catch (Exception e) { -// throw new MalformedJwtException("stomp_jwt"); -// } -// //토큰 유효검증 -// if (jwtTokenProvider.validateAccessToken(token)) {//access token 검증 -// setAuthentication(message, headerAccessor); -// log.info("인증 성공"); -// } -// } catch (Exception e) { -// log.error("JWT에러"); -// throw new MalformedJwtException("jwt"); -// } -// return message; -// } -// -// /** -// * Security ContextHolder에 인증 정보 담아두기 -// */ -// private void setAuthentication(Message message, StompHeaderAccessor headerAccessor) { -//// UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(memberId, null, List.of(new SimpleGrantedAuthority(MemberRole.USER.name()))); -// Authentication authentication = jwtTokenProvider.getAuthentication(token); -// SecurityContextHolder.getContext().setAuthentication(authentication); -// headerAccessor.setUser(authentication); -// } -//} +package vom.spring.global.config; + +import com.fasterxml.jackson.core.JsonProcessingException; +import io.jsonwebtoken.MalformedJwtException; +import lombok.RequiredArgsConstructor; +import lombok.extern.slf4j.Slf4j; +import org.springframework.context.annotation.Configuration; +import org.springframework.messaging.Message; +import org.springframework.messaging.MessageChannel; +import org.springframework.messaging.MessageDeliveryException; +import org.springframework.messaging.simp.stomp.StompCommand; +import org.springframework.messaging.simp.stomp.StompHeaderAccessor; +import org.springframework.messaging.support.ChannelInterceptor; +import org.springframework.messaging.support.MessageHeaderAccessor; +import org.springframework.security.authentication.UsernamePasswordAuthenticationToken; +import org.springframework.security.core.Authentication; +import org.springframework.security.core.context.SecurityContextHolder; +import vom.spring.global.jwt.JwtTokenProvider; + +@Configuration +@RequiredArgsConstructor +@Slf4j +public class StompPreHandler implements ChannelInterceptor { + + private final JwtTokenProvider jwtTokenProvider; + private String token; + private Long memberId = 0L; + @Override + public Message preSend(Message message, MessageChannel channel) { + try { + StompHeaderAccessor headerAccessor = MessageHeaderAccessor.getAccessor(message, StompHeaderAccessor.class); + String authorizationHeader = String.valueOf(headerAccessor.getNativeHeader("Authorization")); + StompCommand command = headerAccessor.getCommand(); + if (command.equals(StompCommand.UNSUBSCRIBE) || command.equals(StompCommand.MESSAGE) || command.equals(StompCommand.CONNECTED) || command.equals(StompCommand.SEND)) + return message; + else if (command.equals(StompCommand.ERROR)) { + log.error("메시지 에러"); + throw new MessageDeliveryException("error"); + } + if (authorizationHeader == null) { + log.info("chat header가 없는 요청입니다."); + throw new MalformedJwtException("jwt"); + } + // 토큰 추출 + token = ""; + String authorizationHeaderStr = authorizationHeader.replace("[","").replace("]",""); + if (authorizationHeaderStr.startsWith("Bearer ")) { + token = authorizationHeaderStr.replace("Bearer ", ""); + } else { + log.error("Authorization 헤더 형식이 틀립니다. : {}", authorizationHeader); + throw new MalformedJwtException("jwt"); + } + //memberId 추출 + try { + memberId = jwtTokenProvider.getMemberId(token); + + } catch (Exception e) { + throw new MalformedJwtException("stomp_jwt"); + } + //토큰 유효검증 + if (jwtTokenProvider.validateAccessToken(token)) {//access token 검증 + setAuthentication(message, headerAccessor); + log.info("인증 성공"); + } + } catch (Exception e) { + log.error("JWT에러"); + throw new MalformedJwtException("jwt"); + } + return message; + } + + /** + * Security ContextHolder에 인증 정보 담아두기 + */ + private void setAuthentication(Message message, StompHeaderAccessor headerAccessor) { +// UsernamePasswordAuthenticationToken authentication = new UsernamePasswordAuthenticationToken(memberId, null, List.of(new SimpleGrantedAuthority(MemberRole.USER.name()))); + Authentication authentication = jwtTokenProvider.getAuthentication(token); + SecurityContextHolder.getContext().setAuthentication(authentication); + headerAccessor.setUser(authentication); + } +} From 00b114f634496420be174b3d74480cc90b28d360 Mon Sep 17 00:00:00 2001 From: Ojimin Date: Tue, 11 Jun 2024 02:07:12 +0900 Subject: [PATCH 3/5] =?UTF-8?q?feat:=20signaling=20=EC=84=9C=EB=B2=84=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../webcam/controller/WebcamController.java | 75 ++++++++++--------- .../spring/domain/webcam/domain/Message.java | 4 +- .../vom/spring/global/config/WebConfig.java | 3 + 3 files changed, 44 insertions(+), 38 deletions(-) diff --git a/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java b/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java index c2cd124..8727c69 100644 --- a/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java +++ b/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java @@ -22,14 +22,13 @@ import vom.spring.domain.webcam.dto.WebcamResponseDto; import vom.spring.domain.webcam.service.WebcamServcie; -@Tag(name = "화상채팅(시그널링) API", description = "유저 API 명세서") +@Tag(name = "화상채팅(시그널링) API", description = "화상채팅 API 명세서") @RestController @RequiredArgsConstructor @Slf4j -//db에 webcam 업데이트 로직 필요 public class WebcamController { private final WebcamServcie webcamServcie; - private final SimpMessagingTemplate messagingTemplate; +// private final SimpMessagingTemplate messagingTemplate; /** * 방 생성 */ @@ -49,60 +48,64 @@ public ResponseEntity createWebcamRoom(@Reque /** * offer 정보를 주고받기 - step 5에서 offer를 받고 구독하고 있는 client들에게 전송 */ +// @MessageMapping("/peer/offer/{camKey}/{webcamId}") //해당 경로로 메시지가 날아오면 해당 메서드 실행해서 리턴, /app/~~이런식으로 전달된다 +// @SendTo("/topic/peer/offer/{camKey}/{webcamId}") +// //camKey : 각 요청하는 캠의 key , roomId : 룸 아이디 =>룸 id를 webcam id로 수정 +// public String PeerHandleOffer(@Payload String offer, @DestinationVariable(value = "webcamId") String webcamId, @DestinationVariable(value = "camKey") String camKey) { +// log.info("[OFFER] {} : {}", camKey, offer); +//// messagingTemplate.convertAndSend("/topic/peer/offer/" +message.getWebcamId(), message); +// return offer; +// } @MessageMapping("/peer/offer/{webcamId}") //해당 경로로 메시지가 날아오면 해당 메서드 실행해서 리턴, /app/~~이런식으로 전달된다 - //camKey : 각 요청하는 캠의 key , roomId : 룸 아이디 =>룸 id를 webcam id로 수정 - public void PeerHandleOffer(@Payload Message message, SimpMessageHeaderAccessor headerAccessor) { - log.info("offer받은 webcamId:"+ message.getWebcamId()+"offer받은 sender:"+ message.getSender()); - messagingTemplate.convertAndSend("/topic/peer/offer/" +message.getWebcamId(), message); + @SendTo("/topic/peer/offer/{webcamId}") + public Message PeerHandleOffer(Message message, @DestinationVariable(value = "webcamId") String webcamId) { + log.info("offer 메세지 왔다, sender: {}, 전달할 webcamId는: {}", message.getSender(),message.getWebcamId()); +// messagingTemplate.convertAndSend("/topic/peer/offer/" +message.getWebcamId(), message); + return message; } /** * iceCandidate 정보를 주고 받기 위한 websocket */ @MessageMapping("/peer/iceCandidate/{webcamId}") - public void PeerHandleIceCandidate(@Payload Message message, SimpMessageHeaderAccessor headerAccessor) { - log.info("ice받은 webcamId:"+ message.getWebcamId()+"ice받은 sender:"+ message.getSender()); - messagingTemplate.convertAndSend("/topic/peer/iceCandidate/" + message.getWebcamId(), message); + @SendTo("/topic/peer/iceCandidate/{webcamId}") + public Message PeerHandleIceCandidate(Message message, @DestinationVariable(value = "webcamId") String webcamId) { + log.info("[ICECANDIDATE] sender: {}, candidate 정보: {}, 전달할 webcamId: {}", message.getSender(), message.getIce(), message.getWebcamId()); +// messagingTemplate.convertAndSend("/topic/peer/iceCandidate/" + message.getWebcamId(), message); + return message; } /** * answer 정보 주고받기 */ +// @MessageMapping("/peer/answer/{webcamId}") +// @SendTo("/topic/peer/answer/{camKey}/{webcamId}") +// public String PeerHandleAnswer(@Payload String answer, @DestinationVariable(value = "webcamId") String webcamId, @DestinationVariable(value = "camKey") String camKey) { +// log.info("[ANSWER] {} : {}", camKey, answer); +//// messagingTemplate.convertAndSend("/topic/peer/answer/" + message.getWebcamId(), message); +// return answer; +// } @MessageMapping("/peer/answer/{webcamId}") - public void PeerHandleAnswer(@Payload Message message, SimpMessageHeaderAccessor simpMessageHeaderAccessor ) { - log.info("answer받은 webcamId:"+ message.getWebcamId()+"answer받은 sender:"+ message.getSender()); - messagingTemplate.convertAndSend("/topic/peer/answer/" + message.getWebcamId(), message); + @SendTo("/topic/peer/answer/{webcamId}") + public Message PeerHandleAnswer(Message message, @DestinationVariable(value = "webcamId") String webcamId) { + log.info("[ANSWER] sender: {}, 전달할 곳 : {} ", message.getSender(), message.getAnswer()); +// messagingTemplate.convertAndSend("/topic/peer/answer/" + message.getWebcamId(), message); + return message; } -// /** -// * camKey 를 받기위해 신호를 보내는 webSocket -// */ -// @Operation(summary = "camKey를 받기 위해 신호를 보냄", description = "client의 camKey 정보를 주고 받기 위해 신호를 보냅니다", -// responses = { -// @ApiResponse(responseCode = "201", description = "계정 생성 완료"), -// @ApiResponse(responseCode = "400", description = "존재하지 않은 직업, 존재하지 않은 주소", -// content = @Content(schema = @Schema(implementation = ErrorResponse.class))), -// @ApiResponse(responseCode = "409", description = "올바르지 않은 닉네임, 올바르지 않은 이메일", -// content = @Content(schema = @Schema(implementation = ErrorResponse.class))) -// }) + /** + * camKey 를 받기위해 신호를 보내는 webSocket + */ // @MessageMapping("/call/key") // @SendTo("/topic/call/key") // public String callKey(@Payload String message) { // log.info("[Key] : {}", message); // return message; // } -// -// /** -// * 자신의 camKey 를 모든 연결된 세션에 보내는 webSocket -// */ -// @Operation(summary = "camKey를 모든 연결된 세션에 보냄", description = "client의 camKey를 연결된 모든 peer에게 보냅니다", -// responses = { -// @ApiResponse(responseCode = "200", description = "계정 생성 완료"), -// @ApiResponse(responseCode = "400", description = "존재하지 않은 직업, 존재하지 않은 주소", -// content = @Content(schema = @Schema(implementation = ErrorResponse.class))), -// @ApiResponse(responseCode = "409", description = "올바르지 않은 닉네임, 올바르지 않은 이메일", -// content = @Content(schema = @Schema(implementation = ErrorResponse.class))) -// }) + + /** + * 자신의 camKey 를 모든 연결된 세션에 보내는 webSocket + */ // @MessageMapping("/send/key") // @SendTo("/topic/send/key") // public String sendKey(@Payload String message) { diff --git a/src/main/java/vom/spring/domain/webcam/domain/Message.java b/src/main/java/vom/spring/domain/webcam/domain/Message.java index 7d035d3..67a91cf 100644 --- a/src/main/java/vom/spring/domain/webcam/domain/Message.java +++ b/src/main/java/vom/spring/domain/webcam/domain/Message.java @@ -14,8 +14,8 @@ public class Message { @Enumerated(EnumType.STRING) private Type type; - private Long webcamId; - private Long sender; + private String webcamId; + private String sender; private Object offer; private Object answer; private Object ice; diff --git a/src/main/java/vom/spring/global/config/WebConfig.java b/src/main/java/vom/spring/global/config/WebConfig.java index 650e6cd..d13f264 100644 --- a/src/main/java/vom/spring/global/config/WebConfig.java +++ b/src/main/java/vom/spring/global/config/WebConfig.java @@ -39,6 +39,9 @@ public void addInterceptors(InterceptorRegistry registry) { "/api/auth/**", "/api/members/join", "/api/members/join/nickname", + "/topic/**", + "/app/**", + "/signaling", "/", "/swagger-ui/index.html", "/swagger-ui.html", From faae983dcfb97f749b9dd09ac23fd04f2f72bc49 Mon Sep 17 00:00:00 2001 From: Ojimin Date: Wed, 12 Jun 2024 01:30:35 +0900 Subject: [PATCH 4/5] =?UTF-8?q?feat:=20=EB=B0=A9=EB=82=98=EA=B0=80?= =?UTF-8?q?=EA=B8=B0=20message=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../webcam/controller/WebcamController.java | 39 ++++--------------- .../vom/spring/domain/webcam/domain/Type.java | 2 +- 2 files changed, 9 insertions(+), 32 deletions(-) diff --git a/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java b/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java index 8727c69..801b665 100644 --- a/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java +++ b/src/main/java/vom/spring/domain/webcam/controller/WebcamController.java @@ -48,14 +48,6 @@ public ResponseEntity createWebcamRoom(@Reque /** * offer 정보를 주고받기 - step 5에서 offer를 받고 구독하고 있는 client들에게 전송 */ -// @MessageMapping("/peer/offer/{camKey}/{webcamId}") //해당 경로로 메시지가 날아오면 해당 메서드 실행해서 리턴, /app/~~이런식으로 전달된다 -// @SendTo("/topic/peer/offer/{camKey}/{webcamId}") -// //camKey : 각 요청하는 캠의 key , roomId : 룸 아이디 =>룸 id를 webcam id로 수정 -// public String PeerHandleOffer(@Payload String offer, @DestinationVariable(value = "webcamId") String webcamId, @DestinationVariable(value = "camKey") String camKey) { -// log.info("[OFFER] {} : {}", camKey, offer); -//// messagingTemplate.convertAndSend("/topic/peer/offer/" +message.getWebcamId(), message); -// return offer; -// } @MessageMapping("/peer/offer/{webcamId}") //해당 경로로 메시지가 날아오면 해당 메서드 실행해서 리턴, /app/~~이런식으로 전달된다 @SendTo("/topic/peer/offer/{webcamId}") public Message PeerHandleOffer(Message message, @DestinationVariable(value = "webcamId") String webcamId) { @@ -78,13 +70,6 @@ public Message PeerHandleIceCandidate(Message message, @DestinationVariable(valu /** * answer 정보 주고받기 */ -// @MessageMapping("/peer/answer/{webcamId}") -// @SendTo("/topic/peer/answer/{camKey}/{webcamId}") -// public String PeerHandleAnswer(@Payload String answer, @DestinationVariable(value = "webcamId") String webcamId, @DestinationVariable(value = "camKey") String camKey) { -// log.info("[ANSWER] {} : {}", camKey, answer); -//// messagingTemplate.convertAndSend("/topic/peer/answer/" + message.getWebcamId(), message); -// return answer; -// } @MessageMapping("/peer/answer/{webcamId}") @SendTo("/topic/peer/answer/{webcamId}") public Message PeerHandleAnswer(Message message, @DestinationVariable(value = "webcamId") String webcamId) { @@ -94,23 +79,15 @@ public Message PeerHandleAnswer(Message message, @DestinationVariable(value = "w } /** - * camKey 를 받기위해 신호를 보내는 webSocket + * leave 정보 주고받기 */ -// @MessageMapping("/call/key") -// @SendTo("/topic/call/key") -// public String callKey(@Payload String message) { -// log.info("[Key] : {}", message); -// return message; -// } - - /** - * 자신의 camKey 를 모든 연결된 세션에 보내는 webSocket - */ -// @MessageMapping("/send/key") -// @SendTo("/topic/send/key") -// public String sendKey(@Payload String message) { -// return message; -// } + @MessageMapping("/peer/leaveRoom/{webcamId}") + @SendTo("/topic/peer/leaveRoom/{webcamId}") + public Message PeerHandleLeave(Message message, @DestinationVariable(value = "webcamId") String webcamId) { + log.info("[LEAVE] sender: {}, 전달할 곳 : {} ", message.getSender(), message.getWebcamId()); +// messagingTemplate.convertAndSend("/topic/peer/answer/" + message.getWebcamId(), message); + return message; + } /** * 방 삭제 diff --git a/src/main/java/vom/spring/domain/webcam/domain/Type.java b/src/main/java/vom/spring/domain/webcam/domain/Type.java index b0cf1c9..5427f79 100644 --- a/src/main/java/vom/spring/domain/webcam/domain/Type.java +++ b/src/main/java/vom/spring/domain/webcam/domain/Type.java @@ -1,5 +1,5 @@ package vom.spring.domain.webcam.domain; public enum Type { - OFFER, ANSWER, ENTER, ICE + OFFER, ANSWER, ENTER, ICE, LEAVE } From f40c95c54c209ef8481a04d8d656d67089d455cc Mon Sep 17 00:00:00 2001 From: Ojimin Date: Wed, 12 Jun 2024 01:42:28 +0900 Subject: [PATCH 5/5] =?UTF-8?q?fix:=20=EB=91=90=EB=B2=88=20deploy=EB=90=98?= =?UTF-8?q?=EB=8A=94=20=EC=98=A4=EB=A5=98-=20workflow=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .github/workflows/deploy.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index cd2a252..e3c54b4 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -5,8 +5,6 @@ name: Java CI with Gradle & Deploy to EC2 # develop 브랜치에 push가 되면 아래의 flow가 실행됨 on: # Triggers the workflow on push or pull request events but only for the "develop" branch - push: - branches: [ "develop" ] pull_request: branches: [ "develop" ]