Redirect Probleme Cross Origin

Kirby.exe

Top Contributor
Also ich möchte gerne, wenn man bei der Login Seite Daten eingibt welche auch in der Datenbank existieren also Email und Password, dann soll man auf die Homepage weitergeleitet werden. Dazu habe ich im LoginController ein bisschen was geschrieben, nur leider bekomme ich einen Cross-Origin Error und verstehe nicht ganz wo genau es fehlschlägt :(

Ich habe in den anderen Controllern (welche ja mittels dem Redirect angesprochen werden sollten) einen handler für Get Requests eingefügt und ein simples Printstatement eingefügt. Leider kommt dort gar nichts :(

Hier ist ein Screenshot vom Network Tab:

1628012754756.png

Hier ist der LoginController:

Java:
package de.unihalle.shop.Controller;

import de.unihalle.shop.Model.Customer;
import org.mindrot.jbcrypt.BCrypt;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

import java.net.URI;

@RestController
public class LoginController {

    @CrossOrigin(origins = "http://localhost:3000")
    @PostMapping(value="/login", consumes= MediaType.APPLICATION_JSON_VALUE, produces=MediaType.APPLICATION_JSON_VALUE)
    public ResponseEntity<Object> handleLogin(@RequestBody Customer user){
        Customer db_user = Customer.getCustomer(user.getEmail());
        System.out.println("Passed User: " + user.toString());
        System.out.println("DB User: " + db_user.toString());
        System.out.println("Yeee Boy lets compare some Passwords!");
        if(BCrypt.checkpw(user.getPassword(), db_user.getPassword())){
            System.out.println("Its Correct Nuddy Buddy!");
            HttpHeaders headers = new HttpHeaders();
            headers.setAccessControlAllowOrigin("http://localhost:3000");
            headers.setLocation(URI.create("http://localhost:3000/signup"));
            return new ResponseEntity<>(headers, HttpStatus.MOVED_PERMANENTLY);
        }
        System.out.println("Bye");
        return new ResponseEntity<>(new HttpHeaders(), HttpStatus.FORBIDDEN);
    }
}
 

sascha-sphw

Top Contributor
Dein React Dev Server lauscht auf Port 3000 Dein Backend auf Port 8080. Du musst also im Backend über den access control header den client auf Port 3000 explizit erlauben, sonst blockt der Browser den Response.

Edit: Unterschiedliche Ports werden ebenfalls als Cross Domain betrachtet.
 

sascha-sphw

Top Contributor
Ja, sorry habe es überlesen. Du hast es 2 Mal Konfiguriert.
Java:
@CrossOrigin(origins = "http://localhost:3000")
...
headers.setAccessControlAllowOrigin("http://localhost:3000");
...
Nimm mal eins davon raus.
 

Kirby.exe

Top Contributor
Ja, sorry habe es überlesen. Du hast es 2 Mal Konfiguriert.
Java:
@CrossOrigin(origins = "http://localhost:3000")
...
headers.setAccessControlAllowOrigin("http://localhost:3000");
...
Nimm mal eins davon raus.
Das hatte ich gemacht dann sagt er immernoch das selbe :(

Edit: Er sagt dann was anderes, aber immernoch mit Cross Origin, dass der Redirect irgendwie nicht allowed ist :( Kann gerade leider nicht die genaue meldung schicken
 

sascha-sphw

Top Contributor
Ja, mit der Annotation beschränkt sich der Cross Domain Header auf die verwendete HTTP Methode. Der Browser macht aber immer einen OPTIONS preflight bevor er den echten Request sendet. Du musst also in der Konfiguration noch folgendes einstellen.
Java:
@Configuration
public class WebConfig implements WebMvcConfigurer {
    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry
                .addMapping("/**")
                .allowedOriginPatterns("http://localhost:3000")
                .allowedMethods("OPTIONS");
    }
}
 

sascha-sphw

Top Contributor
Wenn Du mit einem Webserver (Apache, Nginx) arbeitest könntest Du Dir einen reverse proxy einrichten, dann könntest Du die Cross Domain Issues, ohne etwas an der Applikation zu ändern, umgehen.
 

Kirby.exe

Top Contributor
Mhh also die configuration hat leider nichts geändert :( Mir hat ein Freund gesagt ich solle das Front-End mit auf den Backend Server stecken, damit dieser Cross-Origin Mist nicht mehr kommt...Nur finde ich dazu nichts im Internet :( Weiß einer von euch wie man das bei Spring macht? Das mein React Code auf dem Tomcat Server von Spring compiliert wird
 

mrBrown

Super-Moderator
Mitarbeiter
Hast du zufällig ein minimales Ausführbares Beispiel? Dann kann man den Fehler eben nachstellen.

Das Frontend über den gleichen Server auszuleihen ist zwar grundsätzlich möglich, aber nicht immer die sinnvollste Wahl – vor allem nicht wenn man das nur machen will, um die passende Konfiguration zu vermeiden :)
 

Kirby.exe

Top Contributor
Ansonsten versuche ich einfach mal die aktuelle Situtation zu schildern:

Wenn ich mit meinem Projekt interagieren möchte dann muss ich erstmal 3 Dinge tuen:
  1. Front End Webserver starten mit npm start
  2. Back End Webserver von Spring starten durch Intellij
  3. Docker Container mit der Datenbank starten mit sudo docker-compose up
Nun kann gehe ich im Browser auf die "Domain" http://localhost:3000/login dann erscheint diese Seite:

1628102971705.png

Nun gebe ich als Email und Password irgendwelche Einträge ein, welche bereits in der Datenbank existieren und drücke auf "Log In".
Mit dem Log In Button werden die Daten aus den Inputfeldern genommen und per POST an http://localhost:8080/login gesendet und dort auch erfolgreich von meinem LoginController entgegen genommen.

Da die eingegeben Daten auch in der Datenbank vorkommen, möchte ich nun gerne mittels eines 301 Response auf die Homepage (http://localhost:3000/) weiterleiten und hier passiert mist...Da weint er wegen Cross Origin.
 

sascha-sphw

Top Contributor
Der Ablauf bringt uns leider nicht viel weiter, der ist ja durchaus bekannt. Wie @mrBrown bereits gesagt hat, wäre ein minimales Beispiel, bei dem das Problem Auftritt, sehr hilfreich. Es ist definitiv nur ein Problem mit der Konfiguration.

Lieber jetzt richtig lösen anstatt nur workarounds bauen, die dir später auf die Füße fallen.
 

Kirby.exe

Top Contributor
Mhh also ich bin ehrlich gerade etwas überfordert xD Ich verstehe nicht ganz was ihr unter "minimal" Beispiel meint XD Ich könnte eine zwei Random Seiten in React erstellen und für beide einen Backend Controller schreiben und das schicken, aber ich weiß nicht ob ihr das so meint :(
 

mrBrown

Super-Moderator
Mitarbeiter
Einfach nur ein kleines Spring-Projekt mit pom.xml/build.gradle, Configurations-Dateien und einem Controller, an dem das Problem nachstellbar ist.

Irgendwo in deinem Projekt ist irgendwas an der Konfiguration falsch – wenn man dass auf den Minimalisten Stand reduziert, mit dem das Problem noch auftritt, kann man es einmal sehr eingrenzen und meist selbst damit schön lösen und zusätzlich können andere nachvollziehen, was du gemacht hast und dir möglicherweise direkt schon sagen, wo der Fehler ist.
Mit einzelnen Bruchstücken hier im Forum geht das eher nicht, dafür müsstest du ja schon wissen, wo der Fehler liegt, um überhaupt die relevanten Teile zeigen zu können.
 

Kirby.exe

Top Contributor
Also ich habe jetzt ein Projekt erstellt, aber ich weiß nicht ob es meinen Fehler reproduziert, da ich es im Browser nicht hinbekomme einen Post zu machen...Wenn ich mit curl das mache kommt gar nichts und es kommt nach dem Redirect auch nichts beim Server an :(

Ich habe das Projekt mal angehangen :)
 

Anhänge

  • demo.zip
    67,7 KB · Aufrufe: 2

Kirby.exe

Top Contributor
Also um ehrlich zu sein, habe ich in meinem Spring bis jetzt noch gar nichts konfiguriert, also bezogen auf CORS...Ich bin auch im Moment mehr als verwirrt, weil im Web irgendwie jeder was anderes sagt :( Wie wäre denn die korrekte herangehensweise Spring zu konfigurieren, dass eine Kommunikation zwischen Spring und React möglich ist?
 

sascha-sphw

Top Contributor
Also als erstes habe ich mal
Java:
return new ResponseEntity<>(headers, HttpStatus.MOVED_PERMANENTLY);
durch
Java:
return new ResponseEntity<>(headers, HttpStatus.FOUND);
Du willst ja, denke ich, dass immer zuerst page1 über POST aufgerufen wird und nicht der client direkt auf page2 navigiert. Siehe auch https://en.wikipedia.org/wiki/HTTP_301

Package Namen immer klein. Controller -> controller

Und dann habe ich nur noch alles gemacht wie in diesem Thread beschrieben.
 

Anhänge

  • demo.zip
    12,1 KB · Aufrufe: 2

Kirby.exe

Top Contributor
Mhh also ich habe den "Redirect" Code mal so bei mir eingebaut und es funktioniert immernoch nicht...selbe Fehlermeldung wie vorher :(
Ich vermute einfach, dass die Fehlermeldung kommt, weil ich ja "zwei" Webserver habe:

Einmal den wo React drauf läuft und den wo Spring drauf läuft und zwischen denen wurde keine richtige Kommunikation definiert oder configuriert und ich weiß ehrlich gesagt auch nicht so wirklich wie das geht :(
 

sascha-sphw

Top Contributor
Bau doch einfach schnell einen Test Client mit React, dauert ja nicht lange. Oder Du rufst mit Deinem Client mal schnell zum Testen die Endpunkte vom Demo Server auf.

Edit: Bei den Fehlermeldungen musst Du aber schon aufpassen, bei welchem Request (Endpunkt) der denn auftritt. Nicht das Du die ganze Zeit an der falschen Methode änderst.
 

Kirby.exe

Top Contributor
Also ich habe mir mal ein "mini" Front End zu dem demo Zeug gebastelt...And i am not happy to announce:
Housten we have a Problem xD

Die Fehlermeldung ist:

Bildschirmfoto 2021-08-07 um 20.27.08.png

Die React App habe ich hier hochgeladen React App
 

sascha-sphw

Top Contributor
Ich habe gerade beides einfach nur gestartet. Bist Du Sicher, dass Du die richtigen Projekte startest? Mach mal einen anständigen clean und bau alles neu.

Edit: hast Du das Projekt genommen das ich Dir hochgeladen habe?
1628367388046.png
 

Kirby.exe

Top Contributor
Ja ich habe dein Projekt genommen, nur habe ich die redirect url geändert auf http://localhost:3000/page2 da ich ja mir die Seite vom Front End holen möchte oder habe ich hier einen Denkfehler?
 

sascha-sphw

Top Contributor
Ja ich habe dein Projekt genommen, nur habe ich die redirect url geändert auf http://localhost:3000/page2 da ich ja mir die Seite vom Front End holen möchte oder habe ich hier einen Denkfehler?
Ich denke schon. Wie @mrBrown schon geschrieben hat, wenn man eine Single Page App hat, macht man eigentlich den Server als REST Service und den Rest macht man mit dem Frontend. Für was den Umweg über das Backend?

Edit: Eine Frage noch. Willst Du tiefer in die Materie Security einsteigen? Wenn nicht, würde ich eher ein fertiges System dafür einsetzen (z.B. Keycloak), das spart Dir viel Zeit und Sicherheitslücken.
 

sascha-sphw

Top Contributor
@sascha-sphw eigentlich möchte ich wirklich erstmal nur einen gescheites Login hinbekommen xD
Definiere gescheit! Denn "gescheit" in meinen Augen geht nicht, solange Du kein Security Experte bist. Deshalb würde ich Dir auch Keycloak empfehlen, da musst Du das alles nicht selber implementieren (Tuturials dazu gibt es wie Sand am Meer).

Aber ich würde den Flow grob wie folgt machen:
  1. Client sendet User credentials an Server per POST.
  2. Server validiert -> Erfolgreich
    1. Server erstellt ein Cookie mit z.B. SessionId (HTTP only) und return 200 OK.
    2. Client redirected selber entsprechend
  3. Server validiert -> Fail
    1. Server return 403 ggf. mit Fehler.
    2. Client zeigt Fehler an.

Also ich vermute mal dass diese Fehlermeldung kommt, weil ich vom Backend und nicht vom Front End redirecte korrekt?
Der Fehler kommt wegen CORS, so wie wir es bereits besprochen haben. Hier gilt immer, die Methoden die Du von einer anderen Domain über den Browser ansprechen möchtest, müssen mit @CrossOrigin versehen werden. Ginge auch global über den WebMvcConfigurer, wenn Du das bei allen Methoden brauchst.
 

Kirby.exe

Top Contributor
Mhh also irgendwie scheint mir Keycloak sehr komplex xD Kleine Background warum ich den Kram mache...Eigentlich möchte ich wirklich nicht viel mehr als Login Credentials ans Backend senden, DB validiert und dann wird redirected. Sicherheit ist erstmal egal, da dies "nur" eine Hausarbeit ist und die Webpage nicht ans Internet exposed wird :)
 

sascha-sphw

Top Contributor
Eigentlich möchte ich wirklich nicht viel mehr als Login Credentials ans Backend senden, DB validiert und dann wird redirected. Sicherheit ist erstmal egal, da dies "nur" eine Hausarbeit ist und die Webpage nicht ans Internet exposed wird :)

Ja, dann so.
Aber ich würde den Flow grob wie folgt machen:
  1. Client sendet User credentials an Server per POST.
  2. Server validiert -> Erfolgreich
    1. Server erstellt ein Cookie mit z.B. SessionId (HTTP only) und return 200 OK.
    2. Client redirected selber entsprechend
  3. Server validiert -> Fail
    1. Server return 403 ggf. mit Fehler.
    2. Client zeigt Fehler an.
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
Avalon Get Request doppelt abfeuern ohne Post Redirect Get Pattern. Spring Boot Thymeleaf MVC Frameworks - Spring, Play, Blade, Vaadin & Co 12
F Redirect in einer Spring Boot WebApplication Frameworks - Spring, Play, Blade, Vaadin & Co 7
S Spring MVC redirect Nachricht ohne erweiterung der URL Frameworks - Spring, Play, Blade, Vaadin & Co 5
R Probleme beim abfragen von untergeordneten Tabellen Frameworks - Spring, Play, Blade, Vaadin & Co 2
8u3631984 Spring JPA Probleme beim SPeichern von Sets Frameworks - Spring, Play, Blade, Vaadin & Co 3
8u3631984 Spring JDBC Probleme beim Spaltennamen Frameworks - Spring, Play, Blade, Vaadin & Co 3
8u3631984 Probleme mit Records und JPA Frameworks - Spring, Play, Blade, Vaadin & Co 4
8u3631984 Probleme beim Starten von TestContainer Frameworks - Spring, Play, Blade, Vaadin & Co 4
P JWT Probleme Frameworks - Spring, Play, Blade, Vaadin & Co 2
Dimax Spring App Probleme beim Ausführen auf dem Tomcat Server Frameworks - Spring, Play, Blade, Vaadin & Co 1
Dimax Spring Security Probleme Frameworks - Spring, Play, Blade, Vaadin & Co 2
bueseb84 Probleme mit Spring Boot Docker und Bootstrap Frameworks - Spring, Play, Blade, Vaadin & Co 9
B Spring bean initialisierungs probleme Frameworks - Spring, Play, Blade, Vaadin & Co 0
H IE probleme mit multipartfile bei spring 3 anwendungen Frameworks - Spring, Play, Blade, Vaadin & Co 14
8u3631984 Cross-Origin beim Abrufen von Spring Endpoint Frameworks - Spring, Play, Blade, Vaadin & Co 1

Ähnliche Java Themen

Neue Themen


Oben