/** * Yobi, Project Hosting SW * * Copyright 2014 NAVER Corp. * http://yobi.io * * @author Keesun Baik * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package models; import com.avaje.ebean.Page; import models.enumeration.SearchType; import java.util.ArrayList; import java.util.Collections; import java.util.LinkedList; import java.util.List; public class SearchResult { private String keyword; private SearchType searchType; private int usersCount; private int projectsCount; private int issuesCount; private int postsCount; private int milestonesCount; private int issueCommentsCount; private int postCommentsCount; private int reviewsCount; private Page users; private Page projects; private Page issues; private Page posts; private Page milestones; private Page issueComments; private Page postComments; private Page reviews; public List makeSnippets(String contents, int threshold) { String lowerCaseContents = contents.toLowerCase(); String lowerCaseKeyword = keyword.toLowerCase(); LinkedList beginAndEnds = new LinkedList<>(); List indexes = findIndexes(lowerCaseContents, lowerCaseKeyword); // 6, 40 for(int i = 0 ; i < indexes.size() ; i++) { int currentIndex = indexes.get(i); int beginIndex = beginIndex(currentIndex, threshold); int endIndex = endIndex(currentIndex + lowerCaseKeyword.length(), lowerCaseContents.length(), threshold); BeginAndEnd thisOne = new BeginAndEnd(beginIndex, endIndex); if(i == 0) { beginAndEnds.push(thisOne); } else { BeginAndEnd latestOne = beginAndEnds.peek(); if(latestOne.getEndIndex() >= thisOne.getBeginIndex()) { BeginAndEnd mergedOne = new BeginAndEnd(latestOne.getBeginIndex(), thisOne.getEndIndex()); beginAndEnds.pop(); beginAndEnds.push(mergedOne); } else { beginAndEnds.push(thisOne); } } } Collections.reverse(beginAndEnds); List snippets = new ArrayList<>(); for(BeginAndEnd bae : beginAndEnds) { snippets.add(contents.substring(bae.beginIndex, bae.endIndex)); } return snippets; } private List findIndexes(String contents, String keyword) { List indexes = new ArrayList<>(); int index = contents.indexOf(keyword); while (index != -1) { indexes.add(index); index = contents.indexOf(keyword, index + keyword.length()); } return indexes; } private int beginIndex(int index, int threshold) { return index < threshold ? 0 : index - threshold; } private int endIndex(int keywordEndIndex, int contentLength, int threshold) { int endIndex = keywordEndIndex + threshold; return endIndex < contentLength ? endIndex : contentLength; } public void updateSearchType() { if(!(this.searchType == SearchType.AUTO)) { return; } if (getIssuesCount() > 0) { setSearchType(SearchType.ISSUE); return; } if (getUsersCount() > 0) { setSearchType(SearchType.USER); return; } if (getProjectsCount() > 0) { setSearchType(SearchType.PROJECT); return; } if (getPostsCount() > 0) { setSearchType(SearchType.POST); return; } if (getMilestonesCount() > 0) { setSearchType(SearchType.MILESTONE); return; } if (getIssueCommentsCount() > 0) { setSearchType(SearchType.ISSUE_COMMENT); return; } if (getPostCommentsCount() > 0) { setSearchType(SearchType.POST_COMMENT); return; } if (getReviewsCount() > 0) { setSearchType(SearchType.REVIEW); return; } setSearchType(SearchType.ISSUE); } private class BeginAndEnd { int beginIndex; int endIndex; BeginAndEnd(int beginIndex, int endIndex) { this.beginIndex = beginIndex; this.endIndex = endIndex; } public int getBeginIndex() { return beginIndex; } public int getEndIndex() { return endIndex; } @Override public String toString() { return "BeginAndEnd{" + "beginIndex=" + beginIndex + ", endIndex=" + endIndex + '}'; } } public String getKeyword() { return keyword; } public void setKeyword(String keyword) { this.keyword = keyword; } public int getUsersCount() { return usersCount; } public void setUsersCount(int usersCount) { this.usersCount = usersCount; } public int getProjectsCount() { return projectsCount; } public void setProjectsCount(int projectsCount) { this.projectsCount = projectsCount; } public int getIssuesCount() { return issuesCount; } public void setIssuesCount(int issuesCount) { this.issuesCount = issuesCount; } public int getPostsCount() { return postsCount; } public void setPostsCount(int postsCount) { this.postsCount = postsCount; } public int getMilestonesCount() { return milestonesCount; } public void setMilestonesCount(int milestonesCount) { this.milestonesCount = milestonesCount; } public int getIssueCommentsCount() { return issueCommentsCount; } public void setIssueCommentsCount(int issueCommentsCount) { this.issueCommentsCount = issueCommentsCount; } public int getPostCommentsCount() { return postCommentsCount; } public void setPostCommentsCount(int postCommentsCount) { this.postCommentsCount = postCommentsCount; } public int getReviewsCount() { return reviewsCount; } public void setReviewsCount(int reviewsCount) { this.reviewsCount = reviewsCount; } public Page getUsers() { return users; } public void setUsers(Page users) { this.users = users; } public Page getProjects() { return projects; } public void setProjects(Page projects) { this.projects = projects; } public Page getIssues() { return issues; } public void setIssues(Page issues) { this.issues = issues; } public Page getPosts() { return posts; } public void setPosts(Page posts) { this.posts = posts; } public Page getMilestones() { return milestones; } public void setMilestones(Page milestones) { this.milestones = milestones; } public Page getIssueComments() { return issueComments; } public void setIssueComments(Page issueComments) { this.issueComments = issueComments; } public Page getPostComments() { return postComments; } public void setPostComments(Page postComments) { this.postComments = postComments; } public Page getReviews() { return reviews; } public void setReviews(Page reviews) { this.reviews = reviews; } public SearchType getSearchType() { return searchType; } public void setSearchType(SearchType searchType) { this.searchType = searchType; } }