/** Generate a sort string for the given DC metadata */ public static String makeSortString(String value, String language, String type) { OrderFormatDelegate delegate = null; // If there is no value, return null if (value == null) return null; // If a named index has been supplied if (type != null && type.length() > 0) { // Use a delegate if one is configured if ((delegate = OrderFormat.getDelegate(type)) != null) { return delegate.makeSortString(value, language); } // No delegates found, so apply defaults if (type.equalsIgnoreCase(OrderFormat.AUTHOR) && authorDelegate != null) { return authorDelegate.makeSortString(value, language); } if (type.equalsIgnoreCase(OrderFormat.TITLE) && titleDelegate != null) { return titleDelegate.makeSortString(value, language); } if (type.equalsIgnoreCase(OrderFormat.TEXT) && textDelegate != null) { return textDelegate.makeSortString(value, language); } } return value; }
/** * Return a normalized focus value. If there is no normalization that can be performed, return the * focus value that is passed in. * * @param value a focus value to normalize * @return the normalized focus value * @throws BrowseException */ private String normalizeJumpToValue(String value) throws BrowseException { // If the scope has a focus value (focus by value) if (scope.hasJumpToValue()) { // Normalize it based on the specified language as appropriate for this index return OrderFormat.makeSortString( scope.getJumpToValue(), scope.getJumpToValueLang(), scope.getBrowseIndex().getDataType()); } else if (scope.hasStartsWith()) { // Scope has a starts with, so normalize that instead return OrderFormat.makeSortString( scope.getStartsWith(), null, scope.getBrowseIndex().getDataType()); } // No focus value on the scope (ie. focus by id), so just return the passed focus value // This is useful in cases where we have pulled a focus value from the index // which will already be normalized, and avoids another DB lookup return value; }
/** * Browse the archive by the full item browse mechanism. This produces a BrowseInfo object which * contains full BrowseItem objects as its result set. * * @param bs the scope of the browse * @return the results of the browse * @throws BrowseException */ private BrowseInfo browseByItem(BrowserScope bs) throws BrowseException { log.info(LogManager.getHeader(context, "browse_by_item", "")); try { // get the table name that we are going to be getting our data from dao.setTable(browseIndex.getTableName()); // tell the browse query whether we are ascending or descending on the value dao.setAscending(scope.isAscending()); // assemble the value clause String rawValue = null; if (scope.hasFilterValue() && scope.isSecondLevel()) { String value = scope.getFilterValue(); rawValue = value; // make sure the incoming value is normalised value = OrderFormat.makeSortString( value, scope.getFilterValueLang(), scope.getBrowseIndex().getDataType()); dao.setAuthorityValue(scope.getAuthorityValue()); // set the values in the Browse Query if (scope.isSecondLevel()) { dao.setFilterValueField("value"); dao.setFilterValue(rawValue); } else { dao.setFilterValueField("sort_value"); dao.setFilterValue(value); } dao.setFilterValuePartial(scope.getFilterValuePartial()); // to apply the filtering, we need the distinct and map tables for the index dao.setFilterMappingTables( browseIndex.getDistinctTableName(), browseIndex.getMapTableName()); } // define a clause for the WHERE clause which will allow us to constrain // our browse to a specified community or collection if (scope.inCollection() || scope.inCommunity()) { if (scope.inCollection()) { Collection col = (Collection) scope.getBrowseContainer(); dao.setContainerTable("collection2item"); dao.setContainerIDField("collection_id"); dao.setContainerID(col.getID()); } else if (scope.inCommunity()) { Community com = (Community) scope.getBrowseContainer(); dao.setContainerTable("communities2item"); dao.setContainerIDField("community_id"); dao.setContainerID(com.getID()); } } // this is the total number of results in answer to the query int total = getTotalResults(); // assemble the ORDER BY clause String orderBy = browseIndex.getSortField(scope.isSecondLevel()); if (scope.getSortBy() > 0) { orderBy = "sort_" + Integer.toString(scope.getSortBy()); } dao.setOrderField(orderBy); int offset = scope.getOffset(); String rawFocusValue = null; if (offset < 1 && (scope.hasJumpToItem() || scope.hasJumpToValue() || scope.hasStartsWith())) { // We need to convert these to an offset for the actual browse query. // First, get a value that we can look up in the ordering field rawFocusValue = getJumpToValue(); // make sure the incoming value is normalised String focusValue = normalizeJumpToValue(rawFocusValue); log.debug("browsing using focus: " + focusValue); // Convert the focus value into an offset offset = getOffsetForValue(focusValue); } dao.setOffset(offset); // assemble the LIMIT clause dao.setLimit(scope.getResultsPerPage()); // Holder for the results List<BrowseItem> results = null; // Does this browse have any contents? if (total > 0) { // now run the query results = dao.doQuery(); // now, if we don't have any results, we are at the end of the browse. This will // be because a starts_with value has been supplied for which we don't have // any items. if (results.size() == 0) { // In this case, we will calculate a new offset for the last page of results offset = total - scope.getResultsPerPage(); if (offset < 0) { offset = 0; } // And rerun the query dao.setOffset(offset); results = dao.doQuery(); } } else { // No records, so make an empty list results = new ArrayList<BrowseItem>(); } // construct the BrowseInfo object to pass back // BrowseInfo browseInfo = new BrowseInfo(results, position, total, offset); BrowseInfo browseInfo = new BrowseInfo(results, offset, total, offset); if (offset + scope.getResultsPerPage() < total) { browseInfo.setNextOffset(offset + scope.getResultsPerPage()); } if (offset - scope.getResultsPerPage() > -1) { browseInfo.setPrevOffset(offset - scope.getResultsPerPage()); } // add the browse index to the Browse Info browseInfo.setBrowseIndex(browseIndex); // set the sort option for the Browse Info browseInfo.setSortOption(scope.getSortOption()); // tell the Browse Info which way we are sorting browseInfo.setAscending(scope.isAscending()); // tell the Browse Info which level of browse we are at browseInfo.setBrowseLevel(scope.getBrowseLevel()); // set the browse value if there is one browseInfo.setValue(rawValue); // set the browse authority key if there is one browseInfo.setAuthority(scope.getAuthorityValue()); // set the focus value if there is one browseInfo.setFocus(rawFocusValue); if (scope.hasJumpToItem()) { browseInfo.setFocusItem(scope.getJumpToItem()); } // tell the browse info if it is working from a starts with parameter browseInfo.setStartsWith(scope.hasStartsWith()); // tell the browse info what the container for the browse was if (scope.inCollection() || scope.inCommunity()) { browseInfo.setBrowseContainer(scope.getBrowseContainer()); } browseInfo.setResultsPerPage(scope.getResultsPerPage()); browseInfo.setEtAl(scope.getEtAl()); return browseInfo; } catch (SQLException e) { log.error("caught exception: ", e); throw new BrowseException(e); } }