Dynamic Directory in Java EE Web Application

I created a Java EE application that uses JSF. In my web directory, I have a file called index.xhtml . My goal is to serve different content on this web page based on the name of the parent directory.

For example:

http://localhost:8080/myapp/1/index.xhtml will print You accessed through "1" . http://localhost:8080/myapp/1234/index.xhtml will print You accessed through "1234" .

I do not want to create a directory for every possible number; It must be fully dynamic.

In addition, I need my navigation rules to still be usable. Therefore, if I have a navigation rule, for example:

 <navigation-rule> <display-name>*</display-name> <from-view-id>*</from-view-id> <navigation-case> <from-outcome>index</from-outcome> <to-view-id>/index.xhtml</to-view-id> <redirect /> </navigation-case> </navigation-rule> 

Then, if I am in the 1234 directory, it will still be redirected to the index.xhtml inside 1234 .

Is it possible? How can i do this?

+4
jsf
source share
1 answer

To forward /[number]/index.xhtml [number] /[number]/index.xhtml to /index.xhtml , which results in [number] stored as a request attribute, you need a servlet filter . The doFilter() implementation might look like this:

 @WebFilter("/*") public class YourFilter implements Filter { @Override public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException { HttpServletRequest request = (HttpServletRequest) req; String[] paths = request.getRequestURI().substring(request.getContextPath().length()).split("/"); if (paths.length == 3 && paths[2].equals("index.xhtml") && paths[1].matches("[0-9]{1,9}")) { request.setAttribute("directory", Integer.valueOf(paths[1])); request.getRequestDispatcher("/index.xhtml").forward(req, res); } else { chain.doFilter(req, res); } } // ... } 

It ensures that the number matches 1 to 9 latin digits and saves it as a request attribute identified by directory and finally goes to /index.xhtml in the root context. If nothing happens, he simply continues the request, as if nothing special had happened.

In /index.xhtml you can access the number #{directory} .

 <p>You accessed through "#{directory}"</p> 

Then, to make sure the JSF navigation (and <h:form> !) Continues to work, you need a custom view view handler that overrides getActionURL() to add a URL with the path represented by the directory request attribute, if any . Here is an example run:

 public class YourViewHandler extends ViewHandlerWrapper { private ViewHandler wrapped; public YourViewHandler(ViewHandler wrapped) { this.wrapped = wrapped; } @Override public String getActionURL(FacesContext context, String viewId) { String actionURL = super.getActionURL(context, viewId); if (actionURL.endsWith("/index.xhtml")) { Integer directory = (Integer) context.getExternalContext().getRequestMap().get("directory"); if (directory != null) { actionURL = actionURL.substring(0, actionURL.length() - 11) + directory + "/index.xhtml"; } } return actionURL; } @Override public ViewHandler getWrapped() { return wrapped; } } 

To run it, register in faces-config.xml as shown below.

 <application> <view-handler>com.example.YourViewHandler</view-handler> </application> 

This is also largely due to the way JSF targets URL relaying for engines like PrettyFaces .

See also:

  • How to use a servlet filter in Java to change the URL of an incoming servlet?
  • How to create friendly and secure urls in jsf?
  • Get rewritten url with query string
+4
source share

All Articles