struts-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From lukaszlen...@apache.org
Subject [2/9] struts-site git commit: Converts Core Developers guide into MD
Date Mon, 12 Jun 2017 19:03:28 GMT
http://git-wip-us.apache.org/repos/asf/struts-site/blob/f903a0f7/source/core-developers/websphere.md
----------------------------------------------------------------------
diff --git a/source/core-developers/websphere.md b/source/core-developers/websphere.md
new file mode 100644
index 0000000..0933ea8
--- /dev/null
+++ b/source/core-developers/websphere.md
@@ -0,0 +1,205 @@
+---
+layout: core-developers
+title: WebSphere
+---
+
+# WebSphere
+
+#####WebSphere 5\.1#####
+
+ (ok) [Be sure to install WebSphere's Fix Pack 1](http://forums\.opensymphony\.com/thread\.jspa?threadID=26068)^[http://forums\.opensymphony\.com/thread\.jspa?threadID=26068]\.
+
+#####WebSphere 6#####
+
+See forum thread: [http://forums\.opensymphony\.com/message\.jspa?messageID=119574\#119574](http://forums\.opensymphony\.com/message\.jspa?messageID=119574\#119574)
+
+
+> 
+
+> 
+
+> It looks like there is a bug in WebSphere App Server related to which classloader is
used at the time that Struts2 is loading the properties files, (all properties files, not
just struts\.properties and default\.properties)\. The bug may have been fixed in WAS 6\.0\.2\.9,
(check out this link for details [http://www\-1\.ibm\.com/support/docview\.wss?uid=swg27006876](http://www\-1\.ibm\.com/support/docview\.wss?uid=swg27006876))\.
+
+> 
+
+> 
+
+> If you just want to confirm the issue, or you need just a temporary fix, try this:
+
+> 
+
+> 
+
+> 1) jar up all properties files for your project, (including default\.properties in its
full path), and put these into the WS common applications lib directory at the same level
as the "profiles" directory\.
+
+> 
+ > 2) Run the application \- everything should work
+
+> 
+
+> 
+
+> This solution is strictly temporary, as all struts2 apps in this instance of WAS would
have to use the same properties files\. A better solution:
+
+> 
+
+> 
+
+> 1) add a servlet that initializes the Struts Dispatcher with the servlet context:
+
+> 
+ > import org\.apache\.struts2\.dispatcher\.Dispatcher;
+ >  
+ > public class LaunchServlet extends HttpServlet implements Servlet \{
+ >  
+ > 	public LaunchServlet() \{
+ > 		super();
+ > 	\}
+ >  
+ > 	public void init(ServletConfig arg0) throws ServletException \{
+ > 		
+ > 		// this works around a bug in the websphere classloader\.
+ > 		super\.init(arg0);
+ > 		Dispatcher d = new Dispatcher(getServletContext(), new HashMap\<String, String\>());

+ > 		
+ > 	\}
+ >  
+ > \}
+ > 
+
+> 2) launch it at start\-up (web\.xml):
+
+> 
+ >     \<servlet\>
+ >       \<servlet\-name\>dummyaction\</servlet\-name\>
+ >       \<servlet\-class\>com\.xxx\.yyyyyy\.service\.LaunchServlet\</servlet\-class\>
+ >       \<load\-on\-startup\>1\</load\-on\-startup\>
+ >     \</servlet\>
+ > 
+
+> 3) Run application and everything should work\. 
+
+> 
+
+#####WebSphere 6\.5#####
+
+To make struts2 work in Websphere, one has to set Websphere specific properties, you may
want to add that to the wiki:
+
+The properties are:
+
+
+~~~~~~~
+
+com.ibm.ws.webcontainer.assumefiltersuccessonsecurityerror = true
+com.ibm.ws.webcontainer.invokefilterscompatibility = true
+
+~~~~~~~
+
+At least that is necessary when using StrutsPrepareAndExecuteFilter\.
+
+In Websphre admin console one has to add those properties here:
+
+
+~~~~~~~
+
+Servers > Application servers > {server name} > Web container > Custom Properties
+
+~~~~~~~
+
+A wsadmin jython script to set those properties could look like this:
+
+
+~~~~~~~
+
+
+def findObjectName(objectId):
+        index = objectId.find('(')
+        return objectId[0 : index]
+
+node = AdminNodeManagement.listNodes()[0]
+server = AdminConfig.list('Server')
+
+nodeName = findObjectName(node)
+serverName = findObjectName(server)
+
+webContainer = AdminConfig.list('WebContainer', node)
+webContainerDetails = AdminConfig.show(webContainer)
+
+if webContainerDetails.find("com.ibm.ws.webcontainer.assumefiltersuccessonsecurityerror")
== -1:
+        print "creating prop: com.ibm.ws.webcontainer.assumefiltersuccessonsecurityerror"
+        AdminServerManagement.configureCustomProperty(nodeName, serverName, "WebContainer","com.ibm.ws.webcontainer.assumefiltersuccessonsecurityerror",
"true")
+if webContainerDetails.find("com.ibm.ws.webcontainer.invokefilterscompatibility") == -1:
+        print "creating prop: com.ibm.ws.webcontainer.invokefilterscompatibility"
+        AdminServerManagement.configureCustomProperty(nodeName, serverName, "WebContainer",
"com.ibm.ws.webcontainer.invokefilterscompatibility", "true")
+
+~~~~~~~
+
+Thanks to Christoph Nenning (christoph dot nenning at lex\-com at net)
+
+#####JSESSIONID handling#####
+
+IBM WebSphere Application Server uses the JSESSIONID information to keep track of the client
session\. If you have an application where the application client must navigate across multiple
WebSphere Application Server nodes residing in same domain, then the JSESSIONID information
may be over\-written on the client because multiple JSESSIONID cookies received with the same
name and path\.
+
+When persistence is disabled and if the JSESSIONID in the incoming request is not found in
the current session manager, then the session manager will generate a new sessionId and create
a session object, instead of using the sessionId in the incoming request\.
+
+To resolve this issue, configure WebSphere Application Server to reuse the sessionId present
in the incoming request\.
+
+For All versions:
+
+1. Open the administrative console.
+
+2. Select Servers > Application Servers > Server_Name > Server Infrastructure >
Java and Process Management > Process Definition > Java Virtual Machine > Custom
Properties > New
+
+3. Add a new Custom Property for the JVM to reuse the sessionId:
+
+
+~~~~~~~
+
+System Property Name: HttpSessionIdReuse
+System Property Value: true
+
+~~~~~~~
+
+4. Save your changes and restart the Application Server.
+
+If the application client does not navigate across multiple WebSphere Application Server
nodes residing in the same domain but there are multiple WARs with different context roots,
following is the step that needs to be followed for session to be maintained in one web application:
+
+1. Open the administrative console.
+
+2. Select Application servers > Server_Name > Session management > Cookies
+
+3. In "Cookie Path", specify the context root of web application in which session needs to
be maintained. This will ensure that cookies are sent only to /<<context_root>>
URL and prevent overriding of JSSESSIONID cookie which results in new session creation by
WAS.
+
+4. Save your changes and restart the Application Server.
+
+Thanks to Vineet Kanwal from IBM\!
+
+##Big Picture## {#PAGE_13859}
+
+The diagram describes the framework's architecture\.
+
+![Struts2\-Architecture\.png](/Users/lukaszlenart/Projects/Apache/struts\-site/target/md/attachments/att2475\_Struts2\-Architecture\.png)
+
+In the diagram, an initial request goes to the Servlet container (such as Jetty or Resin)
which is passed through a standard filter chain\. The chain includes the (optional) **ActionContextCleanUp**
filter, which is useful when integrating technologies such as _SiteMesh Plugin_ \. Next, the
required **FilterDispatcher** is called, which in turn consults the [ActionMapper](#PAGE_14128)
to determine if the request should invoke an action\.
+
+If the ActionMapper determines that an Action should be invoked, the FilterDispatcher delegates
control to the **ActionProxy**\. The ActionProxy consults the framework [Configuration Files](#PAGE_14163)
manager (initialized from the [struts\.xml](#PAGE_13901) file)\. Next, the ActionProxy creates
an **ActionInvocation**, which is responsible for the command pattern implementation\. This
includes invoking any **Interceptors** (the _before_  clause) in advance of invoking the **Action**
itself\.
+
+Once the Action returns, the ActionInvocation is responsible for looking up the proper **result**
associated with the **Action result code** mapped in 
+
+~~~~~~~
+struts.xml
+~~~~~~~
+\. The result is then executed, which often (but not always, as is the case for [Action Chaining](#PAGE_14214))
involves a template written in _JSP_  or _FreeMarker_  to be rendered\. While rendering, the
templates can use the _Struts Tags_  provided by the framework\. Some of those components
will work with the ActionMapper to render proper URLs for additional requests\.
+
+
+
+| All objects in this architecture (Actions, [Results](#PAGE_14035), [Interceptors](#PAGE_13941),
and so forth) are created by an [ObjectFactory](#PAGE_27470)\. This ObjectFactory is pluggable\.
We can provide our own ObjectFactory for any reason that requires knowing when objects in
the framework are created\. A popular ObjectFactory implementation uses Spring as provided
by the _Spring Plugin_ \.
+
+| 
+
+Interceptors are executed again (in reverse order, calling the _after_  clause)\. Finally,
the response returns through the filters configured in the 
+
+~~~~~~~
+web.xml
+~~~~~~~
+\. If the ActionContextCleanUp filter is present, the FilterDispatcher will _not_  clean
up the ThreadLocal **ActionContext**\. If the ActionContextCleanUp filter is not present,
the FilterDispatcher will cleanup all ThreadLocals\.

http://git-wip-us.apache.org/repos/asf/struts-site/blob/f903a0f7/source/core-developers/wildcard-mappings.md
----------------------------------------------------------------------
diff --git a/source/core-developers/wildcard-mappings.md b/source/core-developers/wildcard-mappings.md
new file mode 100644
index 0000000..bdfd7c9
--- /dev/null
+++ b/source/core-developers/wildcard-mappings.md
@@ -0,0 +1,236 @@
+---
+layout: core-developers
+title: Wildcard Mappings
+---
+
+# Wildcard Mappings
+
+#####Wildcards#####
+
+As an application grows in size, so will the number of action mappings\. Wildcards can be
used to combine similar mappings into one more generic mapping\.
+
+The best way to explain wildcards is to show an example and walk through how it works\. This
example modifies a conventional mapping to use wildcards to match all pages that start with
/edit:
+
+
+~~~~~~~
+
+<action name="/edit*" class="org.apache.struts.webapp.example.Edit{1}Action">
+    <result name="failure">/mainMenu.jsp</result>
+    <result>{1}.jsp</result>
+</action>
+
+~~~~~~~
+
+The "\*" in the name attribute allows the mapping to match the request URIs /editSubscription,
editRegistration, or any other URI that starts with /edit, however /editSubscription/add would
not be matched\. The part of the URI matched by the wildcard will then be substituted into
various attributes of the action mapping and its action results replacing \{1\}\. For the
rest of the request, the framework will see the action mapping and its action results containing
the new values\.
+
+Mappings are matched against the request in the order they appear in the framework's configuration
file\. If more than one pattern matches **the last one wins**, so less specific patterns must
appear before more specific ones\. However, if the request URL can be matched against a path
without any wildcards in it, no wildcard matching is performed and order is not important\.
Also, note that wildcards are not greedy, meaning they only match until the first occurrence
of the following string pattern\.  For example, consider the following mapping:
+
+
+~~~~~~~
+
+<action name="List*s" class="actions.List{1}s">
+  <result>list{1}s.jsp</result>
+</action>
+
+~~~~~~~
+
+This mapping would work correctly for the URI 
+
+~~~~~~~
+ListAccounts
+~~~~~~~
+ but not 
+
+~~~~~~~
+ListSponsors
+~~~~~~~
+, because the latter would turn into this configuration:
+
+
+~~~~~~~
+
+<action name="ListSpons" class="actions.ListSpons">
+  <result>listSpons.jsp</result>
+</action>
+
+~~~~~~~
+
+Wildcard patterns can contain one or more of the following special tokens:
+
+|\*|Matches zero or more characters excluding the slash ('/') character\.|
+|--|---------------------------------------------------------------------|
+|\*\*|Matches zero or more characters including the slash ('/') character\.|
+|\\character|The backslash character is used as an escape sequence\. Thus \
+'\\\*' matches the character asterisk ('\*'), and \
+'\\\\' matches the character backslash ('\\')\.|
+
+
+Patterns can optionally be matched "loosely"\. When the end of the pattern matches \*\[^\*\]\*\$
(wildcard, no wildcard, wildcard), if the pattern fails, it is also matched as if the last
two characters didn't exist\. The goal is to support the legacy "\*\!\*" syntax, where the
"\!\*" is optional\.
+
+| 
+
+In the action mapping and action results, the wildcard\-matched values can be accessed with
the token \{N\} where N is a number from 1 to 9 indicating which wildcard\-matched value to
substitute\. The whole request URI can be accessed with the \{0\} token\.
+
+Also, the action mapping and action result properties will accept wildcard\-matched strings
in their value attribute, like:
+
+
+~~~~~~~
+
+<action name="/edit/*" class="org.apache.struts.webapp.example.Edit{1}Action">
+    <param name="id">{1}</param>
+    <result>
+      <param name="location">/mainMenu.jsp</param>
+      <param name="id">{1}</param> 
+    </result>
+</action>
+
+~~~~~~~
+
+(light\-on) See also [Wildcard Method](#PAGE_14122)
+
+#####Parameters in namespaces#####
+
+From Struts 2\.1\+ namespace patterns can be extracted as request parameters and bound to
the action\. To enable this feature, set the following constant in struts\.xml:
+
+
+~~~~~~~
+
+<constant name="struts.patternMatcher" value="namedVariable"/>
+
+~~~~~~~
+
+With that in place, namespace definitions can contain \{PARAM\_NAME\} patterns which will
be evaluated against the request URL and extracted as parameters, for example:
+
+
+~~~~~~~
+
+@Namespace{"/users/{userID}");
+public class DetailsAction exends ActionSupport {
+  private Long userID;
+  public void setUserID(Long userID) {...}
+}
+
+~~~~~~~
+
+If the request URL is _/users/10/detail_ , then the DetailsAction will be executed and its
userID field will be set to _10_ \. 
+
+
+> 
+
+> 
+
+> Only one PatternMatcher implementation can be used at a time\.  The two implementations
included with Struts 2 are mutually exclusive\.  You cannot use Wildcards and Named Variable
patterns at the same application (if that were required, you'd need to create a custom PatternMatcher
implementation)\.
+
+> 
+
+> 
+
+> Some tags tags not are 100% compatible with variables in the namespace\. For instance,
they may write the literal namespace into the HTML (eg /\{user\}/2w) instead of the path used
in the request (ie\. /brett/24)\.  This usually affects attributes that attempt to guess the
namespace of an action (eg\. Form tag, Action tag, action=)\. This problem can be avoided
by using HTML tags directly with relative paths or explicit URLs\.
+
+> 
+
+
+| 
+
+| Similar functionality can also be implemented using a custom ActionMapper\.  The ActionMapper
will need to parse the namespace and request itself to set parameters on the matched action\.
 The default ActonMapper is responsible for invoking the PatternMatcher\.
+
+| 
+
+#####Parameters after the action name#####
+
+To use parameters in the URL, after the action name, make sure this is set:
+
+
+~~~~~~~
+
+<constant name="struts.enable.SlashesInActionNames" value="true"/>
+<constant name="struts.mapper.alwaysSelectFullNamespace" value="false"/>
+
+~~~~~~~
+
+Then the action mapping will look like:
+
+
+~~~~~~~
+
+<package name="edit" extends="struts-default" namespace="/edit">
+    <action name="/person/*" class="org.apache.struts.webapp.example.EditAction">
+        <param name="id">{1}</param>
+        <result>/mainMenu.jsp</result>
+    </action>   
+</package>
+
+~~~~~~~
+
+When a URL like 
+
+~~~~~~~
+/edit/person/123
+~~~~~~~
+ is requested, EditAction will be called, and its "id" field will be set to 123\. 
+
+#####Advanced Wildcards#####
+
+From 2\.1\.9\+ regular expressions can be defined defined in the action name\. To use this
form of wild card, the following constants must be set:
+
+
+~~~~~~~
+
+<constant name="struts.enable.SlashesInActionNames" value="true"/>
+<constant name="struts.mapper.alwaysSelectFullNamespace" value="false"/>
+<constant name="struts.patternMatcher" value="regex" />
+
+~~~~~~~
+
+The regular expressions can be in two forms, the simplest one is \{FIELD\_NAME\}, in which
case the field with the FIELD\_NAME in the action will be populated with the matched text,
for example:
+
+
+~~~~~~~
+
+<package name="books" extends="struts-default" namespace="/">
+    <action name="/{type}/content/{title}" class="example.BookAction">
+	<result>/books/content.jsp</result>
+    </action>
+</package>
+
+~~~~~~~
+
+In this example, if the url 
+
+~~~~~~~
+/fiction/content/Frankenstein
+~~~~~~~
+ is requested, BookAction's field "type" will be set to "fiction", and the field "title"
will be set to "Frankenstein"\. 
+
+The regular expression can also be in the form \{FIELD\_NAME:REGULAR\_EXPRESSION\}\. The
regular expression is a normal Java regular expression\. For example:
+
+
+~~~~~~~
+
+<package name="books" extends="struts-default" namespace="/">
+    <action name="/{type}/{author:.+}/list" class="example.ListBooksAction">
+	<result>/books/list.jsp</result>
+    </action>
+</package>
+
+~~~~~~~
+
+In this example, if the url 
+
+~~~~~~~
+/philosophy/AynRand/list
+~~~~~~~
+ is requested, ListBooksAction's field "type" will be set to "philosophy" and "author" to
"AynRand"\. 
+
+The matched groups can still be accessed using the \{X\} notation, like:
+
+
+~~~~~~~
+
+<package name="books" extends="struts-default" namespace="/">
+    <action name="/books/{ISBN}/content" class="example.BookAction">
+	<result>/books/{1}.jsp</result>
+    </action>
+</package>
+
+~~~~~~~
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/struts-site/blob/f903a0f7/source/core-developers/writing-interceptors.md
----------------------------------------------------------------------
diff --git a/source/core-developers/writing-interceptors.md b/source/core-developers/writing-interceptors.md
new file mode 100644
index 0000000..09154bf
--- /dev/null
+++ b/source/core-developers/writing-interceptors.md
@@ -0,0 +1,102 @@
+---
+layout: core-developers
+title: Writing Interceptors
+---
+
+# Writing Interceptors
+
+See the [Interceptors](interceptors.html) page for an overview of how interceptors work\.
+
+__Interceptor interface__
+
+Interceptors must implement the com\.opensymphony\.xwork2\.interceptor\.Interceptor interface\.
+
+**Interceptor\.java**
+
+
+~~~~~~~
+
+public interface Interceptor extends Serializable {
+
+    void destroy();
+
+    void init();
+
+    String intercept(ActionInvocation invocation) throws Exception;
+}
+
+~~~~~~~
+
+The _init_  method is called the after interceptor is instantiated and before calling _intercept_
\. This is the place to allocate any resources used by the interceptor\.
+
+The _intercept_  method is where the interceptor code is written\. Just like an action method,
_intercept_  returns a result used by Struts to forward the request to another web resource\.
Calling _invoke_  on the parameter of type ActionInvocation will execute the action (if this
is the last interceptor on the stack) or another interceptor\.
+
+
+
+| Keep in mind that _invoke_  will return **after** the result has been called (eg\. after
you JSP has been rendered), making it perfect for things like open\-session\-in\-view patterns\.
If you want to do something before the result gets called, you should implement a PreResultListener\.
+
+| 
+
+Overwrite _destroy_  to release resources on application shutdown\.
+
+__Thread Safety__
+
+**Interceptors must be thread\-safe\!**
+
+> 
+
+> 
+
+> A Struts 2 Action instance is created for every request and do not need to be thread\-safe\.
Conversely, Interceptors are shared between requests and must be [thread\-safe](http://en\.wikipedia\.org/wiki/Thread\-safety)^[http://en\.wikipedia\.org/wiki/Thread\-safety]\.

+
+> 
+
+__AbstractInterceptor__
+
+The AbstractInterceptor class provides an empty implementation of _init_  and _destroy_ ,
and can be used if these methods are not going to be implemented\.
+
+__Mapping__
+
+Interceptors are declared using the _interceptor_  element, nested inside the _interceptors_
 element\. Example from struts\-default\.xml:
+
+
+~~~~~~~
+
+<struts>
+   ...
+
+   <package name="struts-default">
+      <interceptors>
+         <interceptor name="alias" class="com.opensymphony.xwork2.interceptor.AliasInterceptor"/>
+         <interceptor name="autowiring" class="com.opensymphony.xwork2.spring.interceptor.ActionAutowiringInterceptor"/>
+         ...
+      </interceptors>
+   </package>
+
+   ...
+</struts>
+
+~~~~~~~
+
+__Example__
+
+Assuming there is an action of type "MyAction", with a setDate(Date) method, this simple
interceptor will set the date of the action to the current date:
+
+**Interceptor Example**
+
+
+~~~~~~~
+
+import com.opensymphony.xwork2.ActionInvocation;
+import com.opensymphony.xwork2.interceptor.AbstractInterceptor;
+
+public class SimpleInterceptor extends AbstractInterceptor {
+
+    public String intercept(ActionInvocation invocation) throws Exception {
+       MyAction action = (MyAction)invocation.getAction();
+       action.setDate(new Date());
+       return invocation.invoke();
+    }
+}
+
+~~~~~~~

http://git-wip-us.apache.org/repos/asf/struts-site/blob/f903a0f7/source/core-developers/xsl-result.md
----------------------------------------------------------------------
diff --git a/source/core-developers/xsl-result.md b/source/core-developers/xsl-result.md
new file mode 100644
index 0000000..e6798f8
--- /dev/null
+++ b/source/core-developers/xsl-result.md
@@ -0,0 +1,168 @@
+---
+layout: core-developers
+title: XSL Result
+---
+
+# XSL Result
+
+
+####Description####
+
+XSLTResult uses XSLT to transform an action object to XML\. The recent version has been specifically
modified to deal with Xalan flaws\. When using Xalan you may notice that even though you have
a very minimal stylesheet like this one
+
+
+~~~~~~~
+<xsl:template match="/result">
+<result/>
+</xsl:template>
+~~~~~~~
+
+Xalan would still iterate through every property of your action and all its descendants\.
+
+If you had double\-linked objects, Xalan would work forever analysing an infinite object
tree\. Even if your stylesheet was not constructed to process them all\. It's because the
current Xalan eagerly and extensively converts
+everything to its internal DTM model before further processing\.
+
+That's why there's a loop eliminator added that works by indexing every object\-property
combination during processing\. If it notices that some object's property was already walked
through, it doesn't go any deeper\. Say you have two objects, x and y, with the following
properties set (pseudocode):
+
+
+~~~~~~~
+x.y = y;
+and
+y.x = x;
+action.x=x;
+~~~~~~~
+
+Due to that modification, the resulting XML document based on x would be:
+
+
+~~~~~~~
+<result>
+<x>
+<y/>
+</x>
+</result>
+~~~~~~~
+
+Without it there would be endless 
+
+~~~~~~~
+x/y/x/y/x/y/...
+~~~~~~~
+ elements\.
+
+The 
+
+~~~~~~~
+XSLTResult
+~~~~~~~
+ code tries also to deal with the fact that DTM model is built in a manner that children
are processed before siblings\. The result is that if there is object x that is both set in
action's x property, and very deeply under action's a property then it would only appear under
a, not under x\. That's not what we expect, and that's why 
+
+~~~~~~~
+XSLTResult
+~~~~~~~
+ allows objects to repeat in various places to some extent\.
+
+Sometimes the object mesh is still very dense and you may notice that even though you have
a relatively simple stylesheet, execution takes a tremendous amount of time\. To help you
to deal with that obstacle of Xalan, you may attach regexp filters to elements paths (xpath)\.
+
+
+
+| In your \.xsl file the root match must be named **result**\. This example will output the
username by using **getUsername** on your action class:
+
+| \<xsl:template match="result"\>
+ \<html\>
+ \<body\>
+   Hello \<xsl:value\-of select="username"/\> how are you?
+ \</body\>
+ \</html\>
+ \</xsl:template\>
+
+In the following example the XSLT result would only walk through action's properties without
their childs\. It would also skip every property that has 
+
+~~~~~~~
+hugeCollection
+~~~~~~~
+ in their name\. Element's path is first compared to 
+
+~~~~~~~
+excludingPattern
+~~~~~~~
+ \- if it matches it's no longer processed\. Then it is compared to 
+
+~~~~~~~
+matchingPattern
+~~~~~~~
+ and processed only if there's a match\.
+
+
+~~~~~~~
+<result name="success" type="xslt">
+  <param name="stylesheetLocation">foo.xslt</param>
+  <param name="matchingPattern">^/result/[^/*]$</param>
+  <param name="excludingPattern">.*(hugeCollection).*</param>
+</result>
+~~~~~~~
+
+In the following example the XSLT result would use the action's user property instead of
the action as it's base document and walk through it's properties\. The 
+
+~~~~~~~
+exposedValue
+~~~~~~~
+ uses an OGNL expression to derive it's value\.
+
+
+~~~~~~~
+<result name="success" type="xslt">
+  <param name="stylesheetLocation">foo.xslt</param>
+  <param name="exposedValue">${user}</param>
+</result>
+~~~~~~~
+
+####Parameters####
+
+This result type takes the following parameters:
+
++ **stylesheetLocation** (default) \- the location to go to after execution\.
+
++ **location** (deprecated) \- the same as **stylesheetLocation** but it was dropped since
Struts 2\.5\.
+
++ **encoding **\- character encoding used in XML, default UTF\-8\.
+
++ **parse** \- 
+
+~~~~~~~
+true
+~~~~~~~
+ by default\. If set to false, the location param will not be parsed for Ognl expressions\.
+
++ **matchingPattern **\- 
+
+~~~~~~~
+Pattern
+~~~~~~~
+ that matches only desired elements, by default it matches everything\.
+
++ **excludingPattern** \- 
+
+~~~~~~~
+Pattern
+~~~~~~~
+ that eliminates unwanted elements, by default it matches none\.
+
+
+
+~~~~~~~
+struts.properties
+~~~~~~~
+ related configuration:
+
++ **struts\.xslt\.nocache** \- Defaults to false\. If set to true, disables stylesheet caching\.
Good for development, bad for production\.
+
+####Examples####
+
+
+
+~~~~~~~
+<result name="success" type="xslt">foo.xslt</result>
+~~~~~~~
+
+ 
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/struts-site/blob/f903a0f7/source/core-developers/zero-configuration.md
----------------------------------------------------------------------
diff --git a/source/core-developers/zero-configuration.md b/source/core-developers/zero-configuration.md
new file mode 100644
index 0000000..b3fe406
--- /dev/null
+++ b/source/core-developers/zero-configuration.md
@@ -0,0 +1,119 @@
+---
+layout: core-developers
+title: Zero Configuration
+---
+
+# Zero Configuration
+
+**(\!) Deprecated Plugin**
+
+
+> 
+
+> 
+
+> Since 2\.1 this plugin has been deprecated in favor of the _Convention Plugin_ 
+
+> 
+
+A "Zero Configuration" Struts application or plugin uses no additional XML or properties
files\. Metadata is expressed through convention and annotation\.  
+
+As this is a new feature, and still being field\-tested, the documentation is sketchy\. But,
here's what we have so far:
+
+#####Finding Actions#####
+
+Set the "actionPackages" filter init param to a comma\-separated list of packages containing
Action classes in web\.xml\. The packages and their subpackages will be scanned\. All classes
in the designated packages that implement Action or end in "Action" are examined\.  The latter
is to allow for POJO Actions that don't implement the Action interface\.
+
+**Annotation Initialization actionPackages Filter Parameter in web\.xml**
+
+
+~~~~~~~
+
+<filter>
+  <filter-name>struts2</filter-name>
+  <filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
+  <init-param>
+    <param-name>actionPackages</param-name>
+    <param-value>com.foo.bar,com.baz.quux</param-value>
+  </init-param>
+</filter>
+
+~~~~~~~
+
+We should probably add an action annotation, so that POJOs can itall with annotations\.
+
+#####Examples#####
+
+The only example right now is in the showcase, where the person package uses the classpath
scanning configuration\. 
+
+#####Action and Package name#####
+
+The subpackage name makes the namespace, and the action class name makes the action name\.
 If there is an "Action" suffix, it is dropped before creating the action name\. Therefore,
if the configured package is _com\.myapp\.actions_  and the Action is _com\.myapp\.actions\._
**member**\.EditAction, you can access it via [http://server/myapp/member/edit\.action](http://server/myapp/member/edit\.action)\.
 For multi\-word actions, the first letter is lower\-cased and the rest is left alone, so
the Action 
+
+~~~~~~~
+MyCustomAction
+~~~~~~~
+ will map to 
+
+~~~~~~~
+myCustom.action
+~~~~~~~
+\.
+
+#####Results#####
+
+[Results](#PAGE_43811) are defined with the Result and Results annotations at the **class
level**\. 
+
+#####Namespaces#####
+
+The [Namespace Annotation](#PAGE_68488) overrides the namespace\.
+
+#####Parent Package#####
+
+The [ParentPackage Annotation](#PAGE_68490) configures the XWork package (an XWork package
is created per Java package) to extend one or more defined packages\. The best place for this
annotation is on the package via the 
+
+~~~~~~~
+package-info.java
+~~~~~~~
+ file, however, for backward\-compatibility, they can be specified on one or more Actions
in the package\.  To determine which parent packages should be set, first, it looks for the
package annotation, then adds the action annotations as they are loaded\.  Because the load
order of Actions is undetermined, it is highly recommended you avoid putting the @ParentPackage
annotation on Action classes themselves\.
+
+For example, if you wanted to set the parent package for the 
+
+~~~~~~~
+com.mycompany.myapp.actions
+~~~~~~~
+ package, create this package\-info\.java file:
+
+
+~~~~~~~
+
+@ParentPackage("my-parent-package")
+package com.mycompany.myapp.actions
+
+import org.apache.struts2.config.ParentPackage;
+
+~~~~~~~
+
+To define multiple parent packages, list an array of package names:
+
+
+~~~~~~~
+
+@ParentPackage({"my-parent-package1, my-parent-package2"})
+package com.mycompany.myapp.actions
+
+import org.apache.struts2.config.ParentPackage;
+
+~~~~~~~
+
+#####Feedback#####
+
+Stay tuned to this page for additional details and documentation\. If you have a chance to
 try the zero configuration feature, please share any experiences on dev@ and here\.
+
+#####See also#####
+
++ _Zero Configuration Scanning_  Use Case
+
++ _Codebehind Plugin_ 
+
++ _RESTfulActionMapper_ 

http://git-wip-us.apache.org/repos/asf/struts-site/blob/f903a0f7/source/security/index.md
----------------------------------------------------------------------
diff --git a/source/security/index.md b/source/security/index.md
new file mode 100644
index 0000000..3d52c6c
--- /dev/null
+++ b/source/security/index.md
@@ -0,0 +1,344 @@
+---
+layout: default
+title: Security (WIP)
+---
+
+# Security
+
+
+#####Security tips#####
+
+The Apache Struts 2 doesn't provide any security mechanism \- it is just a pure web framework\.
Below are few tips you should consider during application development with the Apache Struts
2\.
+
+__Restrict access to the Config Browser__
+
+_Config Browser Plugin_  exposes internal configuration and should be used only during development
phase\. If you must use it on production site, we strictly recommend restricting access to
it \- you can use  Basic Authentication or any other security mechanism (e\.g\. [Apache Shiro](http://shiro\.apache\.org/)^[http://shiro\.apache\.org/])
+
+__Don't mix different access levels in the same namespace__
+
+Very often access to different resources is controlled based on URL patterns, see snippet
below\. Because of that you cannot mix actions with different security levels in the same
namespace\. Always group actions in one namespace by security level\.
+
+
+~~~~~~~
+    <security-constraint>
+        <web-resource-collection>
+            <web-resource-name>admin</web-resource-name>
+            <url-pattern>/secure/*</url-pattern>
+        </web-resource-collection>
+        <auth-constraint>
+            <role-name>admin</role-name>
+        </auth-constraint>
+    </security-constraint>
+
+~~~~~~~
+
+__Never expose JSP files directly__
+
+You must always hide JSP file behind an action, you cannot allow for direct access to the
JSP files as this can leads to unpredictable security vulnerabilities\. You can achieve this
by putting all your JSP files under the 
+
+~~~~~~~
+WEB-INF
+~~~~~~~
+ folder \- most of the JEE containers restrict access to files placed under the 
+
+~~~~~~~
+WEB-INF
+~~~~~~~
+ folder\. Second option is to add security constraint to the 
+
+~~~~~~~
+web.xml
+~~~~~~~
+ file:
+
+
+~~~~~~~
+<!-- Restricts access to pure JSP files - access available only via Struts action -->
+<security-constraint>
+    <display-name>No direct JSP access</display-name>
+    <web-resource-collection>
+        <web-resource-name>No-JSP</web-resource-name>
+        <url-pattern>*.jsp</url-pattern>
+    </web-resource-collection>
+    <auth-constraint>
+        <role-name>no-users</role-name>
+    </auth-constraint>
+</security-constraint>
+
+<security-role>
+    <description>Don't assign users to this role</description>
+    <role-name>no-users</role-name>
+</security-role>
+~~~~~~~
+
+The best approach is to used the both solutions\.
+
+__Disable devMode__
+
+The 
+
+~~~~~~~
+devMode
+~~~~~~~
+ is a very useful option during development time, allowing for deep introspection and debugging
into you app\.
+
+However, in production it exposes your application to be presenting too many informations
on application's internals or to evaluating risky parameter expressions\. Please **always
disable 
+
+~~~~~~~
+devMode
+~~~~~~~
+** before deploying your application to a production environment\. While it is disabled
by default, your 
+
+~~~~~~~
+struts.xml
+~~~~~~~
+ might include a line setting it to 
+
+~~~~~~~
+true
+~~~~~~~
+\. The best way is to ensure the following setting is applied to our 
+
+~~~~~~~
+struts.xml
+~~~~~~~
+ for production deployment:
+
+
+
+| \< constant name ="struts\.devMode" value="false" /\>
+
+| 
+
+__Reduce logging level__
+
+ It's a good practice to reduce logging level from **DEBUG** to **INFO** or less\. Framework's
classes can produce a lot of logging entries which will pollute the log file\. You can even
set logging level to **WARN** for classes that belongs to the framework, see example Log4j2
configuration:
+
+
+~~~~~~~
+<?xml version="1.0" encoding="UTF-8"?>
+<Configuration>
+    <Appenders>
+        <Console name="STDOUT" target="SYSTEM_OUT">
+            <PatternLayout pattern="%d %-5p [%t] %C{2} (%F:%L) - %m%n"/>
+        </Console>
+    </Appenders>
+    <Loggers>
+        <Logger name="com.opensymphony.xwork2" level="warn"/>
+        <Logger name="org.apache.struts2" level="warn"/>
+        <Root level="info">
+            <AppenderRef ref="STDOUT"/>
+        </Root>
+    </Loggers>
+</Configuration>
+~~~~~~~
+
+__Use UTF\-8 encoding__
+
+Always use 
+
+~~~~~~~
+UTF-8
+~~~~~~~
+ encoding when building an application with the Apache Struts 2, when using JSPs please add
the following header to each JSP file
+
+
+~~~~~~~
+<%@ page contentType="text/html; charset=UTF-8" %>
+~~~~~~~
+
+__Do not define setters when not needed__
+
+You should carefully design your actions without exposing anything via setters and getters,
thus can leads to potential security vulnerabilities\. Any action's setter can be used to
set incoming untrusted user's value which can contain suspicious expression\. Some Struts 
+
+~~~~~~~
+Result
+~~~~~~~
+s automatically populate params based on values in 
+
+~~~~~~~
+ValueStack
+~~~~~~~
+ (action in most cases is the root) which means incoming value will be evaluated as an expression
during this process\.
+
+__Do not use incoming values as an input for localisation logic__
+
+All 
+
+~~~~~~~
+TextProvider
+~~~~~~~
+'s 
+
+~~~~~~~
+getText(...) 
+~~~~~~~
+methods (e\.g in 
+
+~~~~~~~
+ActionSupport
+~~~~~~~
+) perform evaluation of parameters included in a message to properly localize the text\.
This means using incoming request parameters with 
+
+~~~~~~~
+getText(...)
+~~~~~~~
+ methods is potentially dangerous and should be avoided\. See example below, assuming that
an action implements getter and setter for property 
+
+~~~~~~~
+message
+~~~~~~~
+, the below code allows inject an OGNL expression:
+
+
+~~~~~~~
+public String execute() throws Exception {
+    setMessage(getText(getMessage()));
+    return SUCCESS;
+}
+~~~~~~~
+
+Never use value of incoming request parameter as part of your localisation logic\.
+
+#####Internal security mechanism#####
+
+The Apache Struts 2 contains internal security manager which blocks access to particular
classes and Java packages \- it's a OGNL\-wide mechanism which means it affects any aspect
of the framework ie\. incoming parameters, expressions used in JSPs, etc\.
+
+There are three options that can be used to configure excluded packages and classes:
+
++ 
+
+~~~~~~~
+struts.excludedClasses
+~~~~~~~
+ \- comma\-separated list of excluded classes
+
++ 
+
+~~~~~~~
+struts.excludedPackageNamePatterns
+~~~~~~~
+ \- patterns used to exclude packages based on RegEx \- this option is slower than simple
string comparison but it's more flexible
+
++ 
+
+~~~~~~~
+struts.excludedPackageNames
+~~~~~~~
+ \- comma\-separated list of excluded packages, it is used with simple string comparison
via 
+
+~~~~~~~
+startWith
+~~~~~~~
+ and 
+
+~~~~~~~
+equals
+~~~~~~~
+
+The defaults are as follow:
+
+
+~~~~~~~
+<constant name="struts.excludedClasses"
+          value="com.opensymphony.xwork2.ActionContext" />
+
+<!-- this must be valid regex, each '.' in package name must be escaped! -->
+<!-- it's more flexible but slower than simple string comparison -->
+<!-- constant name="struts.excludedPackageNamePatterns" value="^java\.lang\..*,^ognl.*,^(?!javax\.servlet\..+)(javax\..+)"
/ -->
+
+<!-- this is simpler version of the above used with string comparison -->
+<constant name="struts.excludedPackageNames" value="java.lang,ognl,javax" />
+~~~~~~~
+
+Any expression or target which evaluates to one of these will be blocked and you see a WARN
in logs:
+
+
+~~~~~~~
+[WARNING] Target class [class example.MyBean] or declaring class of member type [public example.MyBean()]
are excluded!
+~~~~~~~
+
+In that case 
+
+~~~~~~~
+new MyBean()
+~~~~~~~
+ was used to create a new instance of class (inside JSP) \- it's blocked because 
+
+~~~~~~~
+target
+~~~~~~~
+ of such expression is evaluated to 
+
+~~~~~~~
+java.lang.Class
+~~~~~~~
+
+
+It is possible to redefine the above constants in struts\.xml but try to avoid this and rather
change design of your application\!
+
+| 
+
+__Accessing static methods__
+
+Support for accessing static methods from expression will be disabled soon, please consider
re\-factoring your application to avoid further problems\! Please check [WW\-4348](https://issues\.apache\.org/jira/browse/WW\-4348)^[https://issues\.apache\.org/jira/browse/WW\-4348]\.
+
+> 
+
+__OGNL is used to call action's methods__
+
+This can impact actions which have large inheritance hierarchy and use the same method's
name throughout the hierarchy, this was reported as an issue [WW\-4405](https://issues\.apache\.org/jira/browse/WW\-4405)^[https://issues\.apache\.org/jira/browse/WW\-4405]\.
See the example below:
+
+
+~~~~~~~
+public class RealAction extends BaseAction {  
+    @Action("save")
+    public String save() throws Exception {
+        super.save();
+        return SUCCESS;
+    }
+}    
+ 
+public class BaseAction extends AbstractAction {
+    public String save() throws Exception {
+        save(Double.MAX_VALUE);
+        return SUCCESS;
+    }
+}
+ 
+public abstract class AbstractAction extends ActionSupport {
+    protected void save(Double val) {
+        // some logic
+    }
+}
+~~~~~~~
+
+In such case OGNL cannot properly map which method to call when request is coming\. This
is do the OGNL limitation\. To solve the problem don't use the same method's names through
the hierarchy, you can simply change the action's method from 
+
+~~~~~~~
+save()
+~~~~~~~
+ to 
+
+~~~~~~~
+saveAction()
+~~~~~~~
+ and leaving annotation as is to allow call this action via 
+
+~~~~~~~
+/save.action
+~~~~~~~
+ request\.
+
+__Accepted / Excluded patterns__
+
+ As from version 2\.3\.20 the framework provides two new interfaces which are used to accept
/ exclude param names and values \- [AcceptedPatternsChecker](http://struts\.apache\.org/maven/struts2\-core/apidocs/com/opensymphony/xwork2/security/AcceptedPatternsChecker\.html)^[http://struts\.apache\.org/maven/struts2\-core/apidocs/com/opensymphony/xwork2/security/AcceptedPatternsChecker\.html]
and [ExcludedPatternsChecker](http://struts\.apache\.org/maven/struts2\-core/apidocs/com/opensymphony/xwork2/security/ExcludedPatternsChecker\.html)^[http://struts\.apache\.org/maven/struts2\-core/apidocs/com/opensymphony/xwork2/security/ExcludedPatternsChecker\.html]
with default implementations\. These two interfaces are used by [Parameters Interceptor](../core-developers/parameters-interceptor.html)
and [Cookie Interceptor](../core-developers/cookie-interceptor.html) to check if param can
be accepted or must be excluded\. If you were using 
+
+~~~~~~~
+excludeParams
+~~~~~~~
+ previously please compare patterns used by you with these provided by the framework in default
implementation\.
+
+__Strict Method Invocation__
+
+ This mechanism was introduced in version 2\.5\. It allows control what methods can be accessed
with the bang "\!" operator via [Dynamic Method Invocation](../core-developers/action-configuration.html#dynamic-method-invocation)\.
Please read more in Strict Method Invocation section of [Action Configuration](../core-developers/action-configuration.html).
\ No newline at end of file


Mime
View raw message