4848import org .apache .lucene .search .IndexSearcher ;
4949import org .apache .lucene .search .Query ;
5050import org .apache .lucene .search .ScoreDoc ;
51+ import org .apache .lucene .search .Sort ;
52+ import org .apache .lucene .search .SortField ;
53+ import org .apache .lucene .search .TopDocsCollector ;
54+ import org .apache .lucene .search .TopFieldCollector ;
5155import org .apache .lucene .search .TopScoreDocCollector ;
5256import org .apache .lucene .util .Version ;
5357import org .opengrok .indexer .analysis .AbstractAnalyzer ;
6670import org .opengrok .indexer .util .Statistics ;
6771import org .opengrok .indexer .util .TandemPath ;
6872import org .opengrok .indexer .web .Prefix ;
73+ import org .opengrok .indexer .web .SortOrder ;
6974
7075/**
7176 * This is an encapsulation of the details on how to search in the index database.
@@ -114,6 +119,10 @@ public class SearchEngine {
114119 * Holds value of property type.
115120 */
116121 private String type ;
122+ /**
123+ * Holds value of property sort.
124+ */
125+ private SortOrder sortOrder ;
117126 /**
118127 * Holds value of property indexDatabase.
119128 */
@@ -132,7 +141,7 @@ public class SearchEngine {
132141 int cachePages = RuntimeEnvironment .getInstance ().getCachePages ();
133142 int totalHits = 0 ;
134143 private ScoreDoc [] hits ;
135- private TopScoreDocCollector collector ;
144+ private TopDocsCollector <?> collector ;
136145 private IndexSearcher searcher ;
137146 boolean allCollected ;
138147 private final ArrayList <SuperIndexSearcher > searcherList = new ArrayList <>();
@@ -181,6 +190,10 @@ private void searchSingleDatabase(boolean paging) throws IOException {
181190 SuperIndexSearcher superIndexSearcher = RuntimeEnvironment .getInstance ().getSuperIndexSearcher ("" );
182191 searcherList .add (superIndexSearcher );
183192 searcher = superIndexSearcher ;
193+ // If a field-based sort is requested, collect all hits (disable paging optimization)
194+ if (sortOrder != SortOrder .RELEVANCY ) {
195+ paging = false ;
196+ }
184197 searchIndex (superIndexSearcher , paging );
185198 }
186199
@@ -205,16 +218,33 @@ private void searchMultiDatabase(List<Project> projectList, boolean paging) thro
205218 }
206219
207220 private void searchIndex (IndexSearcher searcher , boolean paging ) throws IOException {
208- collector = TopScoreDocCollector .create (hitsPerPage * cachePages , Short .MAX_VALUE );
209- Statistics stat = new Statistics ();
221+ Sort luceneSort = null ;
222+ if (getSortOrder () == SortOrder .LASTMODIFIED ) {
223+ luceneSort = new Sort (new SortField (QueryBuilder .DATE , SortField .Type .STRING , true ));
224+ } else if (getSortOrder () == SortOrder .BY_PATH ) {
225+ luceneSort = new Sort (new SortField (QueryBuilder .FULLPATH , SortField .Type .STRING ));
226+ }
227+ if (luceneSort == null ) {
228+ collector = TopScoreDocCollector .create (hitsPerPage * cachePages , Short .MAX_VALUE );
229+ } else {
230+ collector = TopFieldCollector .create (luceneSort , hitsPerPage * cachePages , Short .MAX_VALUE );
231+ }
210232 searcher .search (query , collector );
211233 totalHits = collector .getTotalHits ();
234+ Statistics stat = new Statistics ();
212235 stat .report (LOGGER , Level .FINEST , "search via SearchEngine done" ,
213236 "search.latency" , new String []{"category" , "engine" ,
214237 "outcome" , totalHits > 0 ? "success" : "empty" });
215- if (!paging && totalHits > 0 ) {
216- collector = TopScoreDocCollector .create (totalHits , Short .MAX_VALUE );
217- searcher .search (query , collector );
238+ if (luceneSort == null ) {
239+ if (!paging && totalHits > 0 ) {
240+ collector = TopScoreDocCollector .create (totalHits , Short .MAX_VALUE );
241+ searcher .search (query , collector );
242+ }
243+ } else {
244+ if (!paging && totalHits > 0 ) {
245+ collector = TopFieldCollector .create (luceneSort , totalHits , Short .MAX_VALUE );
246+ searcher .search (query , collector );
247+ }
218248 }
219249 hits = collector .topDocs ().scoreDocs ;
220250 StoredFields storedFields = searcher .storedFields ();
@@ -645,4 +675,22 @@ public String getType() {
645675 public void setType (String fileType ) {
646676 this .type = fileType ;
647677 }
678+
679+ /**
680+ * Getter for property sort.
681+ *
682+ * @return Value of property sortOrder.
683+ */
684+ public SortOrder getSortOrder () {
685+ return this .sortOrder ;
686+ }
687+
688+ /**
689+ * Setter for property sort.
690+ *
691+ * @param sortOrder New value of property sortOrder.
692+ */
693+ public void setSortOrder (SortOrder sortOrder ) {
694+ this .sortOrder = sortOrder ;
695+ }
648696}
0 commit comments