KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > blandware > atleap > webapp > action > core > siteMap > ViewSiteMapAction


1 /*
2  * Copyright 2004 Blandware (http://www.blandware.com)
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package com.blandware.atleap.webapp.action.core.siteMap;
17
18 import com.blandware.atleap.common.Constants;
19 import com.blandware.atleap.common.util.QueryInfo;
20 import com.blandware.atleap.common.util.StringUtil;
21 import com.blandware.atleap.model.core.ActionPage;
22 import com.blandware.atleap.model.core.BaseObject;
23 import com.blandware.atleap.model.core.ContentDocument;
24 import com.blandware.atleap.model.core.ContentPage;
25 import com.blandware.atleap.model.core.Page;
26 import com.blandware.atleap.service.core.ContentResourceManager;
27 import com.blandware.atleap.service.core.PageManager;
28 import com.blandware.atleap.webapp.action.core.BaseAction;
29 import com.blandware.atleap.webapp.util.core.GlobalProperties;
30 import com.blandware.atleap.webapp.util.core.WebappConstants;
31 import com.blandware.atleap.webapp.util.core.WebappUtil;
32 import org.apache.commons.validator.GenericValidator;
33 import org.apache.struts.Globals;
34 import org.apache.struts.action.ActionForm;
35 import org.apache.struts.action.ActionForward;
36 import org.apache.struts.action.ActionMapping;
37
38 import javax.servlet.http.HttpServletRequest JavaDoc;
39 import javax.servlet.http.HttpServletResponse JavaDoc;
40 import java.io.Serializable JavaDoc;
41 import java.lang.reflect.InvocationTargetException JavaDoc;
42 import java.util.ArrayList JavaDoc;
43 import java.util.HashMap JavaDoc;
44 import java.util.Iterator JavaDoc;
45 import java.util.List JavaDoc;
46 import java.util.Locale JavaDoc;
47 import java.util.Map JavaDoc;
48
49 /**
50  * <p>Prepares site map to show on the page
51  * </p>
52  * <p><a HREF="ListContentPagesAction.java.htm"><i>View Source</i></a></p>
53  * <p/>
54  *
55  * @author Sergey Zubtcovskii <a HREF="mailto:sergey.zubtcovskii@blandware.com">&lt;sergey.zubtcovskii@blandware.com&gt;</a>
56  * @version $Revision: 1.10 $ $Date: 2006/03/16 11:09:41 $
57  * @struts.action path="/core/siteMap/view"
58  * validate="false"
59  * @struts.action-forward name="viewSiteMap"
60  * path=".core.siteMap.view"
61  */

62 public final class ViewSiteMapAction extends BaseAction {
63     /**
64      * @param mapping The ActionMapping used to select this instance
65      * @param form The optional ActionForm bean for this request (if any)
66      * @param request The HTTP request we are proceeding
67      * @param response The HTTP response we are creating
68      * @return an ActionForward instance describing where and how
69      * control should be forwarded, or null if response
70      * has already been completed
71      */

72     public ActionForward execute(ActionMapping mapping, ActionForm form,
73                                  HttpServletRequest JavaDoc request, HttpServletResponse JavaDoc response) throws Exception JavaDoc {
74
75         MapSection rootSection = null;
76         // TODO: get from cache here
77

78         if ( rootSection == null ) {
79             // create root section
80
rootSection = new MapSection("/");
81
82             PageManager pageManager = (PageManager) getBean(Constants.PAGE_MANAGER_BEAN);
83             ContentResourceManager resourceManager = (ContentResourceManager) getBean(Constants.CONTENT_RESOURCE_MANAGER_BEAN);
84
85             // get locale identifier
86
Locale JavaDoc locale = (Locale JavaDoc) request.getSession().getAttribute(Globals.LOCALE_KEY);
87             String JavaDoc localeIdentifier = locale.getLanguage();
88             Map JavaDoc queryParameters = new HashMap JavaDoc();
89             queryParameters.put("localeIdentifier", localeIdentifier);
90             QueryInfo queryInfo = new QueryInfo();
91             queryInfo.setQueryParameters(queryParameters);
92             queryInfo.setOrderByClause("r.uri asc");
93
94             // get list of documents
95
List JavaDoc documents = resourceManager.listContentDocuments(queryInfo).asList();
96
97             // add active filter
98
queryInfo.setWhereClause("page.active = 'T'");
99             queryInfo.setOrderByClause("page.uri asc");
100
101             // get list of content pages
102
List JavaDoc contentPages = pageManager.listContentPages(queryInfo).asList();
103
104             // get list of action pages
105
List JavaDoc actionPages = pageManager.listActionPages(queryInfo).asList();
106
107             // process each list
108

109             // cp
110
for ( Iterator JavaDoc i = contentPages.iterator(); i.hasNext(); ) {
111                 ContentPage contentPage = (ContentPage) i.next();
112                 String JavaDoc uri = contentPage.getUri();
113                 rootSection.addElement(contentPage, uri.substring(WebappConstants.CONTENT_PAGES_URI_PREFIX.length()), localeIdentifier, request);
114             }
115
116             // ap
117
for ( Iterator JavaDoc i = actionPages.iterator(); i.hasNext(); ) {
118                 ActionPage actionPage = (ActionPage) i.next();
119                 String JavaDoc uri = actionPage.getUri();
120                 rootSection.addElement(actionPage, uri, localeIdentifier, request);
121             }
122
123             // documents
124
for ( Iterator JavaDoc i = documents.iterator(); i.hasNext(); ) {
125                 ContentDocument contentDocument = (ContentDocument) i.next();
126                 String JavaDoc uri = contentDocument.getUri();
127                 rootSection.addElement(contentDocument, uri.substring(Constants.RESOURCES_URI_PREFIX.length()), localeIdentifier, request);
128             }
129
130             // TODO: put in cache here
131
}
132
133         // get patterns for index elements
134
String JavaDoc patternString = GlobalProperties.getInstance(request.getSession().getServletContext()).getString(Constants.MAP_SECTION_INDEX_PATTERNS_PROPERTY);
135         List JavaDoc patternList = new ArrayList JavaDoc();
136         if ( !GenericValidator.isBlankOrNull(patternString) ) {
137             String JavaDoc[] patterns = patternString.split(",");
138             for ( int i = 0; i < patterns.length; i++ ) {
139                 String JavaDoc pattern = patterns[i];
140                 if ( !GenericValidator.isBlankOrNull(pattern) ) {
141                     patternList.add(pattern.trim());
142                 }
143             }
144         }
145
146         // recursively set index elements for all sections, remove elements, which are not allowed
147
// to currently logged in user and collapse sections which does not have elements
148
rootSection = processSection(rootSection, patternList, request);
149
150         // save section in request
151
request.setAttribute(WebappConstants.SITE_MAP_KEY, rootSection);
152
153         return mapping.findForward("viewSiteMap");
154     }
155
156     /**
157      * Performs recursive copy of section, removes elements which are not allowed
158      * because of security reasons, collapses sections without elements and sets index elements
159      *
160      * @param section Section to process
161      * @param patterns Patterns to which URI must apply to be recognized as index element
162      * @param request Request
163      * @return Copy of section with index element (if any) set and
164      */

165     public MapSection processSection(MapSection section, List JavaDoc patterns, HttpServletRequest JavaDoc request) throws IllegalAccessException JavaDoc, NoSuchMethodException JavaDoc, InvocationTargetException JavaDoc {
166         MapSection newSection = new MapSection(section.getPath());
167         newSection.setIndexElement(null);
168         List JavaDoc elements = section.getElements();
169         for ( Iterator JavaDoc i = elements.iterator(); i.hasNext(); ) {
170             MapSection.SectionElement element = (MapSection.SectionElement) i.next();
171             boolean indexElement = false;
172             if ( WebappUtil.isUserInRole(element.getRoles(), false, "name", request) ) {
173                 for ( Iterator JavaDoc j = patterns.iterator(); j.hasNext() && newSection.getIndexElement() == null; ) {
174                     String JavaDoc pattern = (String JavaDoc) j.next();
175                     String JavaDoc uri = element.getUri();
176                     // if element wraps CP, URI will start with /pages/
177
// if element wraps document, URI will start with /rw/resource/
178
// we need to find index of first occurence of section's path, to correctly get the URI of element to
179
// check for patterns match
180
int k = uri.indexOf(section.getPath());
181                     if ( matchesPattern(uri.substring(k + section.getPath().length()), pattern) ) {
182                         newSection.setIndexElement(element);
183                         indexElement = true;
184                     }
185                 }
186                 if ( !indexElement ) {
187                     // this element does not match any pattern, so add it to the list
188
newSection.getElements().add(element);
189                 }
190             }
191         }
192
193         // process subsections recursively
194
List JavaDoc sections = section.getSections();
195
196         for ( Iterator JavaDoc i = sections.iterator(); i.hasNext(); ) {
197             MapSection subSection = processSection((MapSection) i.next(), patterns, request);
198             if ( subSection.getElements().isEmpty() && subSection.getIndexElement() == null ) {
199                 // move all subsections of this subsection up one level
200
for ( Iterator JavaDoc j = subSection.getSections().iterator(); j.hasNext(); ) {
201                     MapSection s = (MapSection) j.next();
202                     newSection.addSection(s);
203                 }
204             } else {
205                 newSection.addSection(subSection);
206             }
207         }
208
209         // if there is only one element and no index, set this element to be index
210
if ( newSection.getElements().size() == 1 && newSection.getIndexElement() == null ) {
211             newSection.setIndexElement((MapSection.SectionElement) newSection.getElements().get(0));
212             newSection.setElements(new ArrayList JavaDoc());
213         }
214
215         return newSection;
216     }
217
218     /**
219      * Returns true, if given uri matched pattern
220      *
221      * @param uri URI to check
222      * @param pattern Pattern to match
223      * @return True if URI matches given pattern, false otherwise
224      */

225     protected boolean matchesPattern(String JavaDoc uri, String JavaDoc pattern) {
226         // remove extension (if any)
227
// query parameters for document URI will be removed to
228
int dot = uri.lastIndexOf('.');
229         if ( dot != -1 ) {
230             uri = uri.substring(0, dot);
231         }
232         int k = pattern.indexOf('*');
233         if ( k == -1 ) {
234             // no asterisk provided, full coincidence expected
235
return uri.equals(pattern);
236         } else {
237             if ( k == 0 ) {
238                 // asterisk is at the first character
239
return uri.endsWith(pattern.substring(1));
240             } else if ( k == pattern.length() - 1 ) {
241                 // asterisk is at the last character
242
return uri.startsWith(pattern.substring(0, k));
243             } else {
244                 // asterisk is between first and last characters
245
String JavaDoc start = pattern.substring(0, k);
246                 String JavaDoc end = pattern.substring(k + 1, pattern.length());
247                 return uri.startsWith(start) && uri.endsWith(end);
248             }
249         }
250     }
251
252     /**
253      * Describes section of site map, associated with part of URI of page or document in global page's or document's hierarchy
254      */

255     public static class MapSection implements Serializable JavaDoc {
256
257         /**
258          * Path of virtual folders, this section associated with
259          */

260         protected String JavaDoc path;
261
262         /**
263          * Index page or document of this section. May be null
264          */

265         protected SectionElement indexElement;
266
267         /**
268          * List of subsections
269          */

270         protected List JavaDoc sections = new ArrayList JavaDoc();
271
272         /**
273          * List of pages or documents in this section
274          */

275         protected List JavaDoc elements = new ArrayList JavaDoc();
276
277         /**
278          * Creates new instance of MapSection
279          *
280          * @param path Path to associate section with
281          */

282         public MapSection(String JavaDoc path) {
283             if ( path == null ) {
284                 throw new IllegalArgumentException JavaDoc("Path is null");
285             }
286             this.path = path;
287         }
288
289         /**
290          * Returns path
291          *
292          * @return path
293          */

294         public String JavaDoc getPath() {
295             return path;
296         }
297
298         /**
299          * Sets path
300          *
301          * @param path path to set
302          */

303         public void setPath(String JavaDoc path) {
304             this.path = path;
305         }
306
307         /**
308          * Returns index element
309          *
310          * @return index element
311          */

312         public SectionElement getIndexElement() {
313             return indexElement;
314         }
315
316         /**
317          * Sets index element
318          *
319          * @param indexElement index element to set
320          */

321         public void setIndexElement(SectionElement indexElement) {
322             this.indexElement = indexElement;
323         }
324
325         /**
326          * Returns sections
327          *
328          * @return sections
329          */

330         public List JavaDoc getSections() {
331             return sections;
332         }
333
334         /**
335          * Sets sections
336          *
337          * @param sections sections to set
338          */

339         public void setSections(List JavaDoc sections) {
340             this.sections = sections;
341         }
342
343         /**
344          * Returns elements
345          *
346          * @return elements
347          */

348         public List JavaDoc getElements() {
349             return elements;
350         }
351
352         /**
353          * Sets elements
354          *
355          * @param elements elements to set
356          */

357         public void setElements(List JavaDoc elements) {
358             this.elements = elements;
359         }
360
361         /**
362          * Adds section to the list
363          *
364          * @param section Section to add
365          */

366         public void addSection(MapSection section) {
367             sections.add(section);
368         }
369
370         /**
371          * Adds object to this section. Creates sub section if necessary
372          *
373          * @param obj Object to add
374          * @param path Path to section, which must contain this object
375          * @param localeIdentifier Identifier of locale to select title
376          * @param request HTTP servlet request we're currently proceeding
377          */

378         public void addElement(BaseObject obj, String JavaDoc path, String JavaDoc localeIdentifier, HttpServletRequest JavaDoc request) {
379
380             // find slash after path, associated with this section
381
int k = path.indexOf("/", this.path.length());
382             if ( k != -1 ) {
383                 // path to child section. includes path of this section,
384
// folder name following this path and slash at the end of string
385
String JavaDoc sectionPath = path.substring(0, k + 1);
386                 // create sub section
387
MapSection section = findSection(sectionPath);
388                 if ( section == null ) {
389                     // section not found: creating new
390
section = new MapSection(sectionPath);
391                     addSection(section);
392                 }
393                 // add this object to child section
394
section.addElement(obj, path, localeIdentifier, request);
395             } else {
396                 // add object to this section
397
SectionElement se = new SectionElement(obj, localeIdentifier, request);
398                 elements.add(se);
399             }
400         }
401
402         /**
403          * Searches section by specified path
404          *
405          * @param path Path to search section by
406          * @return Section or null if none found
407          */

408         protected MapSection findSection(String JavaDoc path) {
409             for ( Iterator JavaDoc i = sections.iterator(); i.hasNext(); ) {
410                 MapSection section = (MapSection) i.next();
411                 if ( section.getPath().equals(path) ) {
412                     return section;
413                 }
414             }
415             return null;
416         }
417
418         public boolean equals(Object JavaDoc o) {
419             if ( this == o ) {
420                 return true;
421             }
422             if ( !(o instanceof MapSection) ) {
423                 return false;
424             }
425
426             final MapSection mapSection = (MapSection) o;
427
428             if ( path != null ? !path.equals(mapSection.path) : mapSection.path != null ) {
429                 return false;
430             }
431
432             return true;
433         }
434
435         public int hashCode() {
436             return (path != null ? path.hashCode() : 0);
437         }
438
439         /**
440          * Wrapper class that describes separate section element
441          */

442         public static class SectionElement implements Serializable JavaDoc {
443
444             public static final String JavaDoc SECTION_ELEMENT_PAGE = "page";
445             public static final String JavaDoc SECTION_ELEMENT_DOCUMENT = "document";
446
447             /**
448              * Title of this element
449              */

450             protected String JavaDoc title;
451
452             /**
453              * URI of this element
454              */

455             protected String JavaDoc uri;
456
457             /**
458              * Allowed roles
459              */

460             protected List JavaDoc roles;
461
462             /**
463              * Type of element
464              */

465             protected String JavaDoc type;
466
467             /**
468              * Creates new instance of SectionElement
469              *
470              * @param obj Object to wrap
471              * @param localeIdentifier Identifier of locale to get titles of pages for
472              * @param request HTTP servelt request we're currently proceeding
473              */

474             public SectionElement(BaseObject obj, String JavaDoc localeIdentifier, HttpServletRequest JavaDoc request) {
475                 if ( !(obj instanceof ContentPage) && !(obj instanceof ActionPage) && !(obj instanceof ContentDocument) ) {
476                     throw new IllegalArgumentException JavaDoc("Cannot wrap instance of " + obj.getClass().getName());
477                 }
478
479                 if ( obj instanceof Page ) {
480                     Page page = (Page) obj;
481                     title = StringUtil.shortenString(WebappUtil.getFieldValue(page.getTitle(), localeIdentifier, request, true), 40);
482                     uri = WebappUtil.getActionMappingURL(page.getUri(), null, request, WebappConstants.URL_TYPE_CONTEXT_RELATIVE);
483                     if ( GenericValidator.isBlankOrNull(title) ) {
484                         title = uri;
485                     }
486                     type = SECTION_ELEMENT_PAGE;
487                     if ( page instanceof ContentPage ) {
488                         ContentPage cp = (ContentPage) page;
489                         roles = cp.getRoles();
490                     } else if ( page instanceof ActionPage ) {
491                         ActionPage ap = (ActionPage) page;
492                         roles = WebappUtil.getAPRoleNamesAsList(ap.getUri(), request);
493                     }
494                 } else {
495                     ContentDocument document = (ContentDocument) obj;
496                     if ( !GenericValidator.isBlankOrNull(document.getDescription()) ) {
497                         title = StringUtil.shortenString(document.getDescription(), 40);
498                     } else {
499                         title = document.getUri();
500                     }
501                     uri = document.getUri() + "?view=true";
502                     roles = document.getRoles();
503                     type = SECTION_ELEMENT_DOCUMENT;
504                 }
505
506                 if ( roles == null ) {
507                     roles = new ArrayList JavaDoc();
508                 }
509             }
510
511             /**
512              * Returns title
513              *
514              * @return title
515              */

516             public String JavaDoc getTitle() {
517                 return title;
518             }
519
520             /**
521              * Sets title
522              *
523              * @param title title to set
524              */

525             public void setTitle(String JavaDoc title) {
526                 this.title = title;
527             }
528
529             /**
530              * Returns URI
531              *
532              * @return URI
533              */

534             public String JavaDoc getUri() {
535                 return uri;
536             }
537
538             /**
539              * Sets URI
540              *
541              * @param uri URI to set
542              */

543             public void setUri(String JavaDoc uri) {
544                 this.uri = uri;
545             }
546
547             /**
548              * Returns roles
549              *
550              * @return roles
551              */

552             public List JavaDoc getRoles() {
553                 return roles;
554             }
555
556             /**
557              * Sets roles
558              *
559              * @param roles roles to set
560              */

561             public void setRoles(List JavaDoc roles) {
562                 this.roles = roles;
563             }
564
565             /**
566              * Returns type
567              *
568              * @return type
569              */

570             public String JavaDoc getType() {
571                 return type;
572             }
573
574             /**
575              * Sets type
576              *
577              * @param type type to set
578              */

579             public void setType(String JavaDoc type) {
580                 this.type = type;
581             }
582
583             public boolean equals(Object JavaDoc o) {
584                 if ( this == o ) {
585                     return true;
586                 }
587                 if ( !(o instanceof SectionElement) ) {
588                     return false;
589                 }
590
591                 final SectionElement sectionElement = (SectionElement) o;
592
593                 if ( !type.equals(sectionElement.type) ) {
594                     return false;
595                 }
596                 if ( !uri.equals(sectionElement.uri) ) {
597                     return false;
598                 }
599
600                 return true;
601             }
602
603             public int hashCode() {
604                 int result;
605                 result = uri.hashCode();
606                 result = 29 * result + type.hashCode();
607                 return result;
608             }
609
610         }
611     }
612
613 }
Popular Tags