`
zddava
  • 浏览: 243689 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

Struts2的Action调用(一)

阅读更多
Struts2的Action调用还是要从FilterDispatcher的#doFilter()方法开始说起。

	public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {

		HttpServletRequest request = (HttpServletRequest) req;
		HttpServletResponse response = (HttpServletResponse) res;
		ServletContext servletContext = getServletContext();

		String timerKey = "FilterDispatcher_doFilter: ";
		try {
			UtilTimerStack.push(timerKey);

			/* (1) 对请求进行包装 */
			request = prepareDispatcherAndWrapRequest(request, response);

			ActionMapping mapping;
			try {
				/* (2) 获得Action Mapping */
				mapping = actionMapper.getMapping(request, dispatcher.getConfigurationManager());
			} catch (Exception ex) {
				LOG.error("error getting ActionMapping", ex);
				dispatcher.sendError(request, response, servletContext,
						HttpServletResponse.SC_INTERNAL_SERVER_ERROR, ex);
				return;
			}

			if (mapping == null) {// 当Mapping为空时,检查是否访问的为静态资源
				String resourcePath = RequestUtils.getServletPath(request);

				if ("".equals(resourcePath) && null != request.getPathInfo()) {
					resourcePath = request.getPathInfo();
				}

				if (serveStatic && resourcePath.startsWith("/struts")) {
					String name = resourcePath.substring("/struts".length());
					findStaticResource(name, request, response);
				} else {
					// this is a normal request, let it pass through
					chain.doFilter(request, response);
				}
				// The framework did its job here
				return;
			}

			/* (3) 调用被请求的Action的执行方法(例如execute)和拦截器等 */
			dispatcher.serviceAction(request, response, servletContext, mapping);

		} finally {
			try {
				ActionContextCleanUp.cleanUp(req);
			} finally {
				UtilTimerStack.pop(timerKey);
			}
		}
	}


主要有三个部分需要重点说明:
(1) 对请求进行包装;
(2) 获得Action Mapping;
(3) 调用被请求的Action的执行方法(例如execute)和拦截器等。


下面来一一详细说明:

1. 对请求进行包装:request = prepareDispatcherAndWrapRequest(request, response);

下面来看一下#prepareDispatcherAndWrapRequest()的源代码:

protected HttpServletRequest prepareDispatcherAndWrapRequest(HttpServletRequest request, HttpServletResponse response) throws ServletException {

        Dispatcher du = Dispatcher.getInstance();// (1)

        if (du == null) {
            Dispatcher.setInstance(dispatcher);
            dispatcher.prepare(request, response);// (2)
        } else {
            dispatcher = du;
        }
        
        try {
            request = dispatcher.wrapRequest(request, getServletContext());// (3)
        } catch (IOException e) {
            String message = "Could not wrap servlet request with MultipartRequestWrapper!";
            LOG.error(message, e);
            throw new ServletException(message, e);
        }

        return request;
    }

(1) 这个方法先是获取一个Dispatcher的实例,获取是通过ThreadLocal的方式,可见Struts2框架为每一个线程都提供了一个Dispatcher对象,所以在编写Action的时候不需要考虑多线程的问题了。

(2) 如果是第一次访问FilterDispatcher,那么du应该为null,这时要调用Dispatcher的#prepare()方法:

	public void prepare(HttpServletRequest request, HttpServletResponse response) {
		String encoding = null;
		if (defaultEncoding != null) {
			encoding = defaultEncoding;
		}

		Locale locale = null;
		if (defaultLocale != null) {
			locale = LocalizedTextUtil.localeFromString(defaultLocale, request.getLocale());
		}

		if (encoding != null) {
			try {
				request.setCharacterEncoding(encoding);
			} catch (Exception e) {
				LOG.error("Error setting character encoding to '" + encoding + "' - ignoring.", e);
			}
		}

		if (locale != null) {
			response.setLocale(locale);
		}

		if (paramsWorkaroundEnabled) {
			request.getParameter("foo");
		}
	}


通过源代码可以看出,此方法主要为设置编码和Locale。

(3) 第三步是对请求的包装,request = dispatcher.wrapRequest(request, getServletContext()); 源代码如下:

	public HttpServletRequest wrapRequest(HttpServletRequest request, ServletContext servletContext) throws IOException {
		if (request instanceof StrutsRequestWrapper) {// 判断request是否是StrutsRequestWrapper的对象,保证对request只包装一次。
			return request;
		}

		String content_type = request.getContentType();
		if (content_type != null && content_type.indexOf("multipart/form-data") != -1) {
			MultiPartRequest multi = getContainer().getInstance(MultiPartRequest.class);
			request = new MultiPartRequestWrapper(multi, request, getSaveDir(servletContext));
		} else {
			request = new StrutsRequestWrapper(request);
		}

		return request;
	}


判断Content-Type是否是multipart/form-data,如果是的话返回一个MultiPartRequestWrapper的对象处理文件上传,否则返回StrutsRequestWrapper的对象处理普通请求。

分享到:
评论

相关推荐

    struts 2 action 动态调用

    在Struts 2框架中,Action动态方法调用是一项非常实用的功能。它允许开发者在一个Action类中定义多个处理方法,而不仅仅局限于传统的`execute()`方法。这种机制不仅能够减少代码重复,还能提高代码的可读性和可维护...

    struts2利用通配符调用同一个Action里面不同的方法

    在Struts2中,Action是业务逻辑处理的核心,而通配符的使用则是Struts2框架中一种灵活的配置方式,允许我们以更简洁的方式调用同一个Action中的不同方法。下面我们将深入探讨如何利用Struts2的通配符来实现这一功能...

    Struts2 动态方法调用(十三)

    在Struts2中,动态方法调用(Dynamic Method Invocation,DMI)是一种特性,允许我们通过URL直接调用Action类的方法,而无需在配置文件中显式指定。这在某些情况下提供了更大的灵活性。 在Struts2的动态方法调用中...

    struts2一个action处理多个请求 struts2实例

    在Struts2的配置文件(通常为struts.xml或struts.properties)中,我们定义Action的映射规则,包括请求路径、方法调用以及结果视图等。默认情况下,一个Action类对应一个请求URL,但通过特定配置,可以让一个Action...

    一个Action多方法调用的Struts 2的应用程序

    利用Struts 2框架创建一个web项目chap2_e22,实现用户登录过程。具体要求是在loginAction类中分别用login()和registered()处理用户登录和注册的过程,分别创建login.jsp和register.jsp两个页面实现登录和注册的...

    Struts2动态方法调用

    Struts2的配置文件(struts.xml)可以通过通配符来定义Action,使得一个Action能够处理多个方法调用。例如,我们可以定义一个Action,然后使用不同的参数值来调用不同的Action方法。这样可以减少Action的数量,简化...

    Struts2 Action参数详细说明

    Struts2框架中的Action是核心组件之一,它负责接收HTTP请求并进行业务逻辑处理,然后将控制转向相应的视图进行展示。在Struts2中,Action的配置和使用方式有多种,下面将详细介绍Struts2 Action参数的详细说明。 ...

    Struts2之异步调用机制详解案例struts014

    在Struts2中,异步调用机制是实现页面动态更新和提高用户体验的关键技术之一。这个案例“struts014”很可能展示了如何在Struts2中实现异步调用来处理耗时操作,如数据库查询或复杂计算。 异步调用的基本概念是,...

    struts2 Action 包 命名空间 servlet API

    Struts2是一个强大的Java web应用程序框架,它基于MVC(模型-视图-控制器)设计模式,用于构建高效、可维护的web应用。Struts2是Struts1.x和WebWork社区合作的产物,它的核心设计与Struts1.x有很大的不同,更倾向于...

    Struts2 in action(struts2实战)

    - **Interceptor**(拦截器):拦截器是Struts2的核心组件,它们按照预定义的顺序对Action的调用进行拦截,实现如日志记录、权限验证、事务管理等功能。 2. **配置方式**: - **XML配置**:传统的Struts2配置通常...

    struts2笔记之动态调用Action指定方法及默认Action

    Struts2 动态调用 Action 指定方法及默认 Action 配置 Struts2 框架中,一个 Action 可以包含多个处理逻辑,而不是只有一个 execute() 方法。在实际开发中,我们经常需要在一个 Action 中实现多个处理逻辑,这样...

    Struts 2实战 Struts 2 in action 的中文版

    根据提供的信息,我们可以推断出这是一本关于Struts 2框架的书籍——《Struts 2实战 Struts 2 in action 的中文版》。本书主要介绍了Struts 2框架的相关概念、工作原理以及实际应用案例等内容。接下来,我们将根据...

    struts2动态调用之通配符

    Struts2作为一款流行的Java Web框架,其动态调用功能为开发者提供了极大的便利。在处理多样化的用户请求时,能够灵活地映射不同的操作(methods)到同一个Action,从而简化配置,提高代码的可维护性。本文将深入探讨...

    JS调用Struts中的Action

    ### JS调用Struts中的...此外,随着现代Web开发技术的发展,诸如React、Vue等前端框架的普及,通过API接口进行前后端分离的设计模式也逐渐成为主流,但这并不影响JavaScript调用Struts Action这一知识点的学习和掌握。

    Struts2 in action中文版+配套源代码

    2. **拦截器(Interceptors)**:Struts2的拦截器机制允许开发者定义一系列处理请求的规则,如日志记录、权限检查、事务管理等,这些规则可以在Action执行前后被调用,提高了代码的复用性和模块化。 3. **结果类型...

    Struts2 in action 中文版

    《Struts2 in Action》中文版是一本深入探讨Struts2框架的专业书籍,该书不仅提供了详尽的理论知识,还包含了大量的实战案例,对于希望掌握Struts2框架的开发者来说,是一本不可或缺的参考书。 ### Struts2框架概览...

    ajaxt json 调用struts2 action的实例(myeclipse 直接导入运行)

    ajaxt json 调用struts2 action的实例(myeclipse 直接导入运行) 学习点: 1;怎样在页面用ajax调用struts2的action 2;怎样对struts进行配置 3;ajax的运行历程 最简单明了的实例,清晰的帮你弄清上述概念,运行...

    Struts2 in action 中文版.pdf

    《Struts2 in Action》是一本深入探讨Struts2框架的权威著作,中文版的发布使得国内开发者能够更方便地理解和应用这一强大的Java Web开发框架。Struts2是Apache软件基金会旗下的一个开源项目,它是MVC(Model-View-...

    struts2 action的三种访问方式

    Struts2是一个强大的MVC(模型-视图-控制器)框架,用于构建Java Web应用程序。在Struts2中,Action是处理用户请求的核心组件。它负责业务逻辑的执行,并将结果返回给视图进行展示。本篇文章将详细介绍Struts2 ...

    Struts2SpringUnitDemo单元测试

    4. **Action和Service的测试**:在Struts2中,Action类是处理用户请求的实体,它通常调用Service层来执行业务逻辑。Service层封装了与数据库或其他外部资源的交互。在单元测试中,Action的测试主要检查其接收请求、...

Global site tag (gtag.js) - Google Analytics