From 7af7208f0d511e82b6f0ac2aadc7d53810e03a70 Mon Sep 17 00:00:00 2001 From: Chris Beer <cabeer@stanford.edu> Date: Fri, 14 Jun 2019 08:25:15 -0700 Subject: [PATCH] Poke the startIndex through to the search components that need it; part of #2684 --- .../src/components/SearchResults.test.js | 3 +- __tests__/src/selectors/searches.test.js | 31 +++++++++++++++++++ src/components/SearchPanelNavigation.js | 6 ++-- src/components/SearchResults.js | 5 ++- src/containers/SearchPanelNavigation.js | 2 ++ src/containers/SearchResults.js | 2 ++ src/state/selectors/searches.js | 28 ++++++++++++----- 7 files changed, 65 insertions(+), 12 deletions(-) diff --git a/__tests__/src/components/SearchResults.test.js b/__tests__/src/components/SearchResults.test.js index 400081c25..dcb477f83 100644 --- a/__tests__/src/components/SearchResults.test.js +++ b/__tests__/src/components/SearchResults.test.js @@ -20,6 +20,7 @@ function createWrapper(props) { match: 'moose', }, ]} + startIndex={10} {...props} />, ); @@ -30,7 +31,7 @@ describe('SearchResults', () => { const selectContentSearchAnnotation = jest.fn(); const wrapper = createWrapper({ selectContentSearchAnnotation }); expect(wrapper.find('Connect(WithStyles(WithPlugins(SearchHit)))').length).toEqual(1); - expect(wrapper.find('Connect(WithStyles(WithPlugins(SearchHit)))').prop('index')).toEqual(0); + expect(wrapper.find('Connect(WithStyles(WithPlugins(SearchHit)))').prop('index')).toEqual(10); }); it('can focus on a single item', () => { diff --git a/__tests__/src/selectors/searches.test.js b/__tests__/src/selectors/searches.test.js index 3e5fdde0c..c9b10342e 100644 --- a/__tests__/src/selectors/searches.test.js +++ b/__tests__/src/selectors/searches.test.js @@ -5,6 +5,7 @@ import { getSelectedContentSearchAnnotationIds, getSelectedContentSearchAnnotations, getSearchAnnotationsForCompanionWindow, + getSearchForCompanionWindow, } from '../../../src/state/selectors'; describe('getSearchResultsForWindow', () => { @@ -36,6 +37,36 @@ describe('getSearchResultsForWindow', () => { }); }); +describe('getSearchForCompanionWindow', () => { + const companionWindowId = 'cwid'; + it('returns the search data for a completed search', () => { + const state = { + searches: { + a: { + [companionWindowId]: { + json: { hits: [1, 2, 3] }, + }, + }, + b: { + [companionWindowId]: { + isFetching: true, + json: { }, + }, + }, + }, + }; + expect( + getSearchForCompanionWindow(state, { companionWindowId, windowId: 'a' }), + ).toEqual({ hits: [1, 2, 3] }); + expect( + getSearchForCompanionWindow(state, { companionWindowId, windowId: 'b' }), + ).toEqual({}); + expect( + getSearchForCompanionWindow({}, { companionWindowId, windowId: 'a' }), + ).toEqual({}); + }); +}); + describe('getSearchHitsForCompanionWindow', () => { const companionWindowId = 'cwid'; it('returns flattened hits for a manifest', () => { diff --git a/src/components/SearchPanelNavigation.js b/src/components/SearchPanelNavigation.js index 6b01ee592..17dd409f4 100644 --- a/src/components/SearchPanelNavigation.js +++ b/src/components/SearchPanelNavigation.js @@ -42,9 +42,9 @@ export class SearchPanelNavigation extends Component { */ render() { const { - searchHits, selectedContentSearchAnnotation, classes, t, + searchHits, selectedContentSearchAnnotation, classes, t, startIndex, } = this.props; - const currentHitIndex = searchHits + const currentHitIndex = startIndex + searchHits .findIndex(val => val.annotations.includes(selectedContentSearchAnnotation[0])); return ( <> @@ -79,11 +79,13 @@ SearchPanelNavigation.propTypes = { }).isRequired, selectContentSearchAnnotation: PropTypes.func.isRequired, selectedContentSearchAnnotation: PropTypes.arrayOf(PropTypes.string).isRequired, + startIndex: PropTypes.number, t: PropTypes.func, windowId: PropTypes.string.isRequired, }; SearchPanelNavigation.defaultProps = { classes: {}, searchHits: [], + startIndex: 0, t: key => key, }; diff --git a/src/components/SearchResults.js b/src/components/SearchResults.js index 6827d0f70..b205642db 100644 --- a/src/components/SearchResults.js +++ b/src/components/SearchResults.js @@ -30,6 +30,7 @@ export class SearchResults extends Component { const { classes, searchHits, + startIndex, t, windowId, } = this.props; @@ -53,7 +54,7 @@ export class SearchResults extends Component { key={hit.annotations[0]} focused={focused} hit={hit} - index={index} + index={startIndex + index} windowId={windowId} showDetails={this.toggleFocus} /> @@ -68,11 +69,13 @@ export class SearchResults extends Component { SearchResults.propTypes = { classes: PropTypes.objectOf(PropTypes.string), searchHits: PropTypes.arrayOf(PropTypes.object).isRequired, + startIndex: PropTypes.number, t: PropTypes.func, windowId: PropTypes.string.isRequired, // eslint-disable-line react/no-unused-prop-types }; SearchResults.defaultProps = { classes: {}, + startIndex: 0, t: k => k, }; diff --git a/src/containers/SearchPanelNavigation.js b/src/containers/SearchPanelNavigation.js index d806158df..6515d6c1e 100644 --- a/src/containers/SearchPanelNavigation.js +++ b/src/containers/SearchPanelNavigation.js @@ -8,6 +8,7 @@ import * as actions from '../state/actions'; import { getSearchHitsForCompanionWindow, getSelectedContentSearchAnnotationIds, + getSearchForCompanionWindow, } from '../state/selectors'; /** @@ -18,6 +19,7 @@ import { const mapStateToProps = (state, { companionWindowId, windowId }) => ({ searchHits: getSearchHitsForCompanionWindow(state, { companionWindowId, windowId }), selectedContentSearchAnnotation: getSelectedContentSearchAnnotationIds(state, { windowId }), + startIndex: getSearchForCompanionWindow(state, { companionWindowId, windowId }).startIndex, }); /** diff --git a/src/containers/SearchResults.js b/src/containers/SearchResults.js index 0ff458962..68f6dc458 100644 --- a/src/containers/SearchResults.js +++ b/src/containers/SearchResults.js @@ -8,6 +8,7 @@ import * as actions from '../state/actions'; import { getSearchHitsForCompanionWindow, getSelectedContentSearchAnnotationIds, + getSearchForCompanionWindow, } from '../state/selectors'; /** @@ -18,6 +19,7 @@ import { const mapStateToProps = (state, { companionWindowId, windowId }) => ({ searchHits: getSearchHitsForCompanionWindow(state, { companionWindowId, windowId }), selectedContentSearchAnnotation: getSelectedContentSearchAnnotationIds(state, { windowId }), + startIndex: getSearchForCompanionWindow(state, { companionWindowId, windowId }).startIndex, }); const mapDispatchToProps = { diff --git a/src/state/selectors/searches.js b/src/state/selectors/searches.js index 6ec183684..6ae506232 100644 --- a/src/state/selectors/searches.js +++ b/src/state/selectors/searches.js @@ -25,20 +25,30 @@ export const getSearchResultsForCompanionWindow = createSelector( }, ); -export const getSearchHitsForCompanionWindow = createSelector( +export const getSearchForCompanionWindow = createSelector( [ getSearchResultsForCompanionWindow, ], (result) => { - if (!result || !result.json || result.isFetching || !result.json.hits) return []; - return result.json.hits; + if (!result || !result.json || result.isFetching) return {}; + return result.json; + }, +); + +export const getSearchHitsForCompanionWindow = createSelector( + [ + getSearchForCompanionWindow, + ], + (result) => { + if (!result.hits) return []; + return result.hits; }, ); /** convert search results to an annotation */ -const searchResultsToAnnotation = (result) => { - if (!result || !result.json || result.isFetching || !result.json.resources) return undefined; - const anno = new Annotation(result.json); +const searchResultsToAnnotation = (json) => { + if (!json.resources) return undefined; + const anno = new Annotation(json); return { id: anno.id, resources: anno.resources, @@ -47,7 +57,7 @@ const searchResultsToAnnotation = (result) => { export const getSearchAnnotationsForCompanionWindow = createSelector( [ - getSearchResultsForCompanionWindow, + getSearchForCompanionWindow, ], result => searchResultsToAnnotation(result), ); @@ -58,7 +68,9 @@ export const getSearchAnnotationsForWindow = createSelector( ], (results) => { if (!results) return []; - const arr = Object.values(results).map(result => searchResultsToAnnotation(result)); + const arr = Object.values(results).map(result => ( + result && result.json && !result.isFetching && searchResultsToAnnotation(result.json) + )); return arr.filter(e => e); }, ); -- GitLab