복붙노트

[SPRING] Spring 웹 소켓에서 오류 메시지를 보내는 중

SPRING

Spring 웹 소켓에서 오류 메시지를 보내는 중

SockJS를 통해 STOMP가있는 Spring 웹 소켓에서 오류 메시지를 보내려고합니다.

나는 기본적으로 여기서 이루어지고있는 것을 성취하려고 노력하고있다.

이것은 내 예외 처리기입니다.

@MessageExceptionHandler
@SendToUser(value = "/queue/error",broadcast = false)
public ApplicationError handleException(Exception message) throws ApplicationError {
        return  new ApplicationError("test");
}

그리고 나는에 가입하고있다.

stompClient.subscribe('/user/queue/error', stompErrorCallback, {token: accessToken});

내 경우 사용자가 인증되지 않았지만 여기에서

이 모든 오류는 webSocket config에 정의 된 mySocket Handler 인 myHandler에서이 오류가 발생하면 제대로 작동합니다.

PreSend에있는 모든 메시지를 가로채는 ChannelInterceptorAdapter를 확장하는 ClientInboundChannelInterceptor가 있습니다.

이 인터셉터에서 예외가 발생하면이 메시지를 보낸 사용자 세션으로 되돌려 보내려고합니다.

public class ClientInboundChannelInterceptor extends ChannelInterceptorAdapter {
    @Autowired
    @Lazy(value = true)
    @Qualifier("brokerMessagingTemplate")
    private SimpMessagingTemplate simpMessagingTemplate;

    @Override
    public Message<?> preSend(Message message, MessageChannel channel) throws IllegalArgumentException{
         if(some thing goes wrong)
           throw new RuntimeException();
    }

    @MessageExceptionHandler
    @SendToUser(value = "/queue/error",broadcast = false)
    public ApplicationError handleException(RuntimeException message) throws    ApplicationError {
        return  new ApplicationError("test");
    }
}

@MessageExceptionHandler는이 예외를 포착하지 않습니다. 그래서 simpMessagingTemplate을 사용하여 직접 사용자에게 보냈습니다.

나는 기본적으로하고 싶다.

simpMessagingTemplate.convertAndSendToUser(SOMETHING,"/queue/error",e);

SOMEETHING은 올바른 사용자 이름이어야하지만 내 경우에는 사용자가 인증되지 않으므로 headerAccessor.getUser (). getName ()을 사용할 수 없습니다.

나도 같이 해봤 어.

simpMessagingTemplate.convertAndSendToUser(headerAccessor.getHeader("","/queue/error",e, Collections.singletonMap(SimpMessageHeaderAccessor.SESSION_ID_HEADER, headerAccessor.getSessionId()));

그러나 이것은 작동하지 않습니다.

나는 심지어 username의 자리에 headerAccessor.getSessionId ()를 시도했지만 작동하지 않는 것 같습니다.

이 작업을 수행하는 올바른 방법은 무엇입니까?

convertAndSendToUser에서 사용자 이름으로 무엇을 사용해야합니까?

해결법

  1. ==============================

    1.내 초기 직관은 정확했지만 sessionId는 인증되지 않은 사용자 상황에서 사용자 이름으로 사용되지만 헤더에 문제가있는 것입니다.

    내 초기 직관은 정확했지만 sessionId는 인증되지 않은 사용자 상황에서 사용자 이름으로 사용되지만 헤더에 문제가있는 것입니다.

    @SendToUser와 simpMessagingTemplate.convertAndSendToUser ()를 통해 디버깅을 한 후, @SendToUser 헤더를 사용하면 헤더가 자동으로 설정되고 simpMessagingTemplate.convertAndSendToUser ()를 사용하는 경우 헤더를 명시 적으로 정의해야한다는 것을 깨달았습니다.

    @SendToUser는 두 개의 헤더를 설정하고있었습니다.

    그래서 나는 헤더를 추가하려고 시도했다.

    String sessionId = headerAccessor.getSessionId();
    Map<String,Object> headerMap = new HashMap<>();
    headerMap.put("simpMessageType", SimpMessageType.MESSAGE);
    headerMap.put("simpSessionId",sessionId);   
    simpMessagingTemplate.convertAndSendToUser(headerAccessor.getSessionId(),"/queue/error",e,headerMap);
    

    그것은 작동하지 않았다, 나는 MessageHeaders로 헤더를주는 시도했다.

    String sessionId = headerAccessor.getSessionId();
    Map<String,Object> headerMap = new HashMap<>();
    headerMap.put("simpMessageType", SimpMessageType.MESSAGE);
    headerMap.put("simpSessionId",sessionId); 
    MessageHeaders headers = new MessageHeaders(headerMap);
    
    simpMessagingTemplate.convertAndSendToUser(headerAccessor.getSessionId(),"/queue/error",e,headers);
    

    어느 쪽도 일하지 않았다.

    좀 더 디버깅을 한 후에 헤더를 설정하는 정확한 방법을 알았고 아마도 이것이 SendToMethodReturnValueHandler.java의 헤더를 만드는 유일한 방법 일 것입니다.

    private MessageHeaders createHeaders(String sessionId) {
        SimpMessageHeaderAccessor headerAccessor = SimpMessageHeaderAccessor.create(SimpMessageType.MESSAGE);
        headerAccessor.setSessionId(sessionId);
        headerAccessor.setLeaveMutable(true);
        return headerAccessor.getMessageHeaders();
    }
    

    결국,

    String sessionId = headerAccessor.getSessionId();
    template.convertAndSendToUser(sessionId,"/queue/error","tesssssts",createHeaders(sessionId));
    

    트릭을 했어.

  2. ==============================

    2.자세한 정보는 SendToMethodReturnValueHandler 소스 코드를 참조하십시오.

    자세한 정보는 SendToMethodReturnValueHandler 소스 코드를 참조하십시오.

  3. from https://stackoverflow.com/questions/33806014/sending-error-message-in-spring-websockets by cc-by-sa and MIT license