Struts2 约定插件 @Actions 未与 Spring 引导映射
Struts2 Convention Plugin @Actions not mapping with Spring Boot
升级我的应用程序以使用 Spring 引导版本 2.1.8.RELEASE + struts2-convention-plugin使用 Struts2-核心版本 2.5.20 操作未正确映射,我收到错误
com.opensymphony.xwork2.config.ConfigurationException: There is no
Action mapped for namespace [/] and action name [home] associated with
context path [].
如果我对 struts.xml
中的动作进行 decalre,它们将完美运行。
下面是我目前的配置,为什么没有映射?
我尝试了很多不同的配置,但似乎没有任何效果,StrutsPrepareAndExecuteFilter
正在触发但未找到任何操作,就好像 Spring 没有扫描它们一样。这可能是依赖版本问题吗?
application.yaml
server:
port: 8080
servlet:
context-path: /
Struts2.xml
<struts>
<constant name="struts.devMode" value="false" />
<constant name="struts.convention.action.packages" value="com.myactions.action" />
<constant name="struts.convention.action.includeJars" value=".*?/myjar.*?jar(!/)?,.*?/myjar*?jar(!/)?" />
<constant name="struts.objectFactory" value="spring" />
<constant name="struts.objectFactory.spring.autoWire" value="name" />
<constant name="struts.multipart.maxSize" value="100000000" />
<constant name="struts.convention.default.parent.package" value="struts-default"/>
## THIS WORKS
<!-- <package name="home" extends="struts-default">-->
<!-- <action name="actionHome" class="com.myactions.action.HomeController" method="actionHome">-->
<!-- <result name="success">home.jsp</result>-->
<!-- </action>-->
<!-- </package>-->
</struts>
控制器
@Namespace("/")
public class HomeController extends BaseController {
@Action("home")
public String actionHome() throws Exception {
return SUCCESS;
}
}
主要
@SpringBootApplication
@ServletComponentScan
public class Application extends SpringBootServletInitializer {
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder springApplicationBuilder) {
return springApplicationBuilder.sources(Application.class);
}
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
Struts2 过滤器
@WebFilter("/*")
public class Struts2Filter extends StrutsPrepareAndExecuteFilter {
}
更新
逐步完成 spring2-convention-plugin
class PackageBasedActionConfigBuilder
有一个方法 buildUrlSet
可以获取所有需要的 urls
到 class要扫描 Actions
,这是将 urls
删除到我的 classes,因此没有扫描任何内容。
有个条件excludeParentClassLoader
需要设置为false
(第415行).
解决方案
将下面的常量设置为 -
<constant name="struts.convention.exclude.parentClassLoader" value="false" />
<constant name="struts.convention.action.fileProtocols" value="jar,code-source" />
经过几天的反复试验,这里有一些线索。
Spring 引导 2.1.8 与 Struts 2.5.20 配置 struts.xml 工作。
您的项目 POM 至少需要以下依赖项:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>2.1.8</version>
</dependency>
...
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-core</artifactId>
<version>${struts2.version}</version>
</dependency>
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-spring-plugin</artifactId>
<version>2.5.20</version>
</dependency>
我还建议添加 Config Browser Plugin 以轻松列出可用操作:
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-config-browser-plugin</artifactId>
<version>2.5.20</version>
</dependency>
打包时有效:
- 带有嵌入式 Tomcat 服务器的胖 JAR,这是默认行为
- 一个WAR in an external Tomcat Server
要摆脱 struts.xml 并仅通过 Java 配置您的操作 类,需要 Convention plugin:
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-convention-plugin</artifactId>
<version>2.5.20</version>
</dependency>
备注:
- struts.xml中定义的常量也可以迁移到struts.properties文件中(默认值列出here)
- struts.xml 优先于 Convention 插件和 struts.properties
当 struts.xml 被删除时,约定插件接管并使用包名和 类 映射操作 类。由于一组 annotations.
,默认约定(操作到 URL 映射、结果路径...)也可以被覆盖
不过,正如 OP 所提到的,通过注释进行配置确实 NOT 开箱即用,带有嵌入式 Tomcat(它与外部 Tomcat, 虽然).
到目前为止我能做的最好的就是使用 embedded Jetty instead of Tomcat, and adding the recommended configuration 到 struts.properties:
struts.convention.exclude.parentClassLoader=false
struts.convention.action.fileProtocols=jar,code-source
启动日志仍然显示错误,但我可以访问已配置的操作而无需更多 XML。
更新
OP 更新后,我又深入了解了一些。事实证明,通过执行以下操作,约定插件在 Tomcat 嵌入的情况下工作正常,不需要 XML:
将以下行添加到 struts.properties
struts.convention.exclude.parentClassLoader=false
升级 asm 模块 asm、asm-commons 和 asm- tree 发布 6.2 或更高版本以防止类似于
的错误
ERROR org.apache.struts2.convention.DefaultClassFinder.<init>:95 - Unable to read class [...]
升级我的应用程序以使用 Spring 引导版本 2.1.8.RELEASE + struts2-convention-plugin使用 Struts2-核心版本 2.5.20 操作未正确映射,我收到错误
com.opensymphony.xwork2.config.ConfigurationException: There is no Action mapped for namespace [/] and action name [home] associated with context path [].
如果我对 struts.xml
中的动作进行 decalre,它们将完美运行。
下面是我目前的配置,为什么没有映射?
我尝试了很多不同的配置,但似乎没有任何效果,StrutsPrepareAndExecuteFilter
正在触发但未找到任何操作,就好像 Spring 没有扫描它们一样。这可能是依赖版本问题吗?
application.yaml
server:
port: 8080
servlet:
context-path: /
Struts2.xml
<struts>
<constant name="struts.devMode" value="false" />
<constant name="struts.convention.action.packages" value="com.myactions.action" />
<constant name="struts.convention.action.includeJars" value=".*?/myjar.*?jar(!/)?,.*?/myjar*?jar(!/)?" />
<constant name="struts.objectFactory" value="spring" />
<constant name="struts.objectFactory.spring.autoWire" value="name" />
<constant name="struts.multipart.maxSize" value="100000000" />
<constant name="struts.convention.default.parent.package" value="struts-default"/>
## THIS WORKS
<!-- <package name="home" extends="struts-default">-->
<!-- <action name="actionHome" class="com.myactions.action.HomeController" method="actionHome">-->
<!-- <result name="success">home.jsp</result>-->
<!-- </action>-->
<!-- </package>-->
</struts>
控制器
@Namespace("/")
public class HomeController extends BaseController {
@Action("home")
public String actionHome() throws Exception {
return SUCCESS;
}
}
主要
@SpringBootApplication
@ServletComponentScan
public class Application extends SpringBootServletInitializer {
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder springApplicationBuilder) {
return springApplicationBuilder.sources(Application.class);
}
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
Struts2 过滤器
@WebFilter("/*")
public class Struts2Filter extends StrutsPrepareAndExecuteFilter {
}
更新
逐步完成 spring2-convention-plugin
class PackageBasedActionConfigBuilder
有一个方法 buildUrlSet
可以获取所有需要的 urls
到 class要扫描 Actions
,这是将 urls
删除到我的 classes,因此没有扫描任何内容。
有个条件excludeParentClassLoader
需要设置为false
(第415行).
解决方案
将下面的常量设置为 -
<constant name="struts.convention.exclude.parentClassLoader" value="false" />
<constant name="struts.convention.action.fileProtocols" value="jar,code-source" />
经过几天的反复试验,这里有一些线索。
Spring 引导 2.1.8 与 Struts 2.5.20 配置 struts.xml 工作。 您的项目 POM 至少需要以下依赖项:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>2.1.8</version>
</dependency>
...
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-core</artifactId>
<version>${struts2.version}</version>
</dependency>
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-spring-plugin</artifactId>
<version>2.5.20</version>
</dependency>
我还建议添加 Config Browser Plugin 以轻松列出可用操作:
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-config-browser-plugin</artifactId>
<version>2.5.20</version>
</dependency>
打包时有效:
- 带有嵌入式 Tomcat 服务器的胖 JAR,这是默认行为
- 一个WAR in an external Tomcat Server
要摆脱 struts.xml 并仅通过 Java 配置您的操作 类,需要 Convention plugin:
<dependency>
<groupId>org.apache.struts</groupId>
<artifactId>struts2-convention-plugin</artifactId>
<version>2.5.20</version>
</dependency>
备注:
- struts.xml中定义的常量也可以迁移到struts.properties文件中(默认值列出here)
- struts.xml 优先于 Convention 插件和 struts.properties
当 struts.xml 被删除时,约定插件接管并使用包名和 类 映射操作 类。由于一组 annotations.
,默认约定(操作到 URL 映射、结果路径...)也可以被覆盖不过,正如 OP 所提到的,通过注释进行配置确实 NOT 开箱即用,带有嵌入式 Tomcat(它与外部 Tomcat, 虽然).
到目前为止我能做的最好的就是使用 embedded Jetty instead of Tomcat, and adding the recommended configuration 到 struts.properties:
struts.convention.exclude.parentClassLoader=false
struts.convention.action.fileProtocols=jar,code-source
启动日志仍然显示错误,但我可以访问已配置的操作而无需更多 XML。
更新
OP 更新后,我又深入了解了一些。事实证明,通过执行以下操作,约定插件在 Tomcat 嵌入的情况下工作正常,不需要 XML:
将以下行添加到 struts.properties
struts.convention.exclude.parentClassLoader=false
升级 asm 模块 asm、asm-commons 和 asm- tree 发布 6.2 或更高版本以防止类似于
的错误ERROR org.apache.struts2.convention.DefaultClassFinder.<init>:95 - Unable to read class [...]