2、struct2的工作流程
1、首先执行StrutsPrepareAndExecuteFilter,调用StrutsPrepareAndExecuteFilter类的doFilter方法
在该方法中会产生一个ActionMapping 对象,如果客户端访问不是action对象,例如访问jsp对象ActionMapping 就为空
如果访问是action对象,则ActionMapping 不为null执行
2、execute.executeAction(request, response, mapping);该方法调用下面的dispatcher.serviceAction(request, response, servletContext, mapping);
3、在dispatcher.serviceAction(request, response, servletContext, mapping);调用下面的函数
ActionProxy proxy = config.getContainer().getInstance(ActionProxyFactory.class).createActionProxy(
namespace, name, method, extraContext, true, false);
创建一个ActionProxy 代理对象
public ActionProxy createActionProxy(String namespace, String actionName, String methodName, Map<String, Object> extraContext, boolean executeResult, boolean cleanupContext) {
ActionInvocation inv = new DefaultActionInvocation(extraContext, true);
container.inject(inv);
return createActionProxy(inv, namespace, actionName, methodName, executeResult, cleanupContext);
}
在创建代理对象的同时创建了ActionInvocation 对象
4、
/*
* $Id: DefaultActionSupport.java 651946 2008-04-27 13:41:38Z apetrelli $
*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.struts2.dispatcher.ng.filter; import org.apache.struts2.StrutsStatics;
import org.apache.struts2.dispatcher.Dispatcher;
import org.apache.struts2.dispatcher.mapper.ActionMapping;
import org.apache.struts2.dispatcher.ng.ExecuteOperations;
import org.apache.struts2.dispatcher.ng.InitOperations;
import org.apache.struts2.dispatcher.ng.PrepareOperations; import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;
import java.util.regex.Pattern; /**
* Handles both the preparation and execution phases of the Struts dispatching process. This filter is better to use
* when you don't have another filter that needs access to action context information, such as Sitemesh.
*/
public class StrutsPrepareAndExecuteFilter implements StrutsStatics, Filter {
protected PrepareOperations prepare;
protected ExecuteOperations execute;
protected List<Pattern> excludedPatterns = null; public void init(FilterConfig filterConfig) throws ServletException {
InitOperations init = new InitOperations();
try {
FilterHostConfig config = new FilterHostConfig(filterConfig);
init.initLogging(config);
Dispatcher dispatcher = init.initDispatcher(config);
init.initStaticContentLoader(config, dispatcher); prepare = new PrepareOperations(filterConfig.getServletContext(), dispatcher);
execute = new ExecuteOperations(filterConfig.getServletContext(), dispatcher);
this.excludedPatterns = init.buildExcludedPatternsList(dispatcher); postInit(dispatcher, filterConfig);
} finally {
init.cleanup();
} } /**
* Callback for post initialization
*/
protected void postInit(Dispatcher dispatcher, FilterConfig filterConfig) {
} public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException { HttpServletRequest request = (HttpServletRequest) req;
HttpServletResponse response = (HttpServletResponse) res; try {
prepare.setEncodingAndLocale(request, response);
prepare.createActionContext(request, response);
prepare.assignDispatcherToThread();
if ( excludedPatterns != null && prepare.isUrlExcluded(request, excludedPatterns)) {
chain.doFilter(request, response);
} else {
request = prepare.wrapRequest(request);
ActionMapping mapping = prepare.findActionMapping(request, response, true);
if (mapping == null) {
boolean handled = execute.executeStaticResourceRequest(request, response);
if (!handled) {
chain.doFilter(request, response);
}
} else {
execute.executeAction(request, response, mapping);
}
}
} finally {
prepare.cleanupRequest(request);
}
} public void destroy() {
prepare.cleanupDispatcher();
}
}
/*
* $Id: DefaultActionSupport.java 651946 2008-04-27 13:41:38Z apetrelli $
*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.struts2.dispatcher.ng; import org.apache.struts2.dispatcher.Dispatcher;
import org.apache.struts2.dispatcher.StaticContentLoader;
import org.apache.struts2.dispatcher.mapper.ActionMapping;
import org.apache.struts2.RequestUtils; import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException; /**
* Contains execution operations for filters
*/
public class ExecuteOperations {
private ServletContext servletContext;
private Dispatcher dispatcher; public ExecuteOperations(ServletContext servletContext, Dispatcher dispatcher) {
this.dispatcher = dispatcher;
this.servletContext = servletContext;
} /**
* Tries to execute a request for a static resource
* @return True if it was handled, false if the filter should fall through
* @throws IOException
* @throws ServletException
*/
public boolean executeStaticResourceRequest(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
// there is no action in this request, should we look for a static resource?
String resourcePath = RequestUtils.getServletPath(request); if ("".equals(resourcePath) && null != request.getPathInfo()) {
resourcePath = request.getPathInfo();
} StaticContentLoader staticResourceLoader = dispatcher.getContainer().getInstance(StaticContentLoader.class);
if (staticResourceLoader.canHandle(resourcePath)) {
staticResourceLoader.findStaticResource(resourcePath, request, response);
// The framework did its job here
return true; } else {
// this is a normal request, let it pass through
return false;
}
} /**
* Executes an action
* @throws ServletException
*/
public void executeAction(HttpServletRequest request, HttpServletResponse response, ActionMapping mapping) throws ServletException {
dispatcher.serviceAction(request, response, servletContext, mapping);
}
}
/*
* $Id: Dispatcher.java 783012 2009-06-09 14:15:54Z wesw $
*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/ package org.apache.struts2.dispatcher; import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.CopyOnWriteArrayList; import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; import org.apache.struts2.ServletActionContext;
import org.apache.struts2.StrutsConstants;
import org.apache.struts2.StrutsStatics;
import org.apache.struts2.StrutsException;
import org.apache.struts2.config.BeanSelectionProvider;
import org.apache.struts2.config.DefaultPropertiesProvider;
import org.apache.struts2.config.LegacyPropertiesConfigurationProvider;
import org.apache.struts2.config.StrutsXmlConfigurationProvider;
import org.apache.struts2.dispatcher.mapper.ActionMapping;
import org.apache.struts2.dispatcher.multipart.MultiPartRequest;
import org.apache.struts2.dispatcher.multipart.MultiPartRequestWrapper;
import org.apache.struts2.util.AttributeMap;
import org.apache.struts2.util.ClassLoaderUtils;
import org.apache.struts2.util.ObjectFactoryDestroyable;
import org.apache.struts2.views.freemarker.FreemarkerManager; import com.opensymphony.xwork2.ActionContext;
import com.opensymphony.xwork2.ActionProxy;
import com.opensymphony.xwork2.ActionProxyFactory;
import com.opensymphony.xwork2.ObjectFactory;
import com.opensymphony.xwork2.Result;
import com.opensymphony.xwork2.config.Configuration;
import com.opensymphony.xwork2.config.ConfigurationException;
import com.opensymphony.xwork2.config.ConfigurationManager;
import com.opensymphony.xwork2.config.ConfigurationProvider;
import com.opensymphony.xwork2.config.entities.InterceptorMapping;
import com.opensymphony.xwork2.config.entities.InterceptorStackConfig;
import com.opensymphony.xwork2.config.entities.PackageConfig;
import com.opensymphony.xwork2.config.providers.XmlConfigurationProvider;
import com.opensymphony.xwork2.inject.Container;
import com.opensymphony.xwork2.inject.ContainerBuilder;
import com.opensymphony.xwork2.inject.Inject;
import com.opensymphony.xwork2.interceptor.Interceptor;
import com.opensymphony.xwork2.util.FileManager;
import com.opensymphony.xwork2.util.LocalizedTextUtil;
import com.opensymphony.xwork2.util.ValueStack;
import com.opensymphony.xwork2.util.ValueStackFactory;
import com.opensymphony.xwork2.util.location.LocatableProperties;
import com.opensymphony.xwork2.util.location.Location;
import com.opensymphony.xwork2.util.location.LocationUtils;
import com.opensymphony.xwork2.util.logging.Logger;
import com.opensymphony.xwork2.util.logging.LoggerFactory;
import com.opensymphony.xwork2.util.profiling.UtilTimerStack; import freemarker.template.Template; /**
* A utility class the actual dispatcher delegates most of its tasks to. Each instance
* of the primary dispatcher holds an instance of this dispatcher to be shared for
* all requests.
*
* @see org.apache.struts2.dispatcher.FilterDispatcher
*/
public class Dispatcher { /**
* Provide a logging instance.
*/
private static final Logger LOG = LoggerFactory.getLogger(Dispatcher.class); /**
* Provide a thread local instance.
*/
private static ThreadLocal<Dispatcher> instance = new ThreadLocal<Dispatcher>(); /**
* Store list of DispatcherListeners.
*/
private static List<DispatcherListener> dispatcherListeners =
new CopyOnWriteArrayList<DispatcherListener>(); /**
* Store ConfigurationManager instance, set on init.
*/
private ConfigurationManager configurationManager; /**
* Store state of StrutsConstants.STRUTS_DEVMODE setting.
*/
private boolean devMode; /**
* Store state of StrutsConstants.STRUTS_I18N_ENCODING setting.
*/
private String defaultEncoding; /**
* Store state of StrutsConstants.STRUTS_LOCALE setting.
*/
private String defaultLocale; /**
* Store state of StrutsConstants.STRUTS_MULTIPART_SAVEDIR setting.
*/
private String multipartSaveDir; /**
* Stores the value of StrutsConstants.STRUTS_MULTIPART_HANDLER setting
*/
private String multipartHandlerName; /**
* Provide list of default configuration files.
*/
private static final String DEFAULT_CONFIGURATION_PATHS = "struts-default.xml,struts-plugin.xml,struts.xml"; /**
* Store state of STRUTS_DISPATCHER_PARAMETERSWORKAROUND.
* <p/>
* The workaround is for WebLogic.
* We try to autodect WebLogic on Dispatcher init.
* The workaround can also be enabled manually.
*/
private boolean paramsWorkaroundEnabled = false; /**
* Provide the dispatcher instance for the current thread.
*
* @return The dispatcher instance
*/
public static Dispatcher getInstance() {
return instance.get();
} /**
* Store the dispatcher instance for this thread.
*
* @param instance The instance
*/
public static void setInstance(Dispatcher instance) {
Dispatcher.instance.set(instance);
} /**
* Add a dispatcher lifecycle listener.
*
* @param listener The listener to add
*/
public static void addDispatcherListener(DispatcherListener listener) {
dispatcherListeners.add(listener);
} /**
* Remove a specific dispatcher lifecycle listener.
*
* @param listener The listener
*/
public static void removeDispatcherListener(DispatcherListener listener) {
dispatcherListeners.remove(listener);
} private ServletContext servletContext;
private Map<String, String> initParams; private ValueStackFactory valueStackFactory; /**
* Create the Dispatcher instance for a given ServletContext and set of initialization parameters.
*
* @param servletContext Our servlet context
* @param initParams The set of initialization parameters
*/
public Dispatcher(ServletContext servletContext, Map<String, String> initParams) {
this.servletContext = servletContext;
this.initParams = initParams;
} /**
* Modify state of StrutsConstants.STRUTS_DEVMODE setting.
* @param mode New setting
*/
@Inject(StrutsConstants.STRUTS_DEVMODE)
public void setDevMode(String mode) {
devMode = "true".equals(mode);
} /**
* Modify state of StrutsConstants.STRUTS_LOCALE setting.
* @param val New setting
*/
@Inject(value=StrutsConstants.STRUTS_LOCALE, required=false)
public void setDefaultLocale(String val) {
defaultLocale = val;
} /**
* Modify state of StrutsConstants.STRUTS_I18N_ENCODING setting.
* @param val New setting
*/
@Inject(StrutsConstants.STRUTS_I18N_ENCODING)
public void setDefaultEncoding(String val) {
defaultEncoding = val;
} /**
* Modify state of StrutsConstants.STRUTS_MULTIPART_SAVEDIR setting.
* @param val New setting
*/
@Inject(StrutsConstants.STRUTS_MULTIPART_SAVEDIR)
public void setMultipartSaveDir(String val) {
multipartSaveDir = val;
} @Inject(StrutsConstants.STRUTS_MULTIPART_HANDLER)
public void setMultipartHandler(String val) {
multipartHandlerName = val;
} @Inject
public void setValueStackFactory(ValueStackFactory valueStackFactory) {
this.valueStackFactory = valueStackFactory;
} /**
* Releases all instances bound to this dispatcher instance.
*/
public void cleanup() { // clean up ObjectFactory
ObjectFactory objectFactory = getContainer().getInstance(ObjectFactory.class);
if (objectFactory == null) {
LOG.warn("Object Factory is null, something is seriously wrong, no clean up will be performed");
}
if (objectFactory instanceof ObjectFactoryDestroyable) {
try {
((ObjectFactoryDestroyable)objectFactory).destroy();
}
catch(Exception e) {
// catch any exception that may occured during destroy() and log it
LOG.error("exception occurred while destroying ObjectFactory ["+objectFactory+"]", e);
}
} // clean up Dispatcher itself for this thread
instance.set(null); // clean up DispatcherListeners
if (!dispatcherListeners.isEmpty()) {
for (DispatcherListener l : dispatcherListeners) {
l.dispatcherDestroyed(this);
}
} // clean up all interceptors by calling their destroy() method
Set<Interceptor> interceptors = new HashSet<Interceptor>();
Collection<PackageConfig> packageConfigs = configurationManager.getConfiguration().getPackageConfigs().values();
for (PackageConfig packageConfig : packageConfigs) {
for (Object config : packageConfig.getAllInterceptorConfigs().values()) {
if (config instanceof InterceptorStackConfig) {
for (InterceptorMapping interceptorMapping : ((InterceptorStackConfig) config).getInterceptors()) {
interceptors.add(interceptorMapping.getInterceptor());
}
}
}
}
for (Interceptor interceptor : interceptors) {
interceptor.destroy();
} //cleanup action context
ActionContext.setContext(null); // clean up configuration
configurationManager.destroyConfiguration();
configurationManager = null;
} private void init_DefaultProperties() {
configurationManager.addConfigurationProvider(new DefaultPropertiesProvider());
} private void init_LegacyStrutsProperties() {
configurationManager.addConfigurationProvider(new LegacyPropertiesConfigurationProvider());
} private void init_TraditionalXmlConfigurations() {
String configPaths = initParams.get("config");
if (configPaths == null) {
configPaths = DEFAULT_CONFIGURATION_PATHS;
}
String[] files = configPaths.split("\\s*[,]\\s*");
for (String file : files) {
if (file.endsWith(".xml")) {
if ("xwork.xml".equals(file)) {
configurationManager.addConfigurationProvider(new XmlConfigurationProvider(file, false));
} else {
configurationManager.addConfigurationProvider(new StrutsXmlConfigurationProvider(file, false, servletContext));
}
} else {
throw new IllegalArgumentException("Invalid configuration file name");
}
}
} private void init_CustomConfigurationProviders() {
String configProvs = initParams.get("configProviders");
if (configProvs != null) {
String[] classes = configProvs.split("\\s*[,]\\s*");
for (String cname : classes) {
try {
Class cls = ClassLoaderUtils.loadClass(cname, this.getClass());
ConfigurationProvider prov = (ConfigurationProvider)cls.newInstance();
configurationManager.addConfigurationProvider(prov);
} catch (InstantiationException e) {
throw new ConfigurationException("Unable to instantiate provider: "+cname, e);
} catch (IllegalAccessException e) {
throw new ConfigurationException("Unable to access provider: "+cname, e);
} catch (ClassNotFoundException e) {
throw new ConfigurationException("Unable to locate provider class: "+cname, e);
}
}
}
} private void init_FilterInitParameters() {
configurationManager.addConfigurationProvider(new ConfigurationProvider() {
public void destroy() {}
public void init(Configuration configuration) throws ConfigurationException {}
public void loadPackages() throws ConfigurationException {}
public boolean needsReload() { return false; } public void register(ContainerBuilder builder, LocatableProperties props) throws ConfigurationException {
props.putAll(initParams);
}
});
} private void init_AliasStandardObjects() {
configurationManager.addConfigurationProvider(new BeanSelectionProvider());
} private Container init_PreloadConfiguration() {
Configuration config = configurationManager.getConfiguration();
Container container = config.getContainer(); boolean reloadi18n = Boolean.valueOf(container.getInstance(String.class, StrutsConstants.STRUTS_I18N_RELOAD));
LocalizedTextUtil.setReloadBundles(reloadi18n); return container;
} private void init_CheckConfigurationReloading(Container container) {
FileManager.setReloadingConfigs("true".equals(container.getInstance(String.class,
StrutsConstants.STRUTS_CONFIGURATION_XML_RELOAD)));
} private void init_CheckWebLogicWorkaround(Container container) {
// test whether param-access workaround needs to be enabled
if (servletContext != null && servletContext.getServerInfo() != null
&& servletContext.getServerInfo().indexOf("WebLogic") >= 0) {
LOG.info("WebLogic server detected. Enabling Struts parameter access work-around.");
paramsWorkaroundEnabled = true;
} else {
paramsWorkaroundEnabled = "true".equals(container.getInstance(String.class,
StrutsConstants.STRUTS_DISPATCHER_PARAMETERSWORKAROUND));
}
} /**
* Load configurations, including both XML and zero-configuration strategies,
* and update optional settings, including whether to reload configurations and resource files.
*/
public void init() { if (configurationManager == null) {
configurationManager = new ConfigurationManager(BeanSelectionProvider.DEFAULT_BEAN_NAME);
} try {
init_DefaultProperties(); // [1]
init_TraditionalXmlConfigurations(); // [2]
init_LegacyStrutsProperties(); // [3]
init_CustomConfigurationProviders(); // [5]
init_FilterInitParameters() ; // [6]
init_AliasStandardObjects() ; // [7] Container container = init_PreloadConfiguration();
container.inject(this);
init_CheckConfigurationReloading(container);
init_CheckWebLogicWorkaround(container); if (!dispatcherListeners.isEmpty()) {
for (DispatcherListener l : dispatcherListeners) {
l.dispatcherInitialized(this);
}
}
} catch (Exception ex) {
if (LOG.isErrorEnabled())
LOG.error("Dispatcher initialization failed", ex);
throw new StrutsException(ex);
}
} /**
* Load Action class for mapping and invoke the appropriate Action method, or go directly to the Result.
* <p/>
* This method first creates the action context from the given parameters,
* and then loads an <tt>ActionProxy</tt> from the given action name and namespace.
* After that, the Action method is executed and output channels through the response object.
* Actions not found are sent back to the user via the {@link Dispatcher#sendError} method,
* using the 404 return code.
* All other errors are reported by throwing a ServletException.
*
* @param request the HttpServletRequest object
* @param response the HttpServletResponse object
* @param mapping the action mapping object
* @throws ServletException when an unknown error occurs (not a 404, but typically something that
* would end up as a 5xx by the servlet container)
* @param context Our ServletContext object
*/
public void serviceAction(HttpServletRequest request, HttpServletResponse response, ServletContext context,
ActionMapping mapping) throws ServletException { Map<String, Object> extraContext = createContextMap(request, response, mapping, context); // If there was a previous value stack, then create a new copy and pass it in to be used by the new Action
ValueStack stack = (ValueStack) request.getAttribute(ServletActionContext.STRUTS_VALUESTACK_KEY);
boolean nullStack = stack == null;
if (nullStack) {
ActionContext ctx = ActionContext.getContext();
if (ctx != null) {
stack = ctx.getValueStack();
}
}
if (stack != null) {
extraContext.put(ActionContext.VALUE_STACK, valueStackFactory.createValueStack(stack));
} String timerKey = "Handling request from Dispatcher";
try {
UtilTimerStack.push(timerKey);
String namespace = mapping.getNamespace();
String name = mapping.getName();
String method = mapping.getMethod(); Configuration config = configurationManager.getConfiguration();
ActionProxy proxy = config.getContainer().getInstance(ActionProxyFactory.class).createActionProxy(
namespace, name, method, extraContext, true, false); request.setAttribute(ServletActionContext.STRUTS_VALUESTACK_KEY, proxy.getInvocation().getStack()); // if the ActionMapping says to go straight to a result, do it!
if (mapping.getResult() != null) {
Result result = mapping.getResult();
result.execute(proxy.getInvocation());
} else {
proxy.execute();
} // If there was a previous value stack then set it back onto the request
if (!nullStack) {
request.setAttribute(ServletActionContext.STRUTS_VALUESTACK_KEY, stack);
}
} catch (ConfigurationException e) {
// WW-2874 Only log error if in devMode
if(devMode) {
LOG.error("Could not find action or result", e);
}
else {
LOG.warn("Could not find action or result", e);
}
sendError(request, response, context, HttpServletResponse.SC_NOT_FOUND, e);
} catch (Exception e) {
sendError(request, response, context, HttpServletResponse.SC_INTERNAL_SERVER_ERROR, e);
} finally {
UtilTimerStack.pop(timerKey);
}
} /**
* Create a context map containing all the wrapped request objects
*
* @param request The servlet request
* @param response The servlet response
* @param mapping The action mapping
* @param context The servlet context
* @return A map of context objects
*/
public Map<String,Object> createContextMap(HttpServletRequest request, HttpServletResponse response,
ActionMapping mapping, ServletContext context) { // request map wrapping the http request objects
Map requestMap = new RequestMap(request); // parameters map wrapping the http parameters. ActionMapping parameters are now handled and applied separately
Map params = new HashMap(request.getParameterMap()); // session map wrapping the http session
Map session = new SessionMap(request); // application map wrapping the ServletContext
Map application = new ApplicationMap(context); Map<String,Object> extraContext = createContextMap(requestMap, params, session, application, request, response, context); if (mapping != null) {
extraContext.put(ServletActionContext.ACTION_MAPPING, mapping);
}
return extraContext;
} /**
* Merge all application and servlet attributes into a single <tt>HashMap</tt> to represent the entire
* <tt>Action</tt> context.
*
* @param requestMap a Map of all request attributes.
* @param parameterMap a Map of all request parameters.
* @param sessionMap a Map of all session attributes.
* @param applicationMap a Map of all servlet context attributes.
* @param request the HttpServletRequest object.
* @param response the HttpServletResponse object.
* @param servletContext the ServletContextmapping object.
* @return a HashMap representing the <tt>Action</tt> context.
*/
public HashMap<String,Object> createContextMap(Map requestMap,
Map parameterMap,
Map sessionMap,
Map applicationMap,
HttpServletRequest request,
HttpServletResponse response,
ServletContext servletContext) {
HashMap<String,Object> extraContext = new HashMap<String,Object>();
extraContext.put(ActionContext.PARAMETERS, new HashMap(parameterMap));
extraContext.put(ActionContext.SESSION, sessionMap);
extraContext.put(ActionContext.APPLICATION, applicationMap); Locale locale;
if (defaultLocale != null) {
locale = LocalizedTextUtil.localeFromString(defaultLocale, request.getLocale());
} else {
locale = request.getLocale();
} extraContext.put(ActionContext.LOCALE, locale);
//extraContext.put(ActionContext.DEV_MODE, Boolean.valueOf(devMode)); extraContext.put(StrutsStatics.HTTP_REQUEST, request);
extraContext.put(StrutsStatics.HTTP_RESPONSE, response);
extraContext.put(StrutsStatics.SERVLET_CONTEXT, servletContext); // helpers to get access to request/session/application scope
extraContext.put("request", requestMap);
extraContext.put("session", sessionMap);
extraContext.put("application", applicationMap);
extraContext.put("parameters", parameterMap); AttributeMap attrMap = new AttributeMap(extraContext);
extraContext.put("attr", attrMap); return extraContext;
} /**
* Return the path to save uploaded files to (this is configurable).
*
* @return the path to save uploaded files to
* @param servletContext Our ServletContext
*/
private String getSaveDir(ServletContext servletContext) {
String saveDir = multipartSaveDir.trim(); if (saveDir.equals("")) {
File tempdir = (File) servletContext.getAttribute("javax.servlet.context.tempdir");
LOG.info("Unable to find 'struts.multipart.saveDir' property setting. Defaulting to javax.servlet.context.tempdir"); if (tempdir != null) {
saveDir = tempdir.toString();
setMultipartSaveDir(saveDir);
}
} else {
File multipartSaveDir = new File(saveDir); if (!multipartSaveDir.exists()) {
if (multipartSaveDir.mkdir() == false) {
String logMessage;
try {
logMessage = "Could not find create multipart save directory '"+multipartSaveDir.getCanonicalPath()+"'.";
} catch (IOException e) {
logMessage = "Could not find create multipart save directory '"+multipartSaveDir.toString()+"'.";
}
if(devMode) {
LOG.error(logMessage);
}
else {
LOG.warn(logMessage);
}
}
}
} if (LOG.isDebugEnabled()) {
LOG.debug("saveDir=" + saveDir);
} return saveDir;
} /**
* Prepare a request, including setting the encoding and locale.
*
* @param request The request
* @param response The response
*/
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"); // simply read any parameter (existing or not) to "prime" the request
}
} /**
* Wrap and return the given request or return the original request object.
* </p>
* This method transparently handles multipart data as a wrapped class around the given request.
* Override this method to handle multipart requests in a special way or to handle other types of requests.
* Note, {@link org.apache.struts2.dispatcher.multipart.MultiPartRequestWrapper} is
* flexible - look first to that object before overriding this method to handle multipart data.
*
* @param request the HttpServletRequest object.
* @param servletContext Our ServletContext object
* @return a wrapped request or original request.
* @see org.apache.struts2.dispatcher.multipart.MultiPartRequestWrapper
* @throws java.io.IOException on any error.
*/
public HttpServletRequest wrapRequest(HttpServletRequest request, ServletContext servletContext) throws IOException {
// don't wrap more than once
if (request instanceof StrutsRequestWrapper) {
return request;
} String content_type = request.getContentType();
if (content_type != null && content_type.indexOf("multipart/form-data") != -1) {
MultiPartRequest mpr = null;
//check for alternate implementations of MultiPartRequest
Set<String> multiNames = getContainer().getInstanceNames(MultiPartRequest.class);
if (multiNames != null) {
for (String multiName : multiNames) {
if (multiName.equals(multipartHandlerName)) {
mpr = getContainer().getInstance(MultiPartRequest.class, multiName);
}
}
}
if (mpr == null ) {
mpr = getContainer().getInstance(MultiPartRequest.class);
}
request = new MultiPartRequestWrapper(mpr, request, getSaveDir(servletContext));
} else {
request = new StrutsRequestWrapper(request);
} return request;
} /**
* Send an HTTP error response code.
*
* @param request the HttpServletRequest object.
* @param response the HttpServletResponse object.
* @param code the HttpServletResponse error code (see {@link javax.servlet.http.HttpServletResponse} for possible error codes).
* @param e the Exception that is reported.
* @param ctx the ServletContext object.
*/
public void sendError(HttpServletRequest request, HttpServletResponse response,
ServletContext ctx, int code, Exception e) {
if (devMode) {
response.setContentType("text/html"); try {
FreemarkerManager mgr = getContainer().getInstance(FreemarkerManager.class); freemarker.template.Configuration config = mgr.getConfiguration(ctx);
Template template = config.getTemplate("/org/apache/struts2/dispatcher/error.ftl"); List<Throwable> chain = new ArrayList<Throwable>();
Throwable cur = e;
chain.add(cur);
while ((cur = cur.getCause()) != null) {
chain.add(cur);
} HashMap<String,Object> data = new HashMap<String,Object>();
data.put("exception", e);
data.put("unknown", Location.UNKNOWN);
data.put("chain", chain);
data.put("locator", new Locator());
template.process(data, response.getWriter());
response.getWriter().close();
} catch (Exception exp) {
try {
response.sendError(code, "Unable to show problem report: " + exp);
} catch (IOException ex) {
// we're already sending an error, not much else we can do if more stuff breaks
}
}
} else {
try {
// WW-1977: Only put errors in the request when code is a 500 error
if (code == HttpServletResponse.SC_INTERNAL_SERVER_ERROR) {
// send a http error response to use the servlet defined error handler
// make the exception availible to the web.xml defined error page
request.setAttribute("javax.servlet.error.exception", e); // for compatibility
request.setAttribute("javax.servlet.jsp.jspException", e);
} // send the error response
response.sendError(code, e.getMessage());
} catch (IOException e1) {
// we're already sending an error, not much else we can do if more stuff breaks
}
}
} /**
* Provide an accessor class for static XWork utility.
*/
public static class Locator {
public Location getLocation(Object obj) {
Location loc = LocationUtils.getLocation(obj);
if (loc == null) {
return Location.UNKNOWN;
}
return loc;
}
} /**
* Expose the ConfigurationManager instance.
*
* @return The instance
*/
public ConfigurationManager getConfigurationManager() {
return configurationManager;
} /**
* Modify the ConfigurationManager instance
*
* @param mgr The configuration manager
*/
public void setConfigurationManager(ConfigurationManager mgr) {
this.configurationManager = mgr;
} /**
* Expose the dependency injection container.
* @return Our dependency injection container
*/
public Container getContainer() {
ConfigurationManager mgr = getConfigurationManager();
if (mgr == null) {
throw new IllegalStateException("The configuration manager shouldn't be null");
} else {
Configuration config = mgr.getConfiguration();
if (config == null) {
throw new IllegalStateException("Unable to load configuration");
} else {
return config.getContainer();
}
}
}
}
/*
* Copyright (c) 2002-2007 by OpenSymphony
* All rights reserved.
*/
package com.opensymphony.xwork2; import com.opensymphony.xwork2.inject.Container;
import com.opensymphony.xwork2.inject.Inject; import java.util.Map; /**
* Default factory for {@link com.opensymphony.xwork2.ActionProxyFactory}.
*
* @author Jason Carreira
*/
public class DefaultActionProxyFactory implements ActionProxyFactory { protected Container container; public DefaultActionProxyFactory() {
super();
} @Inject
public void setContainer(Container container) {
this.container = container;
} public ActionProxy createActionProxy(String namespace, String actionName, Map<String, Object> extraContext) {
return createActionProxy(namespace, actionName, null, extraContext, true, true);
} public ActionProxy createActionProxy(String namespace, String actionName, String methodName, Map<String, Object> extraContext) {
return createActionProxy(namespace, actionName, methodName, extraContext, true, true);
} public ActionProxy createActionProxy(String namespace, String actionName, Map<String, Object> extraContext, boolean executeResult, boolean cleanupContext) {
return createActionProxy(namespace, actionName, null, extraContext, executeResult, cleanupContext);
} public ActionProxy createActionProxy(String namespace, String actionName, String methodName, Map<String, Object> extraContext, boolean executeResult, boolean cleanupContext) { ActionInvocation inv = new DefaultActionInvocation(extraContext, true);
container.inject(inv);
return createActionProxy(inv, namespace, actionName, methodName, executeResult, cleanupContext);
} public ActionProxy createActionProxy(ActionInvocation inv, String namespace, String actionName, boolean executeResult, boolean cleanupContext) { return createActionProxy(inv, namespace, actionName, null, executeResult, cleanupContext);
} public ActionProxy createActionProxy(ActionInvocation inv, String namespace, String actionName, String methodName, boolean executeResult, boolean cleanupContext) { DefaultActionProxy proxy = new DefaultActionProxy(inv, namespace, actionName, methodName, executeResult, cleanupContext);
container.inject(proxy);
proxy.prepare();
return proxy;
} }
2、struct2的工作流程的更多相关文章
- struts2工作流程
struts2的框架结构图 工作流程 1.客户端请求一个HttpServletRequest的请求,如在浏览器中输入http://localhost: 8080/bookcode/Reg.action ...
- SecondaryNameNode的工作流程
SecondaryNameNode是用来合并fsimage和edits文件来更新NameNode和metadata的. 其工作流程为: 1.secondary通知namenode切换edits文件 2 ...
- Storm 中什么是-acker,acker工作流程介绍
概述 我们知道storm一个很重要的特性是它能够保证你发出的每条消息都会被完整处理, 完整处理的意思是指: 一个tuple被完全处理的意思是: 这个tuple以及由这个tuple所导致的所有的tupl ...
- gitlab工作流程简介
gitlab工作流程简介 新建项目流程 创建/导入项目 可以选择导入github.bitbucket项目,也可以新建空白项目,还可以从SVN导入项目 建议选择private等级 初始化项目 1.本地克 ...
- Git 工作流程
Git 作为一个源码管理系统,不可避免涉及到多人协作. 协作必须有一个规范的工作流程,让大家有效地合作,使得项目井井有条地发展下去.”工作流程”在英语里,叫做”workflow”或者”flow”,原意 ...
- Spark基本工作流程及YARN cluster模式原理(读书笔记)
Spark基本工作流程及YARN cluster模式原理 转载请注明出处:http://www.cnblogs.com/BYRans/ Spark基本工作流程 相关术语解释 Spark应用程序相关的几 ...
- tornado 学习笔记10 Web应用中模板(Template)的工作流程分析
第8,9节中,我们分析Tornado模板系统的语法.使用以及源代码中涉及到的相关类,而且对相关的源代码进行了分析.那么,在一个真正的Web应用程序中,模板到底是怎样使用?怎样被渲染? ...
- RDIFramework.NET ━ .NET快速信息化系统开发框架 ━ 工作流程组件介绍
RDIFramework.NET ━ .NET快速信息化系统开发框架 工作流程组件介绍 RDIFramework.NET,基于.NET的快速信息化系统开发.整合框架,给用户和开发者最佳的.Net框架部 ...
- NSURLSession使用说明及后台工作流程分析
原文摘自http://www.cocoachina.com/industry/20131106/7304.html NSURLSession是iOS7中新的网络接口,它与咱们熟悉的NSURLConne ...
随机推荐
- R语言入门二
一.R语言应知常用函数 1.getwd() 函数:获取工作目录(同eclipse设置workspace类似),直接在R软件中使用,如下图: 2.setwd(dir=”工作目录”) 函数:设置R软件RS ...
- sqlmap tamper脚本备忘录与tamper脚本编写
查看sqlmap全部脚本 $ python sqlmap.py --list-tampers 使用方法 --tamper=TAMPER 2019.9更新后翻译 * apostrophemask.py- ...
- 关于ubuntu下使用l2tpvpn和远程桌面windows系统的测试
一.背景: 2019年9月下旬到10月上旬,到海南澄迈福山度假.随身带的笔记本电脑中windows10系统因硬盘故障挂了,在另一块硬盘上的ubuntu18.04系统正常.因媳妇需要在10月1日远程回公 ...
- Rocket - util - IDPool
https://mp.weixin.qq.com/s/Pe7FGKzfRufzzYDrl0fQ7g 介绍IDPool的实现. 1. 基本介绍 实现从ID池中分配和释放ID的功能. ...
- 【HBase】安装与使用
下载HBase(注意下载与您使用的hadoop版本兼容的版本) 前提:hadoop HA,zookeeper是正常的. 1.解压 tar -zxvf hbase压缩包 -C 解压后存储路径 2.配置环 ...
- vue-组件化-插槽(slot)
理解 Vue组件化中,当我们在设计一个组件的时候,可能会保留一部分,让使用者自定义的内容,比如: 导航栏组件中,右上角的分享按钮,左上角做菜单按钮 弹出框组件中,弹出框的提示内容等 ... 在这种场景 ...
- Spring Boot笔记(二) springboot 集成 SMTP 发送邮件
个人博客网:https://wushaopei.github.io/ (你想要这里多有) 笔记:乘着项目迭代的间隙,把一些可复用的功能从项目中抽取出来,这是其中之一, 一.添加SMTP 及 MA ...
- (Java实现) 洛谷 P1025 数的划分
题目描述 将整数n分成k份,且每份不能为空,任意两个方案不相同(不考虑顺序). 例如:n=7,k=3,下面三种分法被认为是相同的. 1,1,5; 1,5,1; 5,1,1. 问有多少种不同的分法. 输 ...
- Java 第十一届 蓝桥杯 省模拟赛 户户通电(图算法)
户户通电 题目 问题描述 2015年,全中国实现了户户通电.作为一名电力建设者,小明正在帮助一带一路上的国家通电. 这一次,小明要帮助 n 个村庄通电,其中 1 号村庄正好可以建立一个发电站,所发的电 ...
- Java实现 蓝桥杯 算法训练 2的次幂表示
算法训练 2的次幂表示 时间限制:1.0s 内存限制:512.0MB 问题描述 任何一个正整数都可以用2进制表示,例如:137的2进制表示为10001001. 将这种2进制表示写成2的次幂的和的形式, ...