Howto zusätzlich hinzufügen Spring Security Captcha Filter nur für bestimmte URLs

8

Ich bin auf der Suche nach einer nicht-invasiven Möglichkeit, einen Captcha-Filter für bestimmte API-Aufrufe hinzuzufügen.

Mein Setup besteht aus zwei WebSecurityConfigurerAdapters mit jeweils einem Filter (nicht dem Captcha-Filter):

  • Interne API ("/ iapi" verwendet Filter A für alle Aufrufe, ignoriert aber auch einige öffentliche -Anfragen wie / authenticate)
  • Externe API ("/ eapi" verwendet Filter B für alle Anrufe)

Wie kann ich einen Filter vor Spring Spring-Elementen hinzufügen, bei öffentlichen, internen API- oder externen API-Aufrufen? Ich brauche nicht den SecurityContext, muss nur in den Request-Headern nach einem Captcha suchen, an filterChain weiterleiten (normale Filter) oder manuell den Zugriff verweigern. Ich habe versucht, einen Filter in web.xml zu deklarieren, aber das bricht die Fähigkeit, Abhängigkeitsinjektion zu verwenden.

Hier ist meine Spring Security Konfiguration:

%Vor%

Update: Im Moment habe ich eine funktionierende Konfiguration mit einem Filter, der in web.xml deklariert ist. Es hat jedoch den Nachteil, dass es vom Spring-Kontext getrennt ist (z. B. kein Autowiring von Beans), daher suche ich nach einer besseren Lösung, die Spring nutzt.

Zusammenfassung : Es gibt zwei verbleibende Probleme:

  1. fügt einen Filter nur für spezifische URLs hinzu - wenn beforeFilter (...) innerhalb einer Konfiguration verwendet wird, wird allen URLs dieser Konfiguration ein Filter hinzugefügt. Antmatchers hat nicht gearbeitet. Ich brauche so etwas: / iapi / captcha / , / extern / captcha / , / public / captcha / *.
  2. Ich habe eine öffentliche API, die Spring Security komplett umgeht: (web                         .ignoring ()                         .antMatchers ("/ public / **");). Ich muss Spring Security umgehen, aber trotzdem einen Filter deklarieren, indem ich Spring-Autowiring-Funktionen, aber nicht unbedingt Spring Security-Funktionen nutze, da mein Captcha-Filter nur statisch ablehnt oder weiterleitet.
Journeycorner 16.12.2015, 14:03
quelle

1 Antwort

5

Sie haben bereits eine funktionierende Konfiguration mit den Filtern A und B, die vor UsernamePasswordAuthenticationFilter eingefügt wurden. Daher sollte es einfach sein, einen weiteren benutzerdefinierten Filter hinzuzufügen.

Zuerst erstellen Sie den Filter und deklarieren ihn als Bean, indem Sie entweder die Klasse mit @Component oder als @Bean in einer @Configuration -Klasse kommentieren, damit er mit @Autowired injiziert werden kann. .

Jetzt können Sie es als Filter A und B injizieren und verwenden. Laut Abschnitt Filterreihenfolge in der Spring Security-Referenz Dokumentation, der allererste Filter in der Kette ist ChannelProcessingFilter . Um den Filter vor allem anderen in die Spring Security-Filterkette einzufügen, tun Sie Folgendes:

%Vor%

Übrigens, exceptionHandling() anonymous() und servletApi() werden nicht benötigt, weil beim Erweitern von WebSecurityConfigurerAdapter diese bereits enthalten sind, mit Ausnahme von anonymous() , wenn Sie tatsächlich mehr Konfigurationsdetails angeben, da es HttpSecurity javadoc

Beachten Sie, dass der Einstiegspunkt Spring Security " DelegatingFilterProxy " immer noch vor Ihrem Filter ausgeführt wird. Diese Komponente delegiert die Anforderung jedoch nur an den ersten Filter in der Kette, in diesem Fall den CaptchaFilter. so würden Sie Ihren Filter wirklich vor allem anderen von Spring Security ausführen.

Wenn Sie jedoch weiterhin möchten, dass der Captcha-Filter vor DelegatingFilterProxy ausgeführt wird, gibt es keine Möglichkeit, dies in der Spring Security-Konfiguration zu tun, und Sie müssen dies in der Datei web.xml deklarieren.

Update: Wenn Sie den Captcha-Filter nicht in die anderen Konfigurationen aufnehmen möchten, können Sie immer eine dritte Konfiguration hinzufügen, und die Konfigurationsklasse wäre wie folgt:

%Vor%

Übrigens, ein weiterer Tipp, Sie können alle allgemeinen Konfigurationen außerhalb der spezifischen Konfigurationen in die Hauptklasse umgestalten, wie @EnableGlobalMethodSecurity(securedEnabled = true) den AuthenticationManager, WebSecurity , um die Sicherheit für die Öffentlichkeit zu überspringen, aber für diejenigen seit der Hauptklasse erweitert nichts, Sie sollten @Autowire die Methodendeklarationen.

Obwohl es ein Problem mit WebSecurity gäbe, wenn Sie /public/** ignorieren, würde der Matcher für HttpSecurity mit /public/captcha** ignoriert werden, also sollten Sie die WebSecurity und nicht umdefinieren habe ein anderes Muster in der CaptchaConfig-Klasse, so dass es sich nicht überlappt.

    
saljuama 24.12.2015, 04:47
quelle