# Merging Struts Artifacts Into Page Flows

WebLogic Workshop allows you to merge existing Struts artifacts, such as actions, into the configuration XML that is generated for a page flow. You can use a class-level annotation, @jpf:controller struts-merge, to enable the merger. It occurs when the web project is compiled. After the merger the Struts artifacts from the existing configuration are available for use in the page flow.

This topic focuses on the merger of a Struts configuration and a page flow. For information about enabling Struts modules and page flows to exist in the same web project, and allowing them to interact by using form beans, see Interoperating With Struts and Page Flows.

The following diagram illustrates the concepts of this feature, which is called "Struts Merge." The purpose of this feature is to enable you to override page flow defaults, or to specify settings for the page flow that are not provided by page flow annotations or their attributes. The Struts merge files should typically be small and only modify the page flow and its actions and form beans. While you could, for example, add action mappings in the Struts merge file, BEA does not recommend this practice. Struts action mappings should be declared in the page flow's .jpf file with @jpf annotations, and then (if necessary) modified with the Struts merge file.

Note: In the event of a naming conflict during the merger, artifacts in the Struts merge file will supercede any corresponding entities in the page flow.

## Requirements of the Struts Module

Here are a few requirements of the Struts module that you will merge with a page flow:

- You must be using Struts 1.1.
- The Struts configuration XML file to be merged with the page flow must by valid xml. Compilation of the page flow's JPF file fails if the Struts merge file does not exist at the specified location, or is invalid. The merge file is parsed and validated against the DTD before it is merged. For example, not adding all required attributes in the merge file results in an error, even if the page flow generated file has all the remaining, required attributes. The merge file must be valid on its own before the merge operation can continue.
- By convention, the Struts module's XML file should reside in the web project's /WEB-INF directory. However the Struts XML may reside in other directories, as long as the directory is part of the web project's hierarchy of directories.
- All your compiled Struts-related classes (*.class bytecode) that are in a JAR file must reside in the WEB-INF/lib directory. Your Struts *.class files, if they are not in a JAR, must go in the WEB-INF/classes directory. Placing your user-defined Struts classes or JARs in another directory, such as APP-INF/lib or <WEBLOGIC_HOME>/server/lib, will cause classloader problems.

## Requirements of the Page Flow Controller

In the page flow that will use artifacts from a Struts configuration, you must specify the @jpf:controller annotation and use the struts-merge attribute. This annotation appears at the class-level for the page flow controller. For example:

        /**
         * @jpf:controller struts-merge="/WEB-INF/all-struts-config-merge-example.xml"
         */
         public class strutsMergeController extends PageFlowController
         {

Then in your page flow action methods, make sure you use the exact capitalization of actions or other artifacts that will be merged from the Struts configuration.

## The Merge Rules

In the generated jpf-struts-config-<pageflow>.xml file, each <action> tag from the Struts file is merged using the "path" attribute as a key. Similarly:

- Each <forward> tag from the Struts file is merged using the "name" attribute
- Each <form-bean> tag from the Struts file is merged using the "name" attribute
- Each <exception> tag from the Struts file is merged using the "type" attribute

## A Merge Sample

WebLogic Workshop provides a Struts merge sample that you can run. In the IDE, choose File > Open > Application... and browse to:

<WEBLOGIC_HOME>/samples/workshop/SamplesApp/SamplesApp.work

With the application open in the IDE, open the WebApp project. Then look at the files in the /strutsMerge directory. Also see the all-Struts merge file in /WEB-INF/all-struts-config-merge-example.xml. It includes the following global forward and a mapping for an "unknown handler":

     <global-forwards>
         <forward name="fromStrutsConfig" path="page2.jsp"/>
     </global-forwards>

     <action-mappings>
         <action path="/unk" unknown="true"/>
         .
         .
         .

In the /strutsMerge directory, see the page1.jsp page. To demonstrate this Struts Merge feature, the page1.jsp page contains a link that refers to a deliberately undefined "foo.do" action.

     <netui:anchor href="foo.do">This link refers to an unknown action named "foo.do"</netui:anchor>

On the rendered page1.jsp, when you click the link that refers to the "foo" action, the "unknown handler" action in /strutsMerge/strutsMergeController.jpf is run. It is defined as follows:

        /**
         *
         * @jpf:action
         */
         public Forward unk()
         {
         return new Forward( "fromStrutsConfig" );
         }

After the project compilation, which resulted in the merger of the all-Struts and page flow configurations, we were able to use the unknown handler and global forward in the page flow at runtime. In the JPF, the unk() method forwards to the global forward ("fromStrutsConfig") that is defined in the merged file. If you look in the merged /WEB-INF/jpf-struts-config-strutsMerge.xml, it contains:

     <global-forwards>
         <forward name="fromStrutsConfig" path="page2.jsp"/>
     </global-forwards>
     <action-mappings>
         <action validate="false" scope="request"
            type="strutsMerge.strutsMergeController"
            path="/unk" unknown="true"/>

To run this sample, start the server; then in a browser, open:

http://<host>:<port>/WebApp/Controller.jpf

By default the URL for page flow samples running on your machine is:

http://localhost:7001/WebApp/Controller.jpf

On the samples index.jsp start page, click the Go! button link in the section titled "Merging Struts Functionality with Page Flow". When you run the strutsMerge sample, notice how the global action named "fromStrutsConfig" resulted in the forward from page1.jsp to page2.jsp, via the unknown handler and the global forward.

Related Topics

For information about using a form bean to pass data between all-Struts and page flow applications, see:

Interoperating With Struts and Page Flows

### Sample Code

Struts Merging Sample