每一年都奔走在自己热爱里

没有人是一座孤岛,总有谁爱着你

SpringBoot项目访问swagger-ui.html添加登录页面

1. 方法一

1.1 在pom中引入jar

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>

1.2 然后在yml文件中进行配置

spring:
  security:
    user:
      name: admin #账号
      password: 123456  #密码

2. 方法二

2.1 在pom中引入jar

<dependency>
    <groupId>com.github.xiaoymin</groupId>
    <artifactId>swagger-bootstrap-ui</artifactId>
    <version>1.9.3</version>
</dependency>

2.2 然后在yml文件中进行配置

swagger:
  basic:
    enable: true  #是否开启登录认证
    username: admin   #账号
    password: 123456  #密码

2.3 在 SwaggerConfig 添加 @EnableSwaggerBootstrapUI 的注解

import com.github.xiaoymin.swaggerbootstrapui.annotations.EnableSwaggerBootstrapUI;
@Configuration
@EnableSwagger2
@EnableSwaggerBootstrapUI
public class SwaggerConfig {
    // ........正常配置

}

3. 方法三

3.1 在pom中引入jar

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>

3.2 添加 LoginController

package com.project.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;

@Controller
public class LoginController {

    @GetMapping("/login")
    public String login() {
        // 返回 login.html(Thymeleaf 会自动解析)
        return "login";
    }
}

3.3 在 /src/resources/templates/ 路径下面添加 login.html

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
    <title>Login</title>
</head>
<body>
<div th:if="${param.error}">
    Invalid username and password.
</div>
<form th:action="@{/login}" method="post">
    <div>
        <label>Username: <input type="text" name="username"/></label>
    </div>
    <div>
        <label>Password: <input type="password" name="password"/></label>
    </div>
    <div>
        <input type="submit" value="Sign In"/>
    </div>
</form>
</body>
</html>

3.4 添加 SecurityConfig (注意springboot和security的版本)

package com.project.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.security.web.SecurityFilterChain;

@Configuration
@EnableWebSecurity
public class SecurityConfig {

    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        http
                .authorizeRequests()
                .anyRequest().authenticated()
                .and()
                .formLogin((form) -> form
                        .loginPage("/login")
                        .defaultSuccessUrl("/swagger-ui.html", true)
                        .permitAll()
                )
                .logout((logout) -> logout.permitAll());

        return http.build();
    }

    @Bean
    public UserDetailsService userDetailsService() {
        UserDetails user = User.withDefaultPasswordEncoder()
                .username("admin")
                .password("123456")
                .roles("USER")
                .build();

        return new InMemoryUserDetailsManager(user);
    }
}

4. 方法四

4.1 修改 SecurityConfig

@Override
protected void configure(HttpSecurity httpSecurity) throws Exception {
    httpSecurity
            // CSRF禁用,因为不使用session
            .csrf().disable()
            // --- 核心修复 1:分流认证失败处理器 ---
            .exceptionHandling()
                // 让 Swagger 相关的路径在失败时发起 Basic 认证质询,从而触发浏览器弹窗
                .defaultAuthenticationEntryPointFor(
                    new org.springframework.security.web.authentication.www.BasicAuthenticationEntryPoint() {{
                        setRealmName("Swagger Realm");
                    }}, 
                    // 这里匹配所有需要弹显登录框的路径
                    new org.springframework.security.web.util.matcher.OrRequestMatcher(
                        new org.springframework.security.web.util.matcher.AntPathRequestMatcher("/swagger-ui.html"),
                        new org.springframework.security.web.util.matcher.AntPathRequestMatcher("/*/api-docs"),
                        new org.springframework.security.web.util.matcher.AntPathRequestMatcher("/swagger-resources/**")
                    )
                )
                // 其他普通接口(如 /api/**)继续使用原来的 JSON 返回逻辑
                .authenticationEntryPoint(unauthorizedHandler)
            .and()
            // 基于token,所以不需要session
            .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS).and()
            // 过滤请求
            .authorizeRequests()
            // 对于登录、注册、验证码 以及核心的 /error 路径 允许匿名访问
            // --- 核心修复 2:必须允许匿名访问 /error ---
            .antMatchers("/login", "/register", "/captchaImage", "/error").permitAll()

            // Swagger 和 Druid 相关路径必须认证,且会触发上面配置的弹窗
            .antMatchers("/swagger-ui.html").authenticated()
            .antMatchers("/swagger-resources/**").authenticated()
            .antMatchers("/webjars/**").authenticated()
            .antMatchers("/*/api-docs").authenticated()
            .antMatchers("/druid/**").authenticated()

            // 除上面外的所有请求全部需要鉴权认证
            .anyRequest().authenticated()
            .and()
            .headers().frameOptions().disable()
            .and()
            // 开启 Http Basic 认证
            .httpBasic();

    httpSecurity.logout().logoutUrl("/logout").logoutSuccessHandler(logoutSuccessHandler);
    
    // 添加拦截器逻辑保持不变
    httpSecurity.addFilterBefore(authenticationTokenFilter, UsernamePasswordAuthenticationFilter.class);
    httpSecurity.addFilterBefore(corsFilter, JwtAuthenticationTokenFilter.class);
    httpSecurity.addFilterBefore(corsFilter, LogoutFilter.class);
}

 

posted @ 2026-02-28 16:25  helloliyh  阅读(53)  评论(0)    收藏  举报