2

Ich mache ein Beispiel auf Spring Boot + oauth2 + websocket. Ich habe Federwebsocket-Konfiguration und anderen Code auf Ressourcenserver, der auf 8098-Port ausgeführt wird. Und ich versuche, es von Client-Anwendung zu verbinden, die auf 8080-Port ausgeführt wird. Aber wenn ich meine Anwendung starte, erhalte ich den Fehler 401 (nicht autorisiert) in der Browser-Konsole. Ich teile einige meiner Code:Spring + Oauth2 + JWT + Websocket

1) Client-Anwendung (auf Port 8080 läuft) JavaScript-Code websocket Verbindung

'use strict'; 

// pull in the SockJS JavaScript library for talking over WebSockets. 
var SockJS = require('sockjs-client'); 
// pull in the stomp-websocket JavaScript library to use the STOMP sub-protocol. 
require('stompjs'); 

function register(registrations) { 
    const access_token = localStorage.getItem("ACCESS_TOKEN"); 
    console.log("Access Token " + access_token); 
    const csrf_token = localStorage.getItem("XSRF"); 
    // Here is where the WebSocket is pointed at the server application’s /messages endpoint 
    // websocket use this URL to open TCP connection 
    var socket = SockJS('http://localhost:8098/notifications'); 
    var stompClient = Stomp.over(socket); 

    var headers = { 
     'X-Csrf-Token': csrf_token, 
     Authorization: 'Bearer ' + access_token 
    } 

    // connect to server using stompClient 
    stompClient.connect(headers, function(frame) { 
     // Iterate over the array of registrations supplied so each can subscribe for callback as messages arrive. 
     stompClient.send("/app/notifications", {}); 
     registrations.forEach(function (registration) { 
      stompClient.subscribe(registration.route, registration.callback); 
     }); 
    }); 

} 

module.exports = { 
    register: register 
}; 

2) Ressourcen Server (läuft auf 8098-Port) Code zu bekommen, wo ich Server Seite Websocket Konfiguration

@Configuration 
@EnableWebSocketMessageBroker 
public class WebSocketConfiguration extends AbstractSecurityWebSocketMessageBrokerConfigurer { 

    // This prefix we will append to every message's route. 
    static final String MESSAGE_PREFIX = "/topic" 
    static final String END_POINT = "/notifications" 
    static final String APPLICATION_DESTINATION_PREFIX = "/app" 

    @Override 
    protected boolean sameOriginDisabled() { 
     return true; 
    } 

    /** 
    * This method configure the end-point on the backend for clients and server to link ('/notifications'). 
    */ 
    @Override 
    public void registerStompEndpoints(StompEndpointRegistry registry) { 

     // This code register the '/notifications' end-point. The SockJS client will attempt to connect to '/notifications' end-point 
     if(registry != null) { 
      registry.addEndpoint(END_POINT).setAllowedOrigins("*").withSockJS() 
     } 

    } 

    /** 
    * This method configure the message broker used to relay messages between server and client. 
    */ 
    @Override 
    public void configureMessageBroker(MessageBrokerRegistry registry) { 

     if(registry != null) { 
      // Enable a broker to send messages to the client on destinations prefixed with '/topic' 
      registry.enableSimpleBroker(MESSAGE_PREFIX); 
      // prefix for messages that are bound for @MessageMapping annotated methods. This prefix will be used to define all message mappings 
      registry.setApplicationDestinationPrefixes(APPLICATION_DESTINATION_PREFIX) 
     } 
    } 
} 

Bitte einige Lösung vorschlagen.

Antwort

3

Endlich habe ich das Problem gelöst. Das Problem war zuvor, dass ich Access-Token in decodierter Form mit jwt_token und mit dem Präfix "Bearer" gesendet habe.

Also habe ich einige Debugging und ich wusste, dass Token sollte in seiner tatsächlichen Form und ohne Decodierung gesendet werden.

  1. zuvor aus Reaktion auf Client-Seite Zugriffstoken Mag ich wurde Extraktion:

let dekodierten = jwt_decode (response.entity.details.tokenValue); localStorage.setItem ("ACCESS_TOKEN", decodiert.jti);

Und das ist nicht korrekt. Also änderte ich es mit dem folgenden Code:

localStorage.setItem ("ACCESS_TOKEN", response.entity.details.tokenValue);

  1. In websocket-Hörer js Datei ändert ich unten habe

const access_token = localStorage.getItem ("access_token");

var socket = SockJS ('http://localhost:8098/notifications/?access_token=' + access_token);

Und sehen, ich sende Zugriffstoken in URL-Abfrageparameter ohne Präfix "Bearer".

Und es hat funktioniert.