So konfigurieren Sie Spring Security so, dass auf die Swagger-URL ohne Authentifizierung zugegriffen werden kann


92

Mein Projekt hat Spring Security. Hauptproblem: Zugriff auf die Swagger-URL unter http: // localhost: 8080 / api / v2 / api-docs nicht möglich . Es heißt Fehlender oder ungültiger Autorisierungsheader.

Screenshot des Browserfensters Meine pom.xml enthält die folgenden Einträge

<dependency>
    <groupId>io.springfox</groupId>
    <artifactId>springfox-swagger2</artifactId>
    <version>2.4.0</version>
</dependency>

<dependency>
    <groupId>io.springfox</groupId>
    <artifactId>springfox-swagger-ui</artifactId>
    <version>2.4.0</version>
</dependency>

SwaggerConfig:

@Configuration
@EnableSwagger2
public class SwaggerConfig {

@Bean
public Docket api() {
    return new Docket(DocumentationType.SWAGGER_2).select()
            .apis(RequestHandlerSelectors.any())
            .paths(PathSelectors.any())
            .build()
            .apiInfo(apiInfo());
}

private ApiInfo apiInfo() {
    ApiInfo apiInfo = new ApiInfo("My REST API", "Some custom description of API.", "API TOS", "Terms of service", "myeaddress@company.com", "License of API", "API license URL");
    return apiInfo;
}

AppConfig:

@Configuration
@EnableWebMvc
@ComponentScan(basePackages = { "com.musigma.esp2" })
@Import(SwaggerConfig.class)
public class AppConfig extends WebMvcConfigurerAdapter {

// ========= Overrides ===========

@Override
public void addInterceptors(InterceptorRegistry registry) {
    registry.addInterceptor(new LocaleChangeInterceptor());
}

@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
    registry.addResourceHandler("swagger-ui.html")
      .addResourceLocations("classpath:/META-INF/resources/");

    registry.addResourceHandler("/webjars/**")
      .addResourceLocations("classpath:/META-INF/resources/webjars/");
}

web.xml Einträge:

<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>
        com.musigma.esp2.configuration.AppConfig
        com.musigma.esp2.configuration.WebSecurityConfiguration
        com.musigma.esp2.configuration.PersistenceConfig
        com.musigma.esp2.configuration.ACLConfig
        com.musigma.esp2.configuration.SwaggerConfig
    </param-value>
</context-param>

WebSecurityConfig:

@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
@ComponentScan(basePackages = { "com.musigma.esp2.service", "com.musigma.esp2.security" })
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {
@Override
    protected void configure(HttpSecurity httpSecurity) throws Exception {
        httpSecurity
        .csrf()
            .disable()
        .exceptionHandling()
            .authenticationEntryPoint(this.unauthorizedHandler)
            .and()
        .sessionManagement()
            .sessionCreationPolicy(SessionCreationPolicy.STATELESS)
            .and()
        .authorizeRequests()
            .antMatchers("/auth/login", "/auth/logout").permitAll()
            .antMatchers("/api/**").authenticated()
            .anyRequest().authenticated();

        // custom JSON based authentication by POST of {"username":"<name>","password":"<password>"} which sets the token header upon authentication
        httpSecurity.addFilterBefore(loginFilter(), UsernamePasswordAuthenticationFilter.class);

        // custom Token based authentication based on the header previously given to the client
        httpSecurity.addFilterBefore(new StatelessTokenAuthenticationFilter(tokenAuthenticationService), UsernamePasswordAuthenticationFilter.class);
    }
}

Antworten:


175

Das Hinzufügen zu Ihrer WebSecurityConfiguration-Klasse sollte den Trick tun.

@Configuration
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {

    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers("/v2/api-docs",
                                   "/configuration/ui",
                                   "/swagger-resources/**",
                                   "/configuration/security",
                                   "/swagger-ui.html",
                                   "/webjars/**");
    }

}

11
Wenn Sie swagger-ui verwenden, benötigen Sie Folgendes: .antMatchers ("/ v2 / api-docs", "/ configuration / ui", "/ swagger-resources", "/ configuration / security", "/ swagger-ui" .html "," / webjars / ** "," / swagger-resources / configuration / ui "," / swagger-ui.html "). allowAll ()
Daniel Martín

2
In meinem Fall funktioniert diese Regel: .antMatchers ("/ v2 / api-docs", "/ configuration / ui", "/ swagger-resources", "/ configuration / security", "/swagger-ui.html", "/ webjars / **", "/ swagger-resources / configuration / ui", "/ swagge‌ r-ui.html", "/ swagger-resources / configuration / security"). allowAll ()
nikolai.serdiuk

6
Benötigte mehr Regeln: .antMatchers ("/", "/ csrf", "/ v2 / api-docs", "/ swagger-resources / configuration / ui", "/ configuration / ui", "/ swagger-resources", "/ swagger-resources / configuration / security", "/ configuration / security", "/swagger-ui.html", "/ webjars / **"). allowAll ()
Mate Šimović

5
Danke für die Antwort! Gibt es ein Sicherheitsrisiko für den Zugriff auf Webjars / **?
ssimm

sehr hilfreiche Antwort
Praveenkumar Beedanal

26

Ich habe mit / configuration / ** und / swagger-resources / ** aktualisiert und es hat bei mir funktioniert.

@Override
public void configure(WebSecurity web) throws Exception {
    web.ignoring().antMatchers("/v2/api-docs", "/configuration/ui", "/swagger-resources/**", "/configuration/**", "/swagger-ui.html", "/webjars/**");

}

Perfekt! Das Problem wurde behoben.
Madhu

24

Ich hatte das gleiche Problem mit Spring Boot 2.0.0.M7 + Spring Security + Springfox 2.8.0. Und ich habe das Problem mithilfe der folgenden Sicherheitskonfiguration gelöst, die den öffentlichen Zugriff auf Swagger-UI-Ressourcen ermöglicht.

@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true)
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {

    private static final String[] AUTH_WHITELIST = {
            // -- swagger ui
            "/v2/api-docs",
            "/swagger-resources",
            "/swagger-resources/**",
            "/configuration/ui",
            "/configuration/security",
            "/swagger-ui.html",
            "/webjars/**"
            // other public endpoints of your API may be appended to this array
    };


    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.
                // ... here goes your custom security configuration
                authorizeRequests().
                antMatchers(AUTH_WHITELIST).permitAll().  // whitelist Swagger UI resources
                // ... here goes your custom security configuration
                antMatchers("/**").authenticated();  // require authentication for any endpoint that's not whitelisted
    }

}

2
nachdem diese Klasse hinzufügen, ich bin in der Lage Prahlerei-ui aber APIs ist nicht zugegriffen über Postbote auch mit access_token zu sehen, wie weiter unten Zugang verboten Fehler bekommen,{ "timestamp": 1519798917075, "status": 403, "error": "Forbidden", "message": "Access Denied", "path": "/<some path>/shop" }
Chandrakant Audhutwar

@ChandrakantAudhutwar antMatchers("/**").authenticated()Anweisung löschen oder durch Ihre eigene Authentifizierungskonfiguration ersetzen. Seien Sie vorsichtig, Sie wissen besser, was Sie mit Sicherheit tun.
NaXa

Ja, es hat funktioniert. Ich dachte daran, nur swagger-ui zu umgehen, aber andere APIs, wie es gesichert ist. Jetzt werden auch meine APIs umgangen.
Chandrakant Audhutwar

@ChandrakantAudhutwar Sie müssen nicht die gesamte SecurityConfigurationKlasse kopieren und in Ihr Projekt einfügen . Sie sollten eine eigene haben, SecurityConfigurationin der Sie Anforderungen an Swagger-UI-Ressourcen zulassen und Ihre APIs sicher aufbewahren.
NaXa

Ich habe AuthorizationServerConfigurerAdaptereine Klasse implementiert, die die API-Authentifizierung durchführt.
Chandrakant Audhutwar

12

Für diejenigen, die eine neuere Swagger 3-Version verwenden org.springdoc:springdoc-openapi-ui

@Configuration
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {

    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers("/v3/api-docs/**", "/swagger-ui.html", "/swagger-ui/**");
    }
}

Hinweis: Wenn dies dazu führt, dass Sie nicht den Fehler "Authentifizierung erforderlich" erhalten, sondern nur eine leere Seite angezeigt wird, musste ich dieser Liste auch "/ swagger-resources / **" und "/ swagger-resources" hinzufügen. Dieser Fehler wurde behoben Es für mich.
Vinícius M

5

Wenn Ihre Springfox-Version höher als 2,5 , sein sollte, fügen Sie WebSecurityConfiguration wie folgt hinzu:

@Override
public void configure(HttpSecurity http) throws Exception {
    // TODO Auto-generated method stub
    http.authorizeRequests()
        .antMatchers("/v2/api-docs", "/swagger-resources/configuration/ui", "/swagger-resources", "/swagger-resources/configuration/security", "/swagger-ui.html", "/webjars/**").permitAll()
        .and()
        .authorizeRequests()
        .anyRequest()
        .authenticated()
        .and()
        .csrf().disable();
}

duliu1990 ist richtig, seit springfox 2.5+ sind alle springfox-ressourcen (inklusive prahlerei) untergegangen /swagger-resources. /v2/api-docsist der Standard-Swagger-API-Endpunkt (ohne Bedenken springfox.documentation.swagger.v2.path hinsichtlich
Mahieddine M. Ichir

3

Mehr oder weniger hat diese Seite Antworten, aber alle sind nicht an einem Ort. Ich habe mich mit dem gleichen Thema befasst und ziemlich viel Zeit damit verbracht. Jetzt habe ich ein besseres Verständnis und möchte es hier teilen:

I Aktivieren von Swagger UI mit Spring Websecurity:

Wenn Sie Spring Websecurity standardmäßig aktiviert haben, werden alle Anforderungen an Ihre Anwendung blockiert und 401 zurückgegeben. Damit die Swagger-Benutzeroberfläche jedoch in den Browser geladen wird, führt swagger-ui.html mehrere Aufrufe zum Sammeln von Daten durch. Der beste Weg zum Debuggen ist das Öffnen von swagger-ui.html in einem Browser (wie Google Chrome) und die Verwendung von Entwickleroptionen (Taste 'F12'). Sie können mehrere Aufrufe sehen, die getätigt werden, wenn die Seite geladen wird und wenn die Swagger-Benutzeroberfläche nicht vollständig geladen wird, schlagen wahrscheinlich einige davon fehl.

Möglicherweise müssen Sie Spring websecurity anweisen, die Authentifizierung für mehrere Swagger-Pfadmuster zu ignorieren. Ich benutze swagger-ui 2.9.2 und in meinem Fall unten sind die Muster, die ich ignorieren musste:

Wenn Sie jedoch eine andere Version verwenden, kann sich Ihre ändern. Möglicherweise müssen Sie Ihre mit der Entwickleroption in Ihrem Browser herausfinden, wie ich bereits sagte.

@Configuration
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {
@Override
public void configure(WebSecurity web) throws Exception {
    web.ignoring().antMatchers("/v2/api-docs", "/configuration/ui", 
            "/swagger-resources/**", "/configuration/**", "/swagger-ui.html"
            , "/webjars/**", "/csrf", "/");
}
}

II Swagger-Benutzeroberfläche mit Interceptor aktivieren

Im Allgemeinen möchten Sie möglicherweise keine Anforderungen abfangen, die von swagger-ui.html gestellt werden. Um einige Muster von Prahlerei unten auszuschließen, ist der Code:

Die meisten Fallmuster für Web-Sicherheit und Interceptor sind gleich.

@Configuration
@EnableWebMvc
public class RetrieveCiamInterceptorConfiguration implements WebMvcConfigurer {

@Autowired
RetrieveInterceptor validationInterceptor;

@Override
public void addInterceptors(InterceptorRegistry registry) {

    registry.addInterceptor(validationInterceptor).addPathPatterns("/**")
    .excludePathPatterns("/v2/api-docs", "/configuration/ui", 
            "/swagger-resources/**", "/configuration/**", "/swagger-ui.html"
            , "/webjars/**", "/csrf", "/");
}

@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
    registry.addResourceHandler("swagger-ui.html")
      .addResourceLocations("classpath:/META-INF/resources/");

    registry.addResourceHandler("/webjars/**")
      .addResourceLocations("classpath:/META-INF/resources/webjars/");
}

}

Da Sie möglicherweise @EnableWebMvc aktivieren müssen, um Interceptors hinzuzufügen, müssen Sie möglicherweise auch Ressourcenhandler zu Swagger hinzufügen, ähnlich wie im obigen Code-Snippet.


Warum fügen Sie /csrfAusschluss hinzu?
Vishal

2

Beschränkung nur auf Swagger-bezogene Ressourcen:

.antMatchers("/v2/api-docs", "/swagger-resources/**", "/swagger-ui.html", "/webjars/springfox-swagger-ui/**");

2

Hier ist eine Komplettlösung für Swagger mit Spring Security . Wir möchten Swagger wahrscheinlich nur in unserer Entwicklungs- und QS-Umgebung aktivieren und in der Produktionsumgebung deaktivieren. Daher verwende ich eine Eigenschaft ( prop.swagger.enabled) als Flag, um die Spring-Sicherheitsauthentifizierung für swagger-ui nur in der Entwicklungs- / Qa-Umgebung zu umgehen.

@Configuration
@EnableSwagger2
public class SwaggerConfiguration extends WebSecurityConfigurerAdapter implements WebMvcConfigurer {

@Value("${prop.swagger.enabled:false}")
private boolean enableSwagger;

@Bean
public Docket SwaggerConfig() {
    return new Docket(DocumentationType.SWAGGER_2)
            .enable(enableSwagger)
            .select()
            .apis(RequestHandlerSelectors.basePackage("com.your.controller"))
            .paths(PathSelectors.any())
            .build();
}

@Override
public void configure(WebSecurity web) throws Exception {
    if (enableSwagger)  
        web.ignoring().antMatchers("/v2/api-docs",
                               "/configuration/ui",
                               "/swagger-resources/**",
                               "/configuration/security",
                               "/swagger-ui.html",
                               "/webjars/**");
}

@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
    if (enableSwagger) {
        registry.addResourceHandler("swagger-ui.html").addResourceLocations("classpath:/META-INF/resources/");
        registry.addResourceHandler("/webjars/**").addResourceLocations("classpath:/META-INF/resources/webjars/");
    }
  }
}

1

Ich verwende Spring Boot 5. Ich habe diesen Controller, den ein nicht authentifizierter Benutzer aufrufen soll.

  //Builds a form to send to devices   
@RequestMapping(value = "/{id}/ViewFormit", method = RequestMethod.GET)
@ResponseBody
String doFormIT(@PathVariable String id) {
    try
    {
        //Get a list of forms applicable to the current user
        FormService parent = new FormService();

Hier ist, was ich in der Konfiguration getan habe.

  @Override
   protected void configure(HttpSecurity http) throws Exception {
    http
            .authorizeRequests()
            .antMatchers(
                    "/registration**",
                    "/{^[\\\\d]$}/ViewFormit",

Hoffe das hilft....


0

Wenn Sie alle Ihre API-Anforderungen mit einem URL-Muster von berücksichtigen /api/.., können Sie spring anweisen, nur dieses URL-Muster mithilfe der folgenden Konfiguration zu sichern. Was bedeutet, dass Sie dem Frühling sagen, was zu sichern ist, anstatt was zu ignorieren.

@Override
protected void configure(HttpSecurity http) throws Exception {
  http
    .csrf().disable()
     .authorizeRequests()
      .antMatchers("/api/**").authenticated()
      .anyRequest().permitAll()
      .and()
    .httpBasic().and()
    .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
}

1
Vielen Dank für dieses Code-Snippet, das möglicherweise nur begrenzte kurzfristige Hilfe bietet. Eine richtige Erklärung würde ihren langfristigen Wert erheblich verbessern, indem sie zeigt, warum dies eine gute Lösung für das Problem ist, und es für zukünftige Leser mit anderen, ähnlichen Fragen nützlicher machen. Bitte bearbeiten Sie Ihre Antwort, um eine Erklärung hinzuzufügen, einschließlich der von Ihnen getroffenen Annahmen.
Toby Speight
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.