001 /*
002 Licensed to the Apache Software Foundation (ASF) under one
003 or more contributor license agreements. See the NOTICE file
004 distributed with this work for additional information
005 regarding copyright ownership. The ASF licenses this file
006 to you under the Apache License, Version 2.0 (the
007 "License"); you may not use this file except in compliance
008 with the License. You may obtain a copy of the License at
009
010 http://www.apache.org/licenses/LICENSE-2.0
011
012 Unless required by applicable law or agreed to in writing,
013 software distributed under the License is distributed on an
014 "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015 KIND, either express or implied. See the License for the
016 specific language governing permissions and limitations
017 under the License.
018 */
019 package org.apache.wiki.tags;
020
021 import java.io.IOException;
022 import java.util.Collection;
023
024 import javax.servlet.http.HttpServletRequest;
025 import javax.servlet.jsp.JspWriter;
026 import javax.servlet.jsp.PageContext;
027
028 import org.apache.log4j.Logger;
029 import org.apache.wiki.WikiContext;
030 import org.apache.wiki.WikiEngine;
031 import org.apache.wiki.search.SearchResult;
032 import org.apache.wiki.ui.Command;
033 import org.apache.wiki.ui.PageCommand;
034
035 /**
036 * Iterates through Search result results.
037 *
038 * <P><B>Attributes</B></P>
039 * <UL>
040 * <LI>max = how many search results should be shown.
041 * </UL>
042 *
043 * @since 2.0
044 */
045
046 // FIXME: Shares MUCH too much in common with IteratorTag. Must refactor.
047 public class SearchResultIteratorTag
048 extends IteratorTag
049 {
050 private static final long serialVersionUID = 0L;
051
052 private int m_maxItems;
053 private int m_count = 0;
054 private int m_start = 0;
055
056 private static final Logger log = Logger.getLogger(SearchResultIteratorTag.class);
057
058 public void release()
059 {
060 super.release();
061 m_maxItems = m_count = 0;
062 }
063
064 public void setMaxItems( int arg )
065 {
066 m_maxItems = arg;
067 }
068
069 public void setStart( int arg )
070 {
071 m_start = arg;
072 }
073
074 public final int doStartTag()
075 {
076 //
077 // Do lazy eval if the search results have not been set.
078 //
079 if( m_iterator == null )
080 {
081 Collection searchresults = (Collection) pageContext.getAttribute( "searchresults",
082 PageContext.REQUEST_SCOPE );
083 setList( searchresults );
084
085 int skip = 0;
086
087 // Skip the first few ones...
088 m_iterator = searchresults.iterator();
089 while( m_iterator.hasNext() && (skip++ < m_start) ) m_iterator.next();
090 }
091
092 m_count = 0;
093 m_wikiContext = (WikiContext) pageContext.getAttribute( WikiTagBase.ATTR_CONTEXT,
094 PageContext.REQUEST_SCOPE );
095
096 return nextResult();
097 }
098
099 private int nextResult()
100 {
101 if( m_iterator != null && m_iterator.hasNext() && m_count++ < m_maxItems )
102 {
103 SearchResult r = (SearchResult) m_iterator.next();
104
105 // Create a wiki context for the result
106 WikiEngine engine = m_wikiContext.getEngine();
107 HttpServletRequest request = m_wikiContext.getHttpRequest();
108 Command command = PageCommand.VIEW.targetedCommand( r.getPage() );
109 WikiContext context = new WikiContext( engine, request, command );
110
111 // Stash it in the page context
112 pageContext.setAttribute( WikiTagBase.ATTR_CONTEXT,
113 context,
114 PageContext.REQUEST_SCOPE );
115 pageContext.setAttribute( getId(), r );
116
117 return EVAL_BODY_BUFFERED;
118 }
119
120 return SKIP_BODY;
121 }
122
123 public int doAfterBody()
124 {
125 if( bodyContent != null )
126 {
127 try
128 {
129 JspWriter out = getPreviousOut();
130 out.print(bodyContent.getString());
131 bodyContent.clearBody();
132 }
133 catch( IOException e )
134 {
135 log.error("Unable to get inner tag text", e);
136 // FIXME: throw something?
137 }
138 }
139
140 return nextResult();
141 }
142
143 public int doEndTag()
144 {
145 m_iterator = null;
146
147 return super.doEndTag();
148 }
149 }