编程技术分享平台

网站首页 > 技术教程 正文

SpringMVC疑难一:mvc:annotation-dr

xnh888 2024-10-19 16:00:45 技术教程 24 ℃ 0 评论

最近没有发文,因为前几天写的两篇都被头条以全网出现过的理由拒掉了。技术文章不是每日新闻,部分内容重复是很正常的现象,有点怀疑头条不适合发技术文章了。

SpringMVC的学习,相信很多程序员是照虎画猫学的,而且版本迭代又快,没有太多时间去看一下到底是怎么回事。这不,一个小兄弟在实际应用过程中出现了一个问题,<mvc:annotation-driven>放置在不同的配置文件中有的不起作用。

问题描述

我们知道,一个maven web工程有至少有一个Spring配置文件(applicationContext.xml),一个SpringMVC配置文件(xxx-servlet.xml),一般都是这么命名的,如果第二个配置,那么SpirngMVC会默认找/WEB-INF/${servlet-name}-servlet.xml文件。

ApplicationContext.xml的配置(xml文件命名空间之类的不贴了,聚焦问题):

<context:annotation-config />

<context:component-scan base-package="com.niucoding.mall.controller"/>

这个主要是配置了Spring的注解和扫描的包,另一个springmvc-servlet.xml配置如下:

<mvc:annotation-driven/>

<!-- ViewResolver -->

<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">

<property name="prefix" value="/WEB-INF/jsp/"/>

<property name="suffix" value=".jsp"/>

<property name="viewClass">

<value>org.springframework.web.servlet.view.InternalResourceView</value>

</property>

<property name="order" value="1"/>

</bean>

很简答的工程,只有一个test.jsp,但是一直报错404, no mapping。

解决过程

首先检查各种配置,扫描路径,发现没问题,中间尝试无数次,血泪史不表...

最后,使出了必杀技能,copy了一份其他工程的配置,问题解决了,重点对比发现是:

<mvc:annotation-driven/>文件放置不对,如果放在applicationContext.xml中,就可以正常运行,而放在springmvc-servlet.xml中则不能运行。

问题分析

看着小弟一脸懵逼的神情,略微解释一下,不过,我也还有一点不太理解的地方,留着给各位看官解决吧。

首先,我们说一下web.xml的加载顺序,这个大家都不陌生了,listener之后才会加载servlet,也就是说applicationContext.xml首先被Spring容器(ApplicationContext)加载。

然后,servlet初识化的时候,SpringVMC容器(WebApplicationContext,这个是上一个容器的子容器,可以通过parent拿到Spring容器),加载springmvc-servlet.xml。

如果<mvc:annotation-driven/>标签放在applicationContext.xml中,这个没有问题,Spring容器初始化的时候会从@Controller等注解中提取url , 并建立url 到 方法的映射;

如果放在spingmvc-servlet.xml ,Spring 容器加载的时候并不知道这个标签存在,所以只提取了URL,而没有建立映射;

SpringMVC容器在初始化的时候也没建立映射,所以出现了no mapping的错误。

疑难杂症

关于上面的分析,我也看了一下源代码,应该是对的。但是,有一点没有搞清楚的是,SpringMVC容器(暂时这么叫吧)为什么没有建立这种映射?我觉得设计角度来说,这个职责本来就应该是SpringMVC的,而不是Spring的。诸位大侠,有时间有兴趣的可以看一下SpringMVC的代码,给我解惑。

Tags:

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表