package org.ebookdroid.common.settings.books; import android.support.test.InstrumentationRegistry; import android.support.test.runner.AndroidJUnit4; import org.ebookdroid.common.settings.definitions.AppPreferences; import org.ebookdroid.common.settings.types.DocumentViewMode; import org.ebookdroid.common.settings.types.PageAlign; import org.ebookdroid.common.settings.types.RotationType; import org.ebookdroid.core.PageIndex; import org.ebookdroid.core.curl.PageAnimationType; import org.hamcrest.Matchers; import org.json.JSONObject; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; import java.util.Map; import java.util.Set; import static org.hamcrest.CoreMatchers.equalTo; import static org.hamcrest.CoreMatchers.notNullValue; import static org.hamcrest.CoreMatchers.nullValue; import static org.hamcrest.Matchers.empty; import static org.hamcrest.Matchers.greaterThan; import static org.hamcrest.Matchers.hasSize; import static org.hamcrest.Matchers.is; import static org.hamcrest.Matchers.lessThanOrEqualTo; import static org.hamcrest.Matchers.not; import static org.junit.Assert.assertThat; @RunWith(AndroidJUnit4.class) public class DBSettingsManagerTest { private DBSettingsManager m_manager; private BookSettings m_bs; private BookSettings m_bs2; private BookSettings sampleBookSettings(String filename) { BookSettings bs = new BookSettings(filename); // FIXME: shouldn't need to set these bs.rotation = RotationType.UNSPECIFIED; bs.viewMode = DocumentViewMode.VERTICALL_SCROLL; return bs; } private Bookmark m_b1; private Bookmark m_b1_dup; private Bookmark m_b2; @Before public void setup() { m_manager = new DBSettingsManager(InstrumentationRegistry.getTargetContext(), null); // null for in-memory assertThat(m_manager, is(notNullValue())); assertThat(m_manager.deleteAll(), is(true)); m_bs = sampleBookSettings(BS_FILENAME); m_bs2 = sampleBookSettings(BS_FILENAME2); m_b1 = new Bookmark("bookmark", new PageIndex(12, 34), 5.0f, 10.0f); m_b1_dup = new Bookmark("bookmark", new PageIndex(12, 34), 5.0f, 10.0f); m_b2 = new Bookmark("bookmark2", new PageIndex(13, 35), 0.0f, 0.0f); } @After public void cleanUp() { m_manager.close(); } private static final String BS_FILENAME = "testfilename.pdf"; private static final String BS_FILENAME2 = "testfilename2.pdf"; private void checkDefaults(BookSettings bs, long expectedLastUpdated) { assertThat(bs, is(notNullValue())); assertThat(bs.persistent, is(true)); assertThat(bs.lastChanged, is(0L)); assertThat(bs.fileName, is(BS_FILENAME)); assertThat(Math.abs(bs.lastUpdated - expectedLastUpdated), is(lessThanOrEqualTo(1L))); assertThat(bs.firstPageOffset, is(1)); assertThat(bs.currentPage, is(PageIndex.FIRST)); assertThat(bs.zoom, is(100)); assertThat(bs.splitPages, is(false)); assertThat(bs.splitRTL, is(false)); assertThat(bs.rotation, is(RotationType.UNSPECIFIED)); assertThat(bs.viewMode, is(DocumentViewMode.VERTICALL_SCROLL)); assertThat(bs.pageAlign, is(PageAlign.AUTO)); assertThat(bs.animationType, is(PageAnimationType.NONE)); assertThat(bs.bookmarks, is(empty())); assertThat(bs.cropPages, is(false)); assertThat(bs.offsetX, is(0.0f)); assertThat(bs.offsetY, is(0.0f)); assertThat(bs.nightMode, is(false)); assertThat(bs.positiveImagesInNightMode, is(false)); assertThat(bs.contrast, is(AppPreferences.CONTRAST.defValue)); assertThat(bs.gamma, is(AppPreferences.GAMMA.defValue)); assertThat(bs.exposure, is(AppPreferences.EXPOSURE.defValue)); assertThat(bs.autoLevels, is(false)); assertThat(bs.typeSpecific, is(nullValue())); } private BookSettings roundTrip(BookSettings bs) { assertThat(m_manager.storeBookSettings(bs), is(true)); BookSettings roundtrip = m_manager.getBookSettings(bs.fileName); assertThat(roundtrip, is(notNullValue())); return roundtrip; } @Test public void testPersistDefaultObject() { final long creationTime = System.currentTimeMillis(); BookSettings bs = sampleBookSettings(BS_FILENAME); checkDefaults(bs, creationTime); assertThat(m_manager.getBookSettings(BS_FILENAME), is(nullValue())); assertThat(m_manager.storeBookSettings(bs), is(true)); BookSettings roundtrip = m_manager.getBookSettings(bs.fileName); assertThat(roundtrip, is(notNullValue())); checkDefaults(roundtrip, creationTime); } @Test public void testFirstPageOffset() { for (int testValue : new int[] {15, 45}) { m_bs.firstPageOffset = testValue; assertThat(roundTrip(m_bs).firstPageOffset, is(testValue)); } } @Test public void testCurrentPage() { for (PageIndex testValue : new PageIndex[] { PageIndex.FIRST, PageIndex.LAST, PageIndex.NULL, new PageIndex(123, 456)}) { m_bs.currentPage = testValue; assertThat(roundTrip(m_bs).currentPage, is(testValue)); } } @Test public void testZoom() { for (int testValue : new int[] {15, 45}) { m_bs.zoom = testValue; assertThat(roundTrip(m_bs).zoom, is(testValue)); } } @Test public void testSplitPages() { for (boolean testValue : new boolean[] { true, false }) { m_bs.splitPages = testValue; assertThat(roundTrip(m_bs).splitPages, is(testValue)); } } @Test public void testSplitRTL() { for (boolean testValue : new boolean[] { true, false }) { m_bs.splitRTL = testValue; assertThat(roundTrip(m_bs).splitRTL, is(testValue)); } } @Test public void testRotation() { for (RotationType testValue : RotationType.values()) { m_bs.rotation = testValue; assertThat(roundTrip(m_bs).rotation, is(testValue)); } } @Test public void testViewMode() { for (DocumentViewMode testValue : DocumentViewMode.values()) { m_bs.viewMode = testValue; assertThat(roundTrip(m_bs).viewMode, is(testValue)); } } @Test public void testPageAlign() { for (PageAlign testValue : PageAlign.values()) { m_bs.pageAlign = testValue; assertThat(roundTrip(m_bs).pageAlign, is(testValue)); } } @Test public void testAnimationType() { for (PageAnimationType testValue : PageAnimationType.values()) { m_bs.animationType = testValue; assertThat(roundTrip(m_bs).animationType, is(testValue)); } } @Test public void testBookmarksEquality() { assertThat(m_b1, is(m_b1_dup)); assertThat(m_b1, is(not(equalTo(m_b2)))); } @Test public void testBookmarksEmpty() { assertThat(m_bs.bookmarks, is(empty())); assertThat(roundTrip(m_bs).bookmarks, is(empty())); } @Test public void testAddBookmark() { m_bs.bookmarks.addAll(Arrays.asList(m_b1)); assertThat(roundTrip(m_bs).bookmarks, is(Arrays.asList(m_b1))); m_bs.bookmarks.clear(); m_bs.bookmarks.addAll(Arrays.asList(m_b1, m_b2)); assertThat(roundTrip(m_bs).bookmarks, is(Arrays.asList(m_b1, m_b2))); } @Test public void testDuplicateBookmarksAllowed() { m_bs.bookmarks.addAll(Arrays.asList(m_b1, m_b1, m_b2)); assertThat(roundTrip(m_bs).bookmarks, is(Arrays.asList(m_b1, m_b1, m_b2))); m_bs.bookmarks.clear(); m_bs.bookmarks.addAll(Arrays.asList(m_b1, m_b2)); assertThat(roundTrip(m_bs).bookmarks, is(Arrays.asList(m_b1, m_b2))); } @Test public void testDeleteAllBookmarks() { m_bs.bookmarks.add(m_b1); m_bs2.bookmarks.add(m_b2); assertThat(m_manager.storeBookSettings(Arrays.asList(m_bs, m_bs2)), is(true)); assertThat(m_manager.getBookSettings(BS_FILENAME).bookmarks, is(Arrays.asList(m_b1))); assertThat(m_manager.getBookSettings(BS_FILENAME2).bookmarks, is(Arrays.asList(m_b2))); assertThat(m_manager.deleteAllBookmarks(), is(true)); assertThat(m_manager.getBookSettings(BS_FILENAME).bookmarks, is(empty())); assertThat(m_manager.getBookSettings(BS_FILENAME2).bookmarks, is(empty())); } @Test public void testCropPages() { for (boolean testValue : new boolean[] { true, false }) { m_bs.cropPages = testValue; assertThat(roundTrip(m_bs).cropPages, is(testValue)); } } @Test public void testOffsetX() { for (float testValue : new float[] { -1.0f, 3.3f }) { m_bs.offsetX = testValue; assertThat(roundTrip(m_bs).offsetX, is(testValue)); } } @Test public void testOffsetY() { for (float testValue : new float[] { -1.0f, 3.3f }) { m_bs.offsetY = testValue; assertThat(roundTrip(m_bs).offsetY, is(testValue)); } } @Test public void testNightMode() { for (boolean testValue : new boolean[] { true, false }) { m_bs.nightMode = testValue; assertThat(roundTrip(m_bs).nightMode, is(testValue)); } } @Test public void testPositiveImagesInNightMode() { for (boolean testValue : new boolean[] { true, false }) { m_bs.positiveImagesInNightMode = testValue; assertThat(roundTrip(m_bs).positiveImagesInNightMode, is(testValue)); } } @Test public void testContrast() { for (int testValue : new int[] { 1, 255 }) { m_bs.contrast = testValue; assertThat(roundTrip(m_bs).contrast, is(testValue)); } } @Test public void testGamma() { for (int testValue : new int[] { 1, 255 }) { m_bs.gamma = testValue; assertThat(roundTrip(m_bs).gamma, is(testValue)); } } @Test public void testExposure() { for (int testValue : new int[] { 1, 255 }) { m_bs.exposure = testValue; assertThat(roundTrip(m_bs).exposure, is(testValue)); } } @Test public void testAutoLevels() { for (boolean testValue : new boolean[] { true, false }) { m_bs.autoLevels = testValue; assertThat(roundTrip(m_bs).autoLevels, is(testValue)); } } @Test public void testTypeSpecific() { Map<String, String> m = new HashMap<>(); m.put("foo", "bar"); JSONObject testValue = new JSONObject(m); // JSONObject doesn't support equals() m_bs.typeSpecific = testValue; assertThat(roundTrip(m_bs).typeSpecific.toString(), is(testValue.toString())); m_bs.typeSpecific = null; assertThat(roundTrip(m_bs).typeSpecific, is(nullValue())); } private void sleep(long ms) { final long start = System.currentTimeMillis(); while ((System.currentTimeMillis() - start) < ms) { try { Thread.sleep(System.currentTimeMillis() - start); } catch (InterruptedException e) { } } } @Test public void testLastChanged() { final long bs_originalLastUpdated = m_bs.lastUpdated; // first, save without setting `lastChanged` assertThat(m_bs.lastChanged, is(0L)); assertThat(m_manager.storeBookSettings(m_bs), is(true)); assertThat(m_bs.lastUpdated, is(bs_originalLastUpdated)); sleep(1); // second, set `lastChanged` to trigger `lastUpdated` to be updated to the current time m_bs.lastChanged = 1L; assertThat(m_manager.storeBookSettings(m_bs), is(true)); assertThat(m_bs.lastUpdated, is(greaterThan(bs_originalLastUpdated))); } @Test public void testRestoreBookSettings() { m_bs.lastChanged = 1L; m_bs.lastUpdated = 123L; assertThat(m_manager.restoreBookSettings(Collections.singletonList(m_bs)), is(true)); assertThat(m_bs.lastChanged, is(1L)); assertThat(m_bs.lastUpdated, is(123L)); assertThat(m_manager.getBookSettings(BS_FILENAME).lastChanged, is(0L)); assertThat(m_manager.getBookSettings(BS_FILENAME).lastUpdated, is(123L)); } @Test public void testTwoRecentBooks() { m_bs.lastChanged = 1L; // trigger `lastUpdated` to be updated to the current time assertThat(m_manager.storeBookSettings(m_bs), is(true)); sleep(1); m_bs2.lastChanged = 1L; // trigger `lastUpdated` to be updated to the current time assertThat(m_manager.storeBookSettings(m_bs2), is(true)); Set<String> expectedFilenames = new HashSet<String>(Arrays.asList(BS_FILENAME, BS_FILENAME2)); assertThat(expectedFilenames, hasSize(2)); assertThat(m_manager.getAllBooks().keySet(), is(expectedFilenames)); assertThat(m_manager.getRecentBooks(true).keySet(), is(expectedFilenames)); Set<String> filename2Set = new HashSet<String>(Arrays.asList(BS_FILENAME2)); assertThat(m_manager.getRecentBooks(false).keySet(), is(filename2Set)); } @Test public void testNoRecentBooks() { assertThat(m_bs.lastUpdated, is(greaterThan(0L))); m_bs.lastUpdated = 0L; // mark is as "not recent" assertThat(m_bs.lastChanged, is(0L)); assertThat(m_manager.storeBookSettings(m_bs), is(true)); assertThat(m_manager.getRecentBooks(true).values(), is(empty())); } @Test public void testRemoveBookFromRecents() { assertThat(m_manager.storeBookSettings(m_bs), is(true)); assertThat(m_manager.storeBookSettings(m_bs2), is(true)); Set<String> expectedAll = new HashSet<String>(Arrays.asList(BS_FILENAME, BS_FILENAME2)); assertThat(m_manager.getRecentBooks(true).keySet(), is(expectedAll)); // mark `m_bs` as not recent assertThat(m_manager.getBookSettings(BS_FILENAME).lastUpdated, is(not(0L))); assertThat(m_manager.removeBookFromRecents(m_bs), is(true)); assertThat(m_manager.getBookSettings(BS_FILENAME).lastUpdated, is(0L)); Set<String> expectedAfterBsRemoved = new HashSet<String>(Arrays.asList(BS_FILENAME2)); assertThat(m_manager.getRecentBooks(true).keySet(), is(expectedAfterBsRemoved)); } @Test public void testClearRecent() { assertThat(m_manager.storeBookSettings(m_bs), is(true)); assertThat(m_manager.storeBookSettings(m_bs2), is(true)); Set<String> expectedAll = new HashSet<String>(Arrays.asList(BS_FILENAME, BS_FILENAME2)); assertThat(m_manager.getRecentBooks(true).keySet(), is(expectedAll)); assertThat(m_manager.clearRecent(), is(true)); assertThat(m_manager.getRecentBooks(true).keySet(), is(empty())); assertThat(m_manager.getAllBooks().keySet(), is(expectedAll)); } @Test public void testOneRecentBook() { m_bs.lastUpdated = 0L; // mark is as "not recent" assertThat(m_bs.lastChanged, is(0L)); assertThat(m_manager.storeBookSettings(m_bs), is(true)); assertThat(m_bs2.lastUpdated, is(greaterThan(0L))); assertThat(m_manager.storeBookSettings(m_bs2), is(true)); Set<String> expectedAll = new HashSet<String>(Arrays.asList(BS_FILENAME, BS_FILENAME2)); Set<String> expectedRecent = new HashSet<String>(Arrays.asList(BS_FILENAME2)); assertThat(m_manager.getAllBooks().keySet(), is(expectedAll)); assertThat(m_manager.getRecentBooks(true).keySet(), is(expectedRecent)); assertThat(m_manager.getRecentBooks(false).keySet(), is(expectedRecent)); } @Test public void testNonPersistentBookSettings() { m_bs.persistent = false; assertThat(m_manager.storeBookSettings(m_bs), is(false)); assertThat(m_manager.getBookSettings(BS_FILENAME), is(nullValue())); assertThat(m_manager.getAllBooks().keySet(), is(empty())); } @Test public void testDeleteBook() { assertThat(m_manager.storeBookSettings(Arrays.asList(m_bs, m_bs2)), is(true)); Set<String> expectedAll = new HashSet<String>(Arrays.asList(BS_FILENAME, BS_FILENAME2)); Set<String> expectedAfterDeletion = new HashSet<String>(Arrays.asList(BS_FILENAME2)); assertThat(m_manager.getAllBooks().keySet(), is(expectedAll)); m_manager.delete(m_bs); assertThat(m_manager.getAllBooks().keySet(), is(expectedAfterDeletion)); m_manager.delete(m_bs2); assertThat(m_manager.getAllBooks().keySet(), is(empty())); } }