Java Spring MVC框架全面讲解

基础知识

一、Spring MVC 基础知识

1. MVC模式与Spring MVC架构
  • MVC模式:Model(数据模型)、View(视图)、Controller(控制器)的解耦设计。
  • Spring MVC流程
    1. 用户请求 → DispatcherServlet(前端控制器)
    2. DispatcherServlet 调用 HandlerMapping 找到对应 Controller
    3. Controller 处理请求,返回 ModelAndView
    4. ViewResolver 解析视图 → 渲染结果返回用户
2. 核心组件
  • DispatcherServlet:中央调度器,接收所有请求。
  • HandlerMapping:映射请求到处理器(Controller方法)。
  • Controller:处理业务逻辑,返回视图或数据。
  • ViewResolver:将逻辑视图名(如home)解析为物理视图(如/WEB-INF/home.jsp)。
3. 基础配置
  • XML配置:定义DispatcherServlet、视图解析器、组件扫描。
  • Java Config(推荐):
    @Configuration
    @EnableWebMvc
    @ComponentScan("com.example.controller")
    public class WebConfig implements WebMvcConfigurer {
        @Bean
        public ViewResolver viewResolver() {
            InternalResourceViewResolver resolver = new InternalResourceViewResolver();
            resolver.setPrefix("/WEB-INF/views/");
            resolver.setSuffix(".jsp");
            return resolver;
        }
    }
    

二、Spring MVC 高级用法

1. 数据绑定与表单处理
  • @RequestParam:获取请求参数。
  • @ModelAttribute:绑定表单数据到对象。
    @PostMapping("/register")
    public String submitForm(@ModelAttribute User user) {
        // 处理用户注册
        return "result";
    }
    
2. 文件上传
  • 配置MultipartResolver
    <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver"/>
    
  • Controller处理上传:
    @PostMapping("/upload")
    public String handleFileUpload(@RequestParam("file") MultipartFile file) {
        if (!file.isEmpty()) {
            // 保存文件
        }
        return "redirect:/success";
    }
    
3. 拦截器(Interceptor)
  • 实现HandlerInterceptor接口:
    public class AuthInterceptor implements HandlerInterceptor {
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
            // 检查用户登录状态
            return true; // 放行请求
        }
    }
    
  • 注册拦截器:
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new AuthInterceptor()).addPathPatterns("/admin/**");
    }
    
4. 全局异常处理
  • 使用@ControllerAdvice
    @ControllerAdvice
    public class GlobalExceptionHandler {
        @ExceptionHandler(Exception.class)
        public ModelAndView handleException(Exception ex) {
            ModelAndView mav = new ModelAndView("error");
            mav.addObject("message", ex.getMessage());
            return mav;
        }
    }
    

三、深入进阶

1. 源码解析
  • DispatcherServlet初始化:加载WebApplicationContext,初始化HandlerMapping、ViewResolver等。
  • 请求处理流程doDispatch()方法源码分析。
2. 扩展Spring MVC
  • 自定义参数解析器:实现HandlerMethodArgumentResolver
  • 自定义视图解析器:实现ViewResolver接口。
3. 异步处理
  • 使用DeferredResultCallable处理耗时操作:
    @GetMapping("/async")
    public DeferredResult<String> asyncTask() {
        DeferredResult<String> result = new DeferredResult<>();
        CompletableFuture.runAsync(() -> {
            // 模拟耗时操作
            result.setResult("Async Result");
        });
        return result;
    }
    
4. 集成其他技术
  • RESTful API:使用@RestController@ResponseBody
  • WebSocket:通过@EnableWebSocket配置实时通信。
  • Spring Security:整合权限控制。

四、完整案例:用户管理系统

1. 功能需求
  • 用户注册/登录
  • 用户信息CRUD
  • 文件上传头像
  • 分页与搜索
2. 技术栈
  • Spring MVC + Thymeleaf(视图模板)
  • MyBatis(持久层)
  • H2 Database(嵌入式数据库)
  • Bootstrap(前端样式)
3. 关键代码片段
  • Controller示例

    @Controller
    @RequestMapping("/user")
    public class UserController {
        @Autowired
        private UserService userService;
    
        @GetMapping("/list")
        public String listUsers(Model model) {
            model.addAttribute("users", userService.findAll());
            return "user/list";
        }
    }
    
  • Thymeleaf视图

    <table>
        <tr th:each="user : ${users}">
            <td th:text="${user.username}">td>
            <td th:text="${user.email}">td>
        tr>
    table>
    

五、学习阶段指引

  1. 基础阶段

    • 掌握Java Web基础(Servlet/JSP)
    • 学习Spring Core(IoC、AOP)
    • 理解MVC模式与HTTP协议
  2. 进阶阶段

    • 深入Spring MVC核心组件
    • 学习数据绑定、拦截器、异常处理
    • 实践文件上传、异步请求
  3. 实战阶段

    • 开发完整项目(如博客系统、电商平台)
    • 集成其他框架(MyBatis、Spring Security)
  4. 高级阶段

    • 阅读Spring MVC源码
    • 研究性能优化(缓存、静态资源处理)
    • 探索微服务架构(Spring Boot + Spring Cloud)

深度解析

六、DispatcherServlet 的工作流程

1. DispatcherServlet 初始化
  • 继承关系DispatcherServletFrameworkServletHttpServletBeanHttpServlet
  • 初始化步骤
    1. 加载WebApplicationContext:通过initWebApplicationContext()方法创建或继承父容器的上下文。
    2. 初始化策略组件:如HandlerMappingHandlerAdapterViewResolver等,通过initStrategies()方法加载。
    3. 默认配置:若未手动配置,Spring MVC会自动注册默认组件(如RequestMappingHandlerMapping)。
2. 请求处理核心方法 doDispatch()
protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
    // 1. 获取HandlerExecutionChain(包含Controller方法及拦截器)
    HandlerExecutionChain mappedHandler = getHandler(request);
    // 2. 获取HandlerAdapter(如RequestMappingHandlerAdapter)
    HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());
    // 3. 执行拦截器的preHandle()
    if (!mappedHandler.applyPreHandle(request, response)) return;
    // 4. 调用Controller方法,返回ModelAndView
    ModelAndView mv = ha.handle(request, response, mappedHandler.getHandler());
    // 5. 处理视图渲染,触发拦截器的postHandle()
    applyDefaultViewName(request, mv);
    mappedHandler.applyPostHandle(request, response, mv);
    // 6. 渲染视图并触发afterCompletion()
    processDispatchResult(request, response, mappedHandler, mv, null);
}
3. 关键源码片段分析
  • HandlerMapping 的匹配逻辑RequestMappingHandlerMapping通过getHandlerInternal()方法匹配URL和@RequestMapping注解。
  • 参数解析与返回值处理HandlerMethodArgumentResolverHandlerMethodReturnValueHandler的扩展机制。

七、性能优化与最佳实践

1. 静态资源处理
  • 避免DispatcherServlet拦截静态资源
    @Override
    public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
        configurer.enable(); // 启用默认Servlet(Tomcat的DefaultServlet)
    }
    
  • 使用资源处理器
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/static/**").addResourceLocations("classpath:/static/");
    }
    
2. 缓存优化
  • 启用HTTP缓存:通过CacheControl配置静态资源缓存策略。
    registry.addResourceHandler("/images/**")
            .addResourceLocations("classpath:/images/")
            .setCacheControl(CacheControl.maxAge(30, TimeUnit.DAYS));
    
3. 异步请求优化
  • 配置异步线程池
    @Bean
    public AsyncTaskExecutor asyncTaskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
        executor.setCorePoolSize(10);
        executor.setMaxPoolSize(50);
        return executor;
    }
    
  • 异步超时处理
    @GetMapping("/async")
    public DeferredResult<String> asyncWithTimeout() {
        DeferredResult<String> result = new DeferredResult<>(5000L); // 5秒超时
        result.onTimeout(() -> result.setErrorResult("Request Timeout"));
        return result;
    }
    

八、高级集成案例:Spring Security + JWT 鉴权

1. 集成Spring Security
  • 依赖配置
    <dependency>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-starter-securityartifactId>
    dependency>
    
  • 基础安全配置
    @Configuration
    @EnableWebSecurity
    public class SecurityConfig extends WebSecurityConfigurerAdapter {
        @Override
        protected void configure(HttpSecurity http) throws Exception {
            http.authorizeRequests()
                    .antMatchers("/public/**").permitAll()
                    .anyRequest().authenticated()
                    .and().formLogin();
        }
    }
    
2. JWT 鉴权实现
  • 生成与验证JWT Token
    public class JwtUtils {
        public static String generateToken(String username) {
            return Jwts.builder()
                    .setSubject(username)
                    .setExpiration(new Date(System.currentTimeMillis() + 3600 * 1000))
                    .signWith(SignatureAlgorithm.HS512, "secretKey")
                    .compact();
        }
    }
    
  • 自定义JWT过滤器
    public class JwtFilter extends OncePerRequestFilter {
        @Override
        protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain) {
            String token = request.getHeader("Authorization");
            if (validateToken(token)) {
                // 解析Token并设置SecurityContext
            }
            chain.doFilter(request, response);
        }
    }
    

九、测试驱动开发:Spring MVC 单元测试

1. 使用MockMvc测试Controller
@SpringBootTest
@AutoConfigureMockMvc
public class UserControllerTest {
    @Autowired
    private MockMvc mockMvc;

    @Test
    public void testGetUser() throws Exception {
        mockMvc.perform(get("/user/1"))
               .andExpect(status().isOk())
               .andExpect(jsonPath("$.username").value("admin"));
    }
}
2. 集成测试与数据库回滚
@SpringBootTest
@Transactional
@Rollback
public class UserServiceTest {
    @Autowired
    private UserService userService;

    @Test
    public void testCreateUser() {
        User user = new User("test", "[email protected]");
        userService.save(user);
        assertNotNull(userService.findByEmail("[email protected]"));
    }
}

十、Spring Boot 与 Spring MVC 的现代化实践

1. 快速启动Spring Boot项目
  • 使用Spring Initializr:选择Web、Thymeleaf、Security等依赖。
  • 简化配置
    # application.properties
    spring.mvc.view.prefix=/WEB-INF/views/
    spring.mvc.view.suffix=.jsp
    
2. 构建RESTful API
  • 使用@RestController
    @RestController
    @RequestMapping("/api/users")
    public class UserApiController {
        @GetMapping
        public List<User> listUsers() {
            return userService.findAll();
        }
    }
    
  • 统一响应格式
    public class ApiResponse<T> {
        private int code;
        private String message;
        private T data;
        // 构造方法、Getter/Setter
    }
    
3. 微服务化改造
  • 集成Spring Cloud:使用Feign、Eureka、Hystrix等组件。
  • API网关:通过Spring Cloud Gateway统一路由。

十一、学习路径扩展

1. 深入源码
  • 阅读Spring官方文档:理解设计哲学与核心接口(如ApplicationContextBeanFactory)。
  • 调试Spring MVC流程:从DispatcherServletdoDispatch()方法入手。
2. 实战项目推荐
  • 电商平台:商品管理、订单支付、购物车模块。
  • 在线教育系统:课程发布、视频流处理、权限分级。
  • 实时聊天应用:集成WebSocket与消息队列(如RabbitMQ)。
3. 社区与资源
  • 参与开源项目:GitHub上的Spring生态项目(如Spring PetClinic)。
  • 技术博客:Spring官方博客、Baeldung、Stack Overflow问答。

你可能感兴趣的:(java,java,spring,mvc)