@internetarchive/bookreader 5.0.0-8 → 5.0.0-80
Sign up to get free protection for your applications and to get access to all the features.
- package/.eslintrc.js +17 -15
- package/.github/workflows/node.js.yml +73 -10
- package/.github/workflows/npm-publish.yml +6 -20
- package/.testcaferc.js +10 -0
- package/BookReader/BookReader.css +398 -1133
- package/BookReader/BookReader.js +1 -1
- package/BookReader/BookReader.js.LICENSE.txt +20 -20
- package/BookReader/BookReader.js.map +1 -1
- package/BookReader/ia-bookreader-bundle.js +1782 -0
- package/BookReader/ia-bookreader-bundle.js.LICENSE.txt +7 -0
- package/BookReader/ia-bookreader-bundle.js.map +1 -0
- package/BookReader/icons/1up.svg +1 -1
- package/BookReader/icons/2up.svg +1 -1
- package/BookReader/icons/advance.svg +1 -1
- package/BookReader/icons/chevron-right.svg +1 -1
- package/BookReader/icons/close-circle-dark.svg +1 -1
- package/BookReader/icons/close-circle.svg +1 -1
- package/BookReader/icons/fullscreen.svg +1 -1
- package/BookReader/icons/fullscreen_exit.svg +1 -1
- package/BookReader/icons/hamburger.svg +1 -1
- package/BookReader/icons/left-arrow.svg +1 -1
- package/BookReader/icons/magnify-minus.svg +1 -1
- package/BookReader/icons/magnify-plus.svg +1 -1
- package/BookReader/icons/magnify.svg +1 -1
- package/BookReader/icons/pause.svg +1 -1
- package/BookReader/icons/play.svg +1 -1
- package/BookReader/icons/playback-speed.svg +1 -1
- package/BookReader/icons/read-aloud.svg +1 -1
- package/BookReader/icons/review.svg +1 -1
- package/BookReader/icons/thumbnails.svg +1 -1
- package/BookReader/icons/voice.svg +1 -0
- package/BookReader/icons/volume-full.svg +1 -1
- package/BookReader/images/BRicons.svg +3 -3
- package/BookReader/images/books_graphic.svg +1 -1
- package/BookReader/images/icon_book.svg +1 -1
- package/BookReader/images/icon_bookmark.svg +1 -1
- package/BookReader/images/icon_gear.svg +1 -1
- package/BookReader/images/icon_hamburger.svg +1 -1
- package/BookReader/images/icon_home.svg +1 -1
- package/BookReader/images/icon_info.svg +1 -1
- package/BookReader/images/icon_one_page.svg +1 -1
- package/BookReader/images/icon_pause.svg +1 -1
- package/BookReader/images/icon_play.svg +1 -1
- package/BookReader/images/icon_playback-rate.svg +1 -1
- package/BookReader/images/icon_search_button.svg +1 -1
- package/BookReader/images/icon_share.svg +1 -1
- package/BookReader/images/icon_skip-ahead.svg +1 -1
- package/BookReader/images/icon_skip-back.svg +1 -1
- package/BookReader/images/icon_speaker.svg +1 -1
- package/BookReader/images/icon_speaker_open.svg +1 -1
- package/BookReader/images/icon_thumbnails.svg +1 -1
- package/BookReader/images/icon_toc.svg +1 -1
- package/BookReader/images/icon_two_pages.svg +1 -1
- package/BookReader/images/marker_chap-off.svg +1 -1
- package/BookReader/images/marker_chap-on.svg +1 -1
- package/BookReader/images/marker_srch-on.svg +1 -1
- package/BookReader/jquery-3.js +2 -0
- package/BookReader/jquery-3.js.LICENSE.txt +24 -0
- package/BookReader/plugins/plugin.archive_analytics.js +1 -1
- package/BookReader/plugins/plugin.archive_analytics.js.map +1 -1
- package/BookReader/plugins/plugin.autoplay.js +1 -1
- package/BookReader/plugins/plugin.autoplay.js.map +1 -1
- package/BookReader/plugins/plugin.chapters.js +25 -1
- package/BookReader/plugins/plugin.chapters.js.LICENSE.txt +1 -0
- package/BookReader/plugins/plugin.chapters.js.map +1 -1
- package/BookReader/plugins/plugin.iframe.js +1 -1
- package/BookReader/plugins/plugin.iframe.js.map +1 -1
- package/BookReader/plugins/plugin.iiif.js +2 -0
- package/BookReader/plugins/plugin.iiif.js.map +1 -0
- package/BookReader/plugins/plugin.resume.js +1 -1
- package/BookReader/plugins/plugin.resume.js.map +1 -1
- package/BookReader/plugins/plugin.search.js +2 -1
- package/BookReader/plugins/plugin.search.js.LICENSE.txt +1 -0
- package/BookReader/plugins/plugin.search.js.map +1 -1
- package/BookReader/plugins/plugin.text_selection.js +2 -1
- package/BookReader/plugins/plugin.text_selection.js.LICENSE.txt +1 -0
- package/BookReader/plugins/plugin.text_selection.js.map +1 -1
- package/BookReader/plugins/plugin.tts.js +1 -1
- package/BookReader/plugins/plugin.tts.js.LICENSE.txt +2 -0
- package/BookReader/plugins/plugin.tts.js.map +1 -1
- package/BookReader/plugins/plugin.url.js +1 -1
- package/BookReader/plugins/plugin.url.js.map +1 -1
- package/BookReader/plugins/plugin.vendor-fullscreen.js +1 -1
- package/BookReader/plugins/plugin.vendor-fullscreen.js.map +1 -1
- package/BookReader/webcomponents-bundle.js +3 -0
- package/BookReader/webcomponents-bundle.js.LICENSE.txt +9 -0
- package/BookReader/webcomponents-bundle.js.map +1 -0
- package/BookReaderDemo/BookReaderDemo.css +18 -19
- package/BookReaderDemo/BookReaderJSAdvanced.js +0 -3
- package/BookReaderDemo/BookReaderJSAutoplay.js +4 -1
- package/BookReaderDemo/BookReaderJSSimple.js +1 -0
- package/BookReaderDemo/IADemoBr.js +147 -0
- package/BookReaderDemo/demo-advanced.html +2 -2
- package/BookReaderDemo/demo-autoplay.html +2 -3
- package/BookReaderDemo/demo-embed-iframe-src.html +2 -1
- package/BookReaderDemo/demo-fullscreen-mobile.html +3 -5
- package/BookReaderDemo/demo-fullscreen.html +2 -4
- package/BookReaderDemo/demo-iiif.html +99 -12
- package/BookReaderDemo/demo-internetarchive.html +214 -18
- package/BookReaderDemo/demo-multiple.html +2 -1
- package/BookReaderDemo/demo-preview-pages.html +2 -1
- package/BookReaderDemo/demo-simple.html +2 -1
- package/BookReaderDemo/demo-vendor-fullscreen.html +2 -4
- package/BookReaderDemo/ia-multiple-volumes-manifest.js +170 -0
- package/BookReaderDemo/immersion-1up.html +2 -2
- package/BookReaderDemo/immersion-mode.html +2 -4
- package/BookReaderDemo/toggle_controls.html +3 -2
- package/BookReaderDemo/view_mode.html +2 -1
- package/BookReaderDemo/viewmode-cycle.html +2 -3
- package/CHANGELOG.md +536 -33
- package/README.md +14 -1
- package/babel.config.js +20 -0
- package/codecov.yml +6 -0
- package/index.html +4 -1
- package/jsconfig.json +19 -0
- package/netlify.toml +9 -0
- package/package.json +70 -60
- package/renovate.json +52 -0
- package/scripts/preversion.js +0 -1
- package/src/BookNavigator/assets/bookmark-colors.js +1 -1
- package/src/BookNavigator/assets/button-base.js +4 -2
- package/src/BookNavigator/assets/ia-logo.js +17 -0
- package/src/BookNavigator/assets/icon_checkmark.js +1 -1
- package/src/BookNavigator/assets/icon_close.js +1 -1
- package/src/BookNavigator/book-navigator.js +590 -0
- package/src/BookNavigator/bookmarks/bookmark-button.js +3 -2
- package/src/BookNavigator/bookmarks/bookmark-edit.js +3 -4
- package/src/BookNavigator/bookmarks/bookmarks-list.js +2 -3
- package/src/BookNavigator/bookmarks/bookmarks-loginCTA.js +3 -8
- package/src/BookNavigator/bookmarks/bookmarks-provider.js +27 -17
- package/src/BookNavigator/bookmarks/ia-bookmarks.js +116 -67
- package/src/BookNavigator/delete-modal-actions.js +1 -1
- package/src/BookNavigator/downloads/downloads-provider.js +36 -21
- package/src/BookNavigator/downloads/downloads.js +41 -25
- package/src/BookNavigator/search/search-provider.js +49 -27
- package/src/BookNavigator/search/search-results.js +23 -9
- package/src/BookNavigator/sharing.js +27 -0
- package/src/BookNavigator/viewable-files.js +95 -0
- package/src/BookNavigator/visual-adjustments/visual-adjustments-provider.js +11 -10
- package/src/BookNavigator/visual-adjustments/visual-adjustments.js +3 -3
- package/src/BookReader/BookModel.js +64 -34
- package/src/BookReader/DragScrollable.js +233 -0
- package/src/BookReader/Mode1Up.js +56 -351
- package/src/BookReader/Mode1UpLit.js +388 -0
- package/src/BookReader/Mode2Up.js +73 -1318
- package/src/BookReader/Mode2UpLit.js +776 -0
- package/src/BookReader/ModeCoordinateSpace.js +29 -0
- package/src/BookReader/ModeSmoothZoom.js +312 -0
- package/src/BookReader/ModeThumb.js +18 -12
- package/src/BookReader/Navbar/Navbar.js +14 -40
- package/src/BookReader/PageContainer.js +81 -6
- package/src/BookReader/ReduceSet.js +1 -1
- package/src/BookReader/Toolbar/Toolbar.js +10 -37
- package/src/BookReader/events.js +2 -3
- package/src/BookReader/options.js +27 -2
- package/src/BookReader/utils/HTMLDimensionsCacher.js +44 -0
- package/src/BookReader/utils/ScrollClassAdder.js +31 -0
- package/src/BookReader/utils/SelectionObserver.js +45 -0
- package/src/BookReader/utils.js +118 -13
- package/src/BookReader.js +427 -1061
- package/src/assets/icons/magnify-minus.svg +3 -7
- package/src/assets/icons/magnify-plus.svg +3 -7
- package/src/assets/icons/voice.svg +1 -0
- package/src/css/BookReader.scss +1 -5
- package/src/css/_BRBookmarks.scss +1 -1
- package/src/css/_BRComponent.scss +1 -1
- package/src/css/_BRmain.scss +16 -3
- package/src/css/_BRnav.scss +12 -39
- package/src/css/_BRpages.scss +149 -40
- package/src/css/_BRsearch.scss +68 -25
- package/src/css/_BRtoolbar.scss +5 -5
- package/src/css/_TextSelection.scss +87 -27
- package/src/css/_colorbox.scss +2 -2
- package/src/css/_controls.scss +20 -7
- package/src/css/_icons.scss +1 -1
- package/src/ia-bookreader/ia-bookreader.js +224 -0
- package/src/plugins/plugin.archive_analytics.js +3 -3
- package/src/plugins/plugin.autoplay.js +5 -11
- package/src/plugins/plugin.chapters.js +237 -191
- package/src/plugins/plugin.iiif.js +151 -0
- package/src/plugins/plugin.resume.js +3 -3
- package/src/plugins/plugin.text_selection.js +464 -134
- package/src/plugins/plugin.vendor-fullscreen.js +4 -4
- package/src/plugins/search/plugin.search.js +142 -125
- package/src/plugins/search/utils.js +43 -0
- package/src/plugins/search/view.js +33 -58
- package/src/plugins/tts/AbstractTTSEngine.js +71 -40
- package/src/plugins/tts/FestivalTTSEngine.js +13 -14
- package/src/plugins/tts/PageChunk.js +15 -21
- package/src/plugins/tts/PageChunkIterator.js +8 -12
- package/src/plugins/tts/WebTTSEngine.js +87 -71
- package/src/plugins/tts/plugin.tts.js +96 -127
- package/src/plugins/tts/utils.js +15 -25
- package/src/plugins/url/UrlPlugin.js +191 -0
- package/src/plugins/{plugin.url.js → url/plugin.url.js} +45 -16
- package/src/util/browserSniffing.js +22 -0
- package/src/util/docCookies.js +21 -2
- package/tests/e2e/README.md +37 -0
- package/tests/e2e/autoplay.test.js +2 -2
- package/tests/e2e/base.test.js +8 -16
- package/tests/e2e/helpers/base.js +53 -48
- package/tests/e2e/helpers/debug.js +1 -1
- package/tests/e2e/helpers/params.js +17 -0
- package/tests/e2e/helpers/rightToLeft.js +8 -14
- package/tests/e2e/helpers/search.js +73 -0
- package/tests/e2e/models/Navigation.js +20 -37
- package/tests/e2e/rightToLeft.test.js +4 -5
- package/tests/e2e/viewmode.test.js +40 -33
- package/tests/jest/BookNavigator/book-navigator.test.js +661 -0
- package/tests/jest/BookNavigator/bookmarks/bookmark-button.test.js +43 -0
- package/tests/{karma → jest}/BookNavigator/bookmarks/bookmark-edit.test.js +25 -26
- package/tests/{karma → jest}/BookNavigator/bookmarks/bookmarks-list.test.js +41 -42
- package/tests/jest/BookNavigator/bookmarks/ia-bookmarks.test.js +45 -0
- package/tests/jest/BookNavigator/downloads/downloads-provider.test.js +67 -0
- package/tests/jest/BookNavigator/downloads/downloads.test.js +53 -0
- package/tests/jest/BookNavigator/search/search-provider.test.js +167 -0
- package/tests/{karma → jest}/BookNavigator/search/search-results.test.js +109 -60
- package/tests/jest/BookNavigator/sharing/sharing-provider.test.js +49 -0
- package/tests/jest/BookNavigator/viewable-files/viewable-files-provider.test.js +80 -0
- package/tests/jest/BookNavigator/visual-adjustments.test.js +200 -0
- package/tests/{BookReader → jest/BookReader}/BookModel.test.js +74 -14
- package/tests/jest/BookReader/BookReaderPublicFunctions.test.js +193 -0
- package/tests/{BookReader → jest/BookReader}/ImageCache.test.js +4 -4
- package/tests/jest/BookReader/Mode1UpLit.test.js +73 -0
- package/tests/jest/BookReader/Mode2Up.test.js +98 -0
- package/tests/jest/BookReader/Mode2UpLit.test.js +190 -0
- package/tests/jest/BookReader/ModeCoordinateSpace.test.js +16 -0
- package/tests/jest/BookReader/ModeSmoothZoom.test.js +218 -0
- package/tests/jest/BookReader/ModeThumb.test.js +71 -0
- package/tests/{BookReader → jest/BookReader}/Navbar/Navbar.test.js +10 -10
- package/tests/{BookReader → jest/BookReader}/PageContainer.test.js +88 -6
- package/tests/{BookReader → jest/BookReader}/ReduceSet.test.js +1 -1
- package/tests/{BookReader → jest/BookReader}/Toolbar/Toolbar.test.js +2 -2
- package/tests/jest/BookReader/utils/HTMLDimensionsCacher.test.js +59 -0
- package/tests/jest/BookReader/utils/ScrollClassAdder.test.js +49 -0
- package/tests/jest/BookReader/utils/SelectionObserver.test.js +57 -0
- package/tests/{BookReader → jest/BookReader}/utils/classes.test.js +1 -1
- package/tests/jest/BookReader/utils.test.js +229 -0
- package/tests/jest/BookReader.keyboard.test.js +190 -0
- package/tests/{BookReader.options.test.js → jest/BookReader.options.test.js} +9 -1
- package/tests/{BookReader.test.js → jest/BookReader.test.js} +26 -37
- package/tests/{plugins → jest/plugins}/plugin.archive_analytics.test.js +2 -2
- package/tests/{plugins → jest/plugins}/plugin.autoplay.test.js +4 -4
- package/tests/jest/plugins/plugin.chapters.test.js +195 -0
- package/tests/{plugins → jest/plugins}/plugin.iframe.test.js +2 -2
- package/tests/{plugins → jest/plugins}/plugin.resume.test.js +3 -3
- package/tests/jest/plugins/plugin.text_selection.test.js +317 -0
- package/tests/{plugins → jest/plugins}/plugin.vendor-fullscreen.test.js +2 -2
- package/tests/{plugins → jest/plugins}/search/plugin.search.test.js +25 -47
- package/tests/{plugins → jest/plugins}/search/plugin.search.view.test.js +39 -6
- package/tests/jest/plugins/search/utils.js +25 -0
- package/tests/jest/plugins/search/utils.test.js +29 -0
- package/tests/{plugins → jest/plugins}/tts/AbstractTTSEngine.test.js +29 -9
- package/tests/{plugins → jest/plugins}/tts/FestivalTTSEngine.test.js +4 -4
- package/tests/{plugins → jest/plugins}/tts/PageChunk.test.js +1 -1
- package/tests/{plugins → jest/plugins}/tts/PageChunkIterator.test.js +3 -3
- package/tests/{plugins → jest/plugins}/tts/WebTTSEngine.test.js +47 -1
- package/tests/{plugins → jest/plugins}/tts/utils.test.js +1 -60
- package/tests/jest/plugins/url/UrlPlugin.test.js +198 -0
- package/tests/{plugins → jest/plugins/url}/plugin.url.test.js +53 -14
- package/tests/jest/setup.js +3 -0
- package/tests/{util → jest/util}/browserSniffing.test.js +1 -1
- package/tests/jest/util/docCookies.test.js +24 -0
- package/tests/{util → jest/util}/strings.test.js +1 -1
- package/tests/{utils.js → jest/utils.js} +38 -0
- package/webpack.config.js +12 -6
- package/.babelrc +0 -12
- package/.dependabot/config.yml +0 -6
- package/.testcaferc.json +0 -5
- package/BookReader/bookreader-component-bundle.js +0 -1450
- package/BookReader/bookreader-component-bundle.js.LICENSE.txt +0 -38
- package/BookReader/bookreader-component-bundle.js.map +0 -1
- package/BookReader/jquery-1.10.1.js +0 -2
- package/BookReader/jquery-1.10.1.js.LICENSE.txt +0 -24
- package/BookReader/plugins/plugin.menu_toggle.js +0 -2
- package/BookReader/plugins/plugin.menu_toggle.js.map +0 -1
- package/BookReader/plugins/plugin.mobile_nav.js +0 -2
- package/BookReader/plugins/plugin.mobile_nav.js.map +0 -1
- package/BookReaderDemo/IIIFBookReader.js +0 -207
- package/BookReaderDemo/bookreader-template-bundle.js +0 -7178
- package/BookReaderDemo/demo-iiif.js +0 -26
- package/BookReaderDemo/demo-plugin-menu-toggle.html +0 -34
- package/karma.conf.js +0 -23
- package/src/BookNavigator/BookModel.js +0 -14
- package/src/BookNavigator/BookNavigator.js +0 -446
- package/src/BookNavigator/assets/book-loader.js +0 -27
- package/src/BookNavigator/br-fullscreen-mgr.js +0 -83
- package/src/BookNavigator/search/a-search-result.js +0 -55
- package/src/BookReader/DebugConsole.js +0 -54
- package/src/BookReaderComponent/BookReaderComponent.js +0 -112
- package/src/ItemNavigator/ItemNavigator.js +0 -376
- package/src/ItemNavigator/providers/sharing.js +0 -29
- package/src/css/_MobileNav.scss +0 -194
- package/src/dragscrollable-br.js +0 -261
- package/src/lit-wrapper.js +0 -2
- package/src/plugins/menu_toggle/plugin.menu_toggle.js +0 -324
- package/src/plugins/plugin.mobile_nav.js +0 -287
- package/tests/BookReader/BookReaderPublicFunctions.test.js +0 -171
- package/tests/BookReader/DebugConsole.test.js +0 -25
- package/tests/BookReader/Mode1Up.test.js +0 -164
- package/tests/BookReader/Mode2Up.test.js +0 -247
- package/tests/BookReader/utils.test.js +0 -109
- package/tests/e2e/helpers/desktopSearch.js +0 -72
- package/tests/e2e/helpers/mobileSearch.js +0 -85
- package/tests/e2e/ia-production/ia-prod-base.js +0 -17
- package/tests/karma/BookNavigator/book-navigator.test.js +0 -132
- package/tests/karma/BookNavigator/search/search-provider.test.js +0 -23
- package/tests/karma/BookNavigator/visual-adjustments.test.js +0 -201
- package/tests/plugins/menu_toggle/plugin.menu_toggle.test.js +0 -68
- package/tests/plugins/plugin.chapters.test.js +0 -130
- package/tests/plugins/plugin.mobile_nav.test.js +0 -66
- package/tests/plugins/plugin.text_selection.test.js +0 -203
- package/tests/util/docCookies.test.js +0 -15
@@ -0,0 +1,167 @@
|
|
1
|
+
import { fixtureCleanup, fixtureSync } from '@open-wc/testing-helpers';
|
2
|
+
import sinon from 'sinon';
|
3
|
+
import searchProvider from '@/src/BookNavigator/search/search-provider';
|
4
|
+
|
5
|
+
afterEach(() => {
|
6
|
+
sinon.restore();
|
7
|
+
fixtureCleanup();
|
8
|
+
});
|
9
|
+
|
10
|
+
describe('Search Provider', () => {
|
11
|
+
describe('constructor', () => {
|
12
|
+
const provider = new searchProvider({
|
13
|
+
onProviderChange: sinon.fake(),
|
14
|
+
bookreader: {}
|
15
|
+
});
|
16
|
+
|
17
|
+
expect(provider.bookreader).toBeDefined();
|
18
|
+
expect(provider.onProviderChange).toBeDefined();
|
19
|
+
expect(provider.id).toEqual('search');
|
20
|
+
expect(provider.icon).toBeDefined();
|
21
|
+
expect(fixtureSync(provider.icon).tagName).toEqual('IA-ICON-SEARCH');
|
22
|
+
expect(provider.label).toEqual('Search inside');
|
23
|
+
expect(provider.menuDetails).toBeDefined();
|
24
|
+
expect(provider.component).toBeDefined();
|
25
|
+
});
|
26
|
+
describe('Search request life cycles', () => {
|
27
|
+
test('Event: catches `BookReader:SearchStarted`', async() => {
|
28
|
+
const provider = new searchProvider({
|
29
|
+
onProviderChange: sinon.fake(),
|
30
|
+
bookreader: {}
|
31
|
+
});
|
32
|
+
sinon.spy(provider, 'updateMenu');
|
33
|
+
window.dispatchEvent(new CustomEvent('BookReader:SearchStarted', { detail: { props: { term: 'foo' }}}));
|
34
|
+
expect(provider.updateMenu.callCount).toEqual(1);
|
35
|
+
});
|
36
|
+
test('Event: catches `BookReader:SearchCallback`', async() => {
|
37
|
+
const provider = new searchProvider({
|
38
|
+
onProviderChange: sinon.fake(),
|
39
|
+
bookreader: {}
|
40
|
+
});
|
41
|
+
sinon.spy(provider, 'updateMenu');
|
42
|
+
const brStub = {};
|
43
|
+
window.dispatchEvent(new CustomEvent('BookReader:SearchCallback', { detail: { props: { instance: brStub, results: { matches: []} }}}));
|
44
|
+
expect(provider.updateMenu.callCount).toEqual(1);
|
45
|
+
expect(provider.bookreader).toEqual(brStub);
|
46
|
+
});
|
47
|
+
test('Event: catches `BookReader:SearchCallbackEmpty`', async() => {
|
48
|
+
const provider = new searchProvider({
|
49
|
+
onProviderChange: sinon.fake(),
|
50
|
+
bookreader: {}
|
51
|
+
});
|
52
|
+
sinon.spy(provider, 'onSearchRequestError');
|
53
|
+
sinon.spy(provider, 'updateMenu');
|
54
|
+
const brStub = {};
|
55
|
+
window.dispatchEvent(new CustomEvent('BookReader:SearchCallbackEmpty', { detail: { props: { instance: brStub }}}));
|
56
|
+
expect(provider.onSearchRequestError.getCall(0).args[1]).toEqual('noResults');
|
57
|
+
expect(provider.updateMenu.callCount).toEqual(1);
|
58
|
+
expect(provider.bookreader).toEqual(brStub);
|
59
|
+
});
|
60
|
+
test('Event: catches `BookReader:SearchCallbackNotIndexed`', async() => {
|
61
|
+
const provider = new searchProvider({
|
62
|
+
onProviderChange: sinon.fake(),
|
63
|
+
bookreader: {}
|
64
|
+
});
|
65
|
+
const brStub = {};
|
66
|
+
sinon.spy(provider, 'onSearchRequestError');
|
67
|
+
sinon.spy(provider, 'updateMenu');
|
68
|
+
window.dispatchEvent(new CustomEvent('BookReader:SearchCallbackNotIndexed', { detail: { props: { instance: brStub }}}));
|
69
|
+
expect(provider.onSearchRequestError.getCall(0).args[1]).toEqual('notIndexed');
|
70
|
+
expect(provider.updateMenu.callCount).toEqual(1);
|
71
|
+
expect(provider.bookreader).toEqual(brStub);
|
72
|
+
});
|
73
|
+
test('Event: catches `BookReader:SearchCallbackError`', async() => {
|
74
|
+
const provider = new searchProvider({
|
75
|
+
onProviderChange: sinon.fake(),
|
76
|
+
bookreader: {}
|
77
|
+
});
|
78
|
+
sinon.spy(provider, 'onSearchRequestError');
|
79
|
+
sinon.spy(provider, 'updateMenu');
|
80
|
+
const brStub = {};
|
81
|
+
window.dispatchEvent(new CustomEvent('BookReader:SearchCallbackError', { detail: { props: { instance: brStub }}}));
|
82
|
+
expect(provider.onSearchRequestError.getCall(0).args[1]).toEqual(undefined);
|
83
|
+
expect(provider.updateMenu.callCount).toEqual(1);
|
84
|
+
expect(provider.bookreader).toEqual(brStub);
|
85
|
+
});
|
86
|
+
test('Event: catches `component@resultSelected` - user clicks result in side panel - & turns page', async() => {
|
87
|
+
const provider = new searchProvider({
|
88
|
+
onProviderChange: sinon.fake(),
|
89
|
+
bookreader: {
|
90
|
+
leafNumToIndex: sinon.fake(),
|
91
|
+
_searchPluginGoToResult: sinon.fake()
|
92
|
+
}
|
93
|
+
});
|
94
|
+
|
95
|
+
const searchResultStub = {
|
96
|
+
match: { par: [{ text: 'foo', page: 3 }] },
|
97
|
+
};
|
98
|
+
fixtureSync(provider.component).dispatchEvent(
|
99
|
+
new CustomEvent('resultSelected',
|
100
|
+
{ detail: searchResultStub })
|
101
|
+
);
|
102
|
+
|
103
|
+
expect(provider.bookreader._searchPluginGoToResult.callCount).toEqual(1);
|
104
|
+
});
|
105
|
+
test('update url when search is cancelled or input cleared', async() => {
|
106
|
+
const urlPluginMock = {
|
107
|
+
pullFromAddressBar: sinon.fake(),
|
108
|
+
removeUrlParam: sinon.fake()
|
109
|
+
};
|
110
|
+
const provider = new searchProvider({
|
111
|
+
onProviderChange: sinon.fake(),
|
112
|
+
bookreader: {
|
113
|
+
leafNumToIndex: sinon.fake(),
|
114
|
+
_searchPluginGoToResult: sinon.fake(),
|
115
|
+
urlPlugin: urlPluginMock
|
116
|
+
}
|
117
|
+
});
|
118
|
+
|
119
|
+
provider.onSearchCanceled();
|
120
|
+
await provider.updateComplete;
|
121
|
+
|
122
|
+
expect(urlPluginMock.pullFromAddressBar.callCount).toEqual(1);
|
123
|
+
expect(urlPluginMock.removeUrlParam.callCount).toEqual(1);
|
124
|
+
|
125
|
+
provider.onSearchCanceled();
|
126
|
+
await provider.updateComplete;
|
127
|
+
|
128
|
+
expect(urlPluginMock.pullFromAddressBar.callCount).toEqual(2);
|
129
|
+
expect(urlPluginMock.removeUrlParam.callCount).toEqual(2);
|
130
|
+
});
|
131
|
+
it('updateSearchInUrl', async () => {
|
132
|
+
let fieldToSet;
|
133
|
+
let valueOfFieldToSet;
|
134
|
+
let setUrlParamCalled = false;
|
135
|
+
const urlPluginMock = {
|
136
|
+
pullFromAddressBar: sinon.fake(),
|
137
|
+
removeUrlParam: sinon.fake(),
|
138
|
+
setUrlParam: (field, val) => {
|
139
|
+
fieldToSet = field;
|
140
|
+
valueOfFieldToSet = val;
|
141
|
+
setUrlParamCalled = true;
|
142
|
+
}
|
143
|
+
};
|
144
|
+
const provider = new searchProvider({
|
145
|
+
onProviderChange: sinon.fake(),
|
146
|
+
bookreader: {
|
147
|
+
leafNumToIndex: sinon.fake(),
|
148
|
+
_searchPluginGoToResult: sinon.fake(),
|
149
|
+
urlPlugin: urlPluginMock,
|
150
|
+
search: sinon.fake()
|
151
|
+
}
|
152
|
+
});
|
153
|
+
|
154
|
+
const searchInitiatedEvent = new CustomEvent('bookSearchInitiated', { detail: { query: 'foobar' } });
|
155
|
+
// set initial seachState with a query
|
156
|
+
provider.onBookSearchInitiated(searchInitiatedEvent);
|
157
|
+
await provider.updateComplete;
|
158
|
+
// checking this fn:
|
159
|
+
provider.updateSearchInUrl();
|
160
|
+
await provider.updateComplete;
|
161
|
+
|
162
|
+
expect(fieldToSet).toEqual('q');
|
163
|
+
expect(valueOfFieldToSet).toEqual('foobar');
|
164
|
+
expect(setUrlParamCalled).toBe(true);
|
165
|
+
});
|
166
|
+
});
|
167
|
+
});
|
@@ -1,24 +1,23 @@
|
|
1
1
|
import {
|
2
2
|
html,
|
3
3
|
fixture,
|
4
|
-
expect,
|
5
4
|
oneEvent,
|
6
|
-
} from '@open-wc/testing';
|
5
|
+
} from '@open-wc/testing-helpers';
|
7
6
|
import sinon from 'sinon';
|
8
|
-
import { IABookSearchResults } from '
|
7
|
+
import { IABookSearchResults } from '@/src/BookNavigator/search/search-results.js';
|
8
|
+
import { marshallSearchResults } from '@/src/plugins/search/utils.js';
|
9
9
|
|
10
10
|
const container = (results = [], query = '') => (
|
11
11
|
html`<ia-book-search-results .results=${results} .query=${query}></ia-book-search-results>`
|
12
12
|
);
|
13
13
|
|
14
|
-
console.log("ia-book-search-results-test")
|
15
|
-
|
16
14
|
const searchQuery = 'Bristol';
|
17
15
|
|
18
16
|
const results = [{
|
19
17
|
text: `In the drawing of caricatures and cartoons\u2014or any other com' mercial art, for that matter\u2014the artist should know something about the processes of reproduction for that particular form of art work. For pen and ink work the engraving is made on a sine printing plate. It is not necessary, however, to know all about these processes of reproduction. The artist should know that all work intended for line rqproducttons should be made on white paper or {{{${searchQuery}}}} Board with black drawing ink. The drawing to be reproduced is photographed on a chemically treated sine plate, which is then treated with acid. This acid eats away the surface of the sine, except the photographed' lines, which are left in relief, somewhat like printing type. Colored inks do not photograph well; neither does black ink on colored paper.`,
|
20
18
|
cover: '//placehold.it/30x44',
|
21
19
|
title: 'Book title',
|
20
|
+
displayPageNumber: 'Page 24',
|
22
21
|
par: [{
|
23
22
|
boxes: [{
|
24
23
|
r: 2672, b: 792, t: 689, page: 24, l: 2424,
|
@@ -33,6 +32,7 @@ const results = [{
|
|
33
32
|
}],
|
34
33
|
}, {
|
35
34
|
text: `Drawings intended for sale should be made on a good grade of {{{${searchQuery}}}} Board, and a margin left all the way around the drawings. They should be mailed flat, and'require first class postage. Enclose postage for the return of the drawings. Only send good drawings of a reason- able quantity. Enclose a neat and terse letter to the one you are sending the drawings to, written with pen and ink or typewriter if possible, on`,
|
35
|
+
displayPageNumber: 'Page 86',
|
36
36
|
par: [{
|
37
37
|
boxes: [{
|
38
38
|
r: 698, b: 4460, t: 4324, page: 86, l: 450,
|
@@ -44,72 +44,108 @@ const results = [{
|
|
44
44
|
l: 432,
|
45
45
|
page_height: 5357,
|
46
46
|
page: 86,
|
47
|
+
}]
|
48
|
+
}];
|
49
|
+
|
50
|
+
marshallSearchResults({ matches: results }, () => '', '{{{', '}}}');
|
51
|
+
|
52
|
+
const resultWithScript = [{
|
53
|
+
text: `foo bar <script>const msg = 'test' + ' failure'; document.write(msg);</script> {{{${searchQuery}}}} baz`,
|
54
|
+
cover: '//placehold.it/30x44',
|
55
|
+
title: 'Book title',
|
56
|
+
displayPageNumber: 'Page 24',
|
57
|
+
par: [{
|
58
|
+
boxes: [{
|
59
|
+
r: 2672, b: 792, t: 689, page: 24, l: 2424,
|
60
|
+
}],
|
61
|
+
b: 1371,
|
62
|
+
t: 689,
|
63
|
+
page_width: 3658,
|
64
|
+
r: 3192,
|
65
|
+
l: 428,
|
66
|
+
page_height: 5357,
|
67
|
+
page: 24,
|
47
68
|
}],
|
48
69
|
}];
|
49
70
|
|
71
|
+
marshallSearchResults({ matches: resultWithScript }, () => '', '{{{', '}}}');
|
72
|
+
|
50
73
|
describe('<ia-book-search-results>', () => {
|
51
74
|
afterEach(() => {
|
52
75
|
sinon.restore();
|
53
76
|
});
|
54
77
|
|
55
|
-
|
78
|
+
test('sets default properties', async () => {
|
56
79
|
const query = 'bristol';
|
57
80
|
const el = await fixture(container(results, query));
|
58
81
|
|
59
|
-
expect(el.results).
|
60
|
-
expect(el.query).
|
82
|
+
expect(el.results).toEqual(results);
|
83
|
+
expect(el.query).toEqual(query);
|
61
84
|
});
|
62
85
|
|
63
|
-
|
86
|
+
test('sets results when passed in via event object', async () => {
|
64
87
|
const el = await fixture(container());
|
65
88
|
|
66
89
|
el.setResults({ detail: { results } });
|
67
|
-
expect(el.results).
|
90
|
+
expect(el.results).toEqual(results);
|
68
91
|
});
|
69
92
|
|
70
|
-
|
93
|
+
test('listens for a custom search callback event on the document', async () => {
|
71
94
|
IABookSearchResults.prototype.setResults = sinon.fake();
|
72
95
|
const el = await fixture(container());
|
73
96
|
const event = new Event('BookReader:SearchCallback');
|
74
97
|
|
75
98
|
event.detail = { results };
|
76
99
|
document.dispatchEvent(event);
|
77
|
-
expect(el.setResults.callCount).
|
78
|
-
expect(el.setResults.firstArg).
|
100
|
+
expect(el.setResults.callCount).toEqual(1);
|
101
|
+
expect(el.setResults.firstArg).toEqual(event);
|
79
102
|
});
|
80
103
|
|
81
|
-
|
104
|
+
test('renders results that contain the book title', async () => {
|
82
105
|
sinon.replace(IABookSearchResults.prototype, 'createRenderRoot', function createRenderRoot() { return this; });
|
83
106
|
const el = await fixture(container(results));
|
84
107
|
|
85
|
-
expect(el.innerHTML).
|
108
|
+
expect(el.innerHTML).toContain(`${results[0].title}`);
|
86
109
|
});
|
87
110
|
|
88
|
-
|
111
|
+
test('renders results that contain a highlighted match', async () => {
|
89
112
|
sinon.replace(IABookSearchResults.prototype, 'createRenderRoot', function createRenderRoot() { return this; });
|
90
113
|
const el = await fixture(container(results));
|
91
114
|
|
92
|
-
|
115
|
+
// Lit inserts HTML comments that inhibit searching for exact innerHTML matches.
|
116
|
+
// So query the DOM for the match instead.
|
117
|
+
const match = el.querySelector('mark');
|
118
|
+
expect(match?.textContent).toEqual(searchQuery);
|
93
119
|
});
|
94
120
|
|
95
|
-
|
121
|
+
test('renders results that contain sanitized HTML tags', async () => {
|
122
|
+
sinon.replace(IABookSearchResults.prototype, 'createRenderRoot', function createRenderRoot() { return this; });
|
123
|
+
// A result whose text contains a <script> tag that will insert 'test failure' into the element if not sanitized
|
124
|
+
const el = await fixture(container(resultWithScript));
|
125
|
+
|
126
|
+
const match = el.querySelector('mark');
|
127
|
+
expect(match?.textContent).toEqual(searchQuery);
|
128
|
+
expect(el.innerHTML).not.toContain('test failure');
|
129
|
+
});
|
130
|
+
|
131
|
+
test('renders results that contain an optional cover image', async () => {
|
96
132
|
sinon.replace(IABookSearchResults.prototype, 'createRenderRoot', function createRenderRoot() { return this; });
|
97
133
|
const el = await fixture(container(results));
|
98
134
|
|
99
|
-
expect(el.innerHTML).
|
135
|
+
expect(el.innerHTML).toContain(`<img src="${results[0].cover}">`);
|
100
136
|
});
|
101
137
|
|
102
|
-
|
138
|
+
test('sets a query prop when search input receives input', async () => {
|
103
139
|
const el = await fixture(container(results));
|
104
140
|
const searchInput = el.shadowRoot.querySelector('[name="query"]');
|
105
141
|
|
106
142
|
searchInput.value = searchQuery;
|
107
143
|
searchInput.dispatchEvent(new Event('keyup'));
|
108
144
|
|
109
|
-
expect(el.query).
|
145
|
+
expect(el.query).toEqual(searchQuery);
|
110
146
|
});
|
111
147
|
|
112
|
-
|
148
|
+
test('emits a custom event when search form submitted when input is populated', async () => {
|
113
149
|
const el = await fixture(container(results));
|
114
150
|
|
115
151
|
setTimeout(() => {
|
@@ -119,122 +155,135 @@ describe('<ia-book-search-results>', () => {
|
|
119
155
|
});
|
120
156
|
const response = await oneEvent(el, 'bookSearchInitiated');
|
121
157
|
|
122
|
-
expect(response).
|
158
|
+
expect(response).toBeDefined();
|
123
159
|
});
|
124
160
|
|
125
|
-
|
161
|
+
test('uses a singular noun when one result given', async () => {
|
126
162
|
const el = await fixture(container([results[0]]));
|
127
163
|
const resultsCount = await fixture(el.resultsCount);
|
128
164
|
|
129
|
-
expect(resultsCount.innerHTML).
|
165
|
+
expect(resultsCount.innerHTML).toContain('1 result');
|
130
166
|
});
|
131
167
|
|
132
|
-
|
168
|
+
test('can render header with active options count', async () => {
|
133
169
|
const el = await fixture(container(results));
|
134
170
|
el.renderHeader = true;
|
135
171
|
|
136
172
|
await el.updateComplete;
|
137
173
|
|
138
|
-
expect(el.shadowRoot.querySelector('header p').
|
174
|
+
expect(el.shadowRoot.querySelector('header p').textContent).toContain('2');
|
139
175
|
});
|
140
176
|
|
141
|
-
|
177
|
+
test('renders search all files checkbox when enabled', async () => {
|
142
178
|
const el = await fixture(container(results));
|
143
179
|
el.renderSearchAllFiles = true;
|
144
180
|
|
145
181
|
await el.updateComplete;
|
146
182
|
|
147
|
-
expect(el.shadowRoot.querySelector('[name="all_files"]')).
|
183
|
+
expect(el.shadowRoot.querySelector('[name="all_files"]')).not.toBeNull();
|
148
184
|
});
|
149
185
|
|
150
|
-
|
186
|
+
test('emits a resultSelected event when a search result is clicked', async () => {
|
151
187
|
const el = await fixture(container(results));
|
152
188
|
|
153
189
|
setTimeout(() => (
|
154
|
-
el.shadowRoot.querySelector('
|
190
|
+
el.shadowRoot.querySelector('li').click()
|
155
191
|
));
|
156
192
|
const response = await oneEvent(el, 'resultSelected');
|
157
193
|
|
158
|
-
expect(response).
|
194
|
+
expect(response).toBeDefined();
|
159
195
|
});
|
160
196
|
|
161
|
-
|
197
|
+
test('emits a closeMenu event when a search result is clicked', async () => {
|
162
198
|
const el = await fixture(container(results));
|
163
199
|
|
164
200
|
setTimeout(() => (
|
165
|
-
el.shadowRoot.querySelector('
|
201
|
+
el.shadowRoot.querySelector('li').click()
|
166
202
|
));
|
167
203
|
const response = await oneEvent(el, 'closeMenu');
|
168
204
|
|
169
|
-
expect(response).
|
205
|
+
expect(response).toBeDefined();
|
170
206
|
});
|
171
207
|
|
172
208
|
describe('Search results placeholders', () => {
|
173
|
-
|
209
|
+
test('renders a loading state when queryInProgress is true', async () => {
|
174
210
|
const el = await fixture(container(results));
|
175
211
|
|
176
212
|
el.queryInProgress = true;
|
177
213
|
await el.updateComplete;
|
178
214
|
|
179
|
-
expect(el.shadowRoot.querySelector('.loading')).
|
215
|
+
expect(el.shadowRoot.querySelector('.loading')).not.toBeNull();
|
180
216
|
});
|
181
|
-
|
217
|
+
test('renders an error message when provided', async () => {
|
182
218
|
const el = await fixture(container([]));
|
183
219
|
const message = 'Sample error message';
|
184
220
|
el.errorMessage = message;
|
185
221
|
await el.updateComplete;
|
186
222
|
|
187
|
-
expect(el.shadowRoot.querySelector('.error-message')).
|
188
|
-
expect(el.shadowRoot.querySelector('.search-cta')).
|
223
|
+
expect(el.shadowRoot.querySelector('.error-message')).toBeDefined();
|
224
|
+
expect(el.shadowRoot.querySelector('.search-cta')).toBeNull();
|
189
225
|
});
|
190
|
-
|
226
|
+
test('displays call to search when no results or search errors are showing', async () => {
|
191
227
|
const el = await fixture(container([]));
|
192
228
|
|
193
|
-
expect(el.shadowRoot.querySelector('.search-cta')).
|
194
|
-
expect(el.shadowRoot.querySelector('.error-message')).
|
195
|
-
expect(el.shadowRoot.querySelector('.results')).
|
229
|
+
expect(el.shadowRoot.querySelector('.search-cta')).toBeDefined();
|
230
|
+
expect(el.shadowRoot.querySelector('.error-message')).toBeNull();
|
231
|
+
expect(el.shadowRoot.querySelector('.results')).toBeNull();
|
196
232
|
});
|
197
233
|
});
|
198
234
|
|
199
|
-
|
235
|
+
test('displays results images when told to', async () => {
|
200
236
|
const el = await fixture(container(results));
|
201
237
|
el.displayResultImages = true;
|
202
238
|
await el.updateComplete;
|
203
239
|
|
204
|
-
expect(el.shadowRoot.querySelector('.results.show-image')).
|
240
|
+
expect(el.shadowRoot.querySelector('.results.show-image')).toBeDefined();
|
205
241
|
});
|
206
242
|
|
207
243
|
describe('search input focus', () => {
|
208
|
-
|
244
|
+
test('will always try to re-focus once the component updates', async () => {
|
209
245
|
const el = await fixture(container(results));
|
210
246
|
el.focusOnInputIfNecessary = sinon.fake();
|
211
247
|
// update any property to fire lifecycle
|
212
248
|
el.results = [];
|
213
249
|
await el.updateComplete;
|
214
250
|
|
215
|
-
expect(el.focusOnInputIfNecessary.callCount).
|
251
|
+
expect(el.focusOnInputIfNecessary.callCount).toEqual(1);
|
216
252
|
});
|
217
|
-
|
253
|
+
test('refocuses on input when results are empty', async () => {
|
218
254
|
const el = await fixture(container(results));
|
219
255
|
el.results = [];
|
220
256
|
await el.updateComplete;
|
221
257
|
|
222
258
|
const searchInputField = el.shadowRoot.querySelector('input[type=\'search\']');
|
223
|
-
expect(searchInputField).
|
259
|
+
expect(searchInputField).toEqual(el.shadowRoot.activeElement);
|
224
260
|
});
|
225
261
|
});
|
226
262
|
|
227
|
-
|
228
|
-
|
263
|
+
test("emits a bookSearchCanceled event when loading state's cancel action clicked", async () => {
|
264
|
+
const el = await fixture(container(results));
|
229
265
|
|
230
|
-
|
231
|
-
|
266
|
+
el.queryInProgress = true;
|
267
|
+
await el.updateComplete;
|
232
268
|
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
269
|
+
setTimeout(() => (
|
270
|
+
el.shadowRoot.querySelector('button').click()
|
271
|
+
));
|
272
|
+
const response = await oneEvent(el, 'bookSearchCanceled');
|
237
273
|
|
238
|
-
|
239
|
-
|
274
|
+
expect(response).toBeDefined();
|
275
|
+
});
|
276
|
+
it('cancels search when input is cleared', async () => {
|
277
|
+
const el = await fixture(container(results));
|
278
|
+
|
279
|
+
el.cancelSearch = sinon.fake();
|
280
|
+
await el.updateComplete;
|
281
|
+
|
282
|
+
const searchInput = el.shadowRoot.querySelector('[name="query"]');
|
283
|
+
|
284
|
+
searchInput.value = '';
|
285
|
+
searchInput.dispatchEvent(new Event('search'));
|
286
|
+
|
287
|
+
expect(el.cancelSearch.callCount).toEqual(1);
|
288
|
+
});
|
240
289
|
});
|
@@ -0,0 +1,49 @@
|
|
1
|
+
import { fixtureSync } from '@open-wc/testing-helpers';
|
2
|
+
import sinon from 'sinon';
|
3
|
+
import SharingProvider from '@/src/BookNavigator/sharing.js';
|
4
|
+
|
5
|
+
afterEach(() => {
|
6
|
+
sinon.restore();
|
7
|
+
});
|
8
|
+
|
9
|
+
const item = {
|
10
|
+
metadata: {
|
11
|
+
identifier: 'stubby-id',
|
12
|
+
creator: 'mr. big',
|
13
|
+
title: 'Stubby title',
|
14
|
+
}
|
15
|
+
};
|
16
|
+
|
17
|
+
const baseHost = 'foo.org';
|
18
|
+
const subPrefix = 'beep-boop_12 4 5';
|
19
|
+
|
20
|
+
describe('Sharing Provider', () => {
|
21
|
+
describe('constructor', () => {
|
22
|
+
const provider = new SharingProvider({
|
23
|
+
item,
|
24
|
+
baseHost,
|
25
|
+
bookreader: {
|
26
|
+
options: { subPrefix }
|
27
|
+
}
|
28
|
+
});
|
29
|
+
|
30
|
+
expect(provider.id).toEqual('share');
|
31
|
+
expect(provider.icon).toBeDefined();
|
32
|
+
expect(provider.label).toEqual('Share this book');
|
33
|
+
expect(fixtureSync(provider.component).tagName).toContain('IAUX-IN-SHARE-PANEL');
|
34
|
+
});
|
35
|
+
|
36
|
+
describe('Handles being a sub file/volume', () => {
|
37
|
+
test('encodes the subprefix if it has one', async () => {
|
38
|
+
const provider = new SharingProvider({
|
39
|
+
item,
|
40
|
+
baseHost,
|
41
|
+
bookreader: {
|
42
|
+
options: { subPrefix }
|
43
|
+
}
|
44
|
+
});
|
45
|
+
|
46
|
+
expect(fixtureSync(provider.component).fileSubPrefix).toEqual(subPrefix);
|
47
|
+
});
|
48
|
+
});
|
49
|
+
});
|
@@ -0,0 +1,80 @@
|
|
1
|
+
import { fixtureCleanup, fixtureSync } from '@open-wc/testing-helpers';
|
2
|
+
import sinon from 'sinon';
|
3
|
+
import ViewableFilesProvider from '@/src/BookNavigator/viewable-files';
|
4
|
+
|
5
|
+
const brOptions = {
|
6
|
+
"options": {
|
7
|
+
"subPrefix": 'special-subprefix',
|
8
|
+
"enableMultipleBooks": true,
|
9
|
+
"multipleBooksList": {
|
10
|
+
"by_subprefix": {
|
11
|
+
"/details/SubBookTest": {
|
12
|
+
"url_path": "/details/SubBookTest",
|
13
|
+
"file_subprefix": "book1/GPORFP",
|
14
|
+
"orig_sort": 1,
|
15
|
+
"title": "book1/GPORFP.pdf",
|
16
|
+
"file_source": "/book1/GPORFP_jp2.zip"
|
17
|
+
},
|
18
|
+
"/details/SubBookTest/subdir/book2/brewster_kahle_internet_archive": {
|
19
|
+
"url_path": "/details/SubBookTest/subdir/book2/brewster_kahle_internet_archive",
|
20
|
+
"file_subprefix": "subdir/book2/brewster_kahle_internet_archive",
|
21
|
+
"orig_sort": 2,
|
22
|
+
"title": "subdir/book2/brewster_kahle_internet_archive.pdf",
|
23
|
+
"file_source": "/subdir/book2/brewster_kahle_internet_archive_jp2.zip"
|
24
|
+
},
|
25
|
+
"/details/SubBookTest/subdir/subsubdir/book3/Rfp008011ResponseInternetArchive-without-resume": {
|
26
|
+
"url_path": "/details/SubBookTest/subdir/subsubdir/book3/Rfp008011ResponseInternetArchive-without-resume",
|
27
|
+
"file_subprefix": "subdir/subsubdir/book3/Rfp008011ResponseInternetArchive-without-resume",
|
28
|
+
"orig_sort": 3,
|
29
|
+
"title": "subdir/subsubdir/book3/Rfp008011ResponseInternetArchive-without-resume.pdf",
|
30
|
+
"file_source": "/subdir/subsubdir/book3/Rfp008011ResponseInternetArchive-without-resume_jp2.zip"
|
31
|
+
}
|
32
|
+
}
|
33
|
+
}
|
34
|
+
}
|
35
|
+
};
|
36
|
+
|
37
|
+
afterEach(() => {
|
38
|
+
sinon.restore();
|
39
|
+
fixtureCleanup();
|
40
|
+
});
|
41
|
+
|
42
|
+
describe('Volumes Provider', () => {
|
43
|
+
test('initiating & sorting', () => {
|
44
|
+
const onProviderChange = sinon.fake();
|
45
|
+
|
46
|
+
const baseHost = "https://archive.org";
|
47
|
+
const provider = new ViewableFilesProvider({
|
48
|
+
baseHost,
|
49
|
+
bookreader: brOptions,
|
50
|
+
onProviderChange
|
51
|
+
});
|
52
|
+
|
53
|
+
const files = brOptions.options.multipleBooksList.by_subprefix;
|
54
|
+
const volumeCount = Object.keys(files).length;
|
55
|
+
|
56
|
+
expect(provider.onProviderChange).toEqual(onProviderChange);
|
57
|
+
expect(provider.id).toEqual('volumes');
|
58
|
+
expect(provider.icon).toBeDefined();
|
59
|
+
expect(fixtureSync(provider.icon).tagName).toEqual('svg');
|
60
|
+
expect(provider.sortOrderBy).toEqual('default');
|
61
|
+
|
62
|
+
expect(provider.label).toEqual(`Viewable files (${volumeCount})`);
|
63
|
+
expect(provider.viewableFiles).toBeDefined();
|
64
|
+
expect(provider.viewableFiles.length).toEqual(3);
|
65
|
+
expect(provider.volumeCount).toEqual(3);
|
66
|
+
|
67
|
+
expect(provider.component.baseHost).toEqual(baseHost);
|
68
|
+
expect(provider.component.fileList).toEqual(provider.viewableFiles);
|
69
|
+
expect(provider.component.subPrefix).toEqual(brOptions.options.subPrefix);
|
70
|
+
|
71
|
+
expect(provider.actionButton).toBeDefined();
|
72
|
+
expect(provider.actionButton).toEqual(provider.sortFilesComponent);
|
73
|
+
expect(provider.actionButton.fileListRaw).toEqual(provider.viewableFiles);
|
74
|
+
|
75
|
+
const callbackSpy = sinon.spy(provider, 'handleFileListSorted');
|
76
|
+
provider.actionButton.sortVolumes('title_asc');
|
77
|
+
|
78
|
+
expect(callbackSpy.callCount).toEqual(1);
|
79
|
+
});
|
80
|
+
});
|