/*******************************************************************************
*
* Copyright (c) 2013 blinkbox Entertainment Limited. All rights reserved.
*
*
*******************************************************************************/
package com.blinkbox.java.book.factory;
import com.blinkbox.java.book.exceptions.BBBEPubFileNotFoundException;
import com.blinkbox.java.book.exceptions.BBBEPubParseException;
import com.blinkbox.java.book.model.BBBEPubBook;
import com.blinkbox.java.book.model.BBBEPubContent;
import com.blinkbox.java.book.utils.StreamUtils;
import org.junit.Test;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
/**
* Test the end to end functionality of parsing an epub file and producing a
* {@link BBBEPubBook} object
*/
public class BBBEPubFactoryTest {
private BBBEPubFactory bbBBBEPubFactory = BBBEPubFactory.getInstance();
/**
* Parse the sample book from the test resources
*/
@Test
public void testParseASampleBook() throws Exception {
BBBEPubBook book = bookFromResource("books/sample.epub");
assertEquals("application/epub+zip", book.getMimeType());
assertEquals("Nemesis", book.getTitle());
assertEquals(63, book.getTOCList().size());
assertEquals("Cover", book.getTOCList().get(0).getLabel());
assertEquals("OPS/cover.xml", book.getTOCList().get(0).getHREFLink());
assertEquals(0, book.getTOCList().get(0).getDepth());
assertEquals("51 Sans Souci", book.getTOCList().get(62).getLabel());
assertEquals("OPS/062 - Chapter_51.xhtml", book.getTOCList().get(62).getHREFLink());
assertEquals(1, book.getTOCList().get(62).getDepth());
String titleurl = book.getTOCList().get(1).getHREFLink();
BBBEPubContent content = book.getContentAtUrl(titleurl);
assertNotNull(content);
assertNotNull(content.getData());
String data = new String(StreamUtils.toByteArray(content.getData()));
assertTrue(data.startsWith("<?xml"));
assertTrue(data.endsWith("</html>"));
assertEquals(769, data.length());
content = book.getContentAtUrl("OPS/images/fsc.jpg");
assertEquals("image/jpeg", content.getMimeType());
content = book.getContentAtUrl("/OPS/images/fsc.jpg");
assertEquals("image/jpeg", content.getMimeType());
assertEquals(book.getTOCList().get(0).getHREFLink(), book.getBookInfo().getToc().get(0).href);
}
/**
* Parse an actual epub book (A history of my times)
*/
@Test
public void testParseTheHistoryOfMyTimes() throws Exception {
BBBEPubBook book = bookFromResource("books/history.epub");
assertEquals("application/epub+zip", book.getMimeType());
assertEquals("A History of My Times", book.getTitle());
assertEquals(248, book.getTOCList().size());
assertEquals(248, book.getTOCList(5).size());
assertEquals(12, book.getTOCList(0).size());
assertEquals(34, book.getTOCList(1).size());
assertEquals("Cover", book.getTOCList().get(0).getLabel());
assertEquals("OEBPS/html/cover.html", book.getTOCList().get(0).getHREFLink());
assertEquals("page 362", book.getTOCList().get(229).getLabel());
assertEquals("OEBPS/html/bk07notes02.html#bk07notes02", book.getTOCList().get(229).getHREFLink());
assertEquals("page 403", book.getTOCList().get(247).getLabel());
assertEquals("OEBPS/html/bk07notes20.html#bk07notes20", book.getTOCList().get(247).getHREFLink());
String titleurl = book.getTOCList().get(1).getHREFLink();
BBBEPubContent content = book.getContentAtUrl(titleurl);
assertNotNull(content);
assertNotNull(content.getData());
String data = new String(StreamUtils.toByteArray(content.getData()));
assertTrue(data.startsWith("<?xml"));
assertEquals(8548, data.length());
}
/**
* Parse an encrypted epub book
*/
@Test
public void testParseEncryptedAES128SmallEpub() throws Exception {
BBBEPubBook book = bookFromResource("books/encrypted/small-aes128-comp.epub");
// assertEquals("application/epub+zip", book.getMimeType());
assertEquals("Designated Targets: World War 2.2", book.getTitle());
assertEquals(46, book.getTOCList().size());
assertEquals("Cover", book.getTOCList().get(0).getLabel());
assertEquals("DesignatedTargets/xhtml/cover.html", book.getTOCList().get(0).getHREFLink());
String titleurl = book.getTOCList().get(1).getHREFLink();
BBBEPubContent content = book.getContentAtUrl(titleurl);
assertNotNull(content);
assertNotNull(content.getData());
assertEquals("application/xhtml+xml", content.getMimeType());
String data = new String(StreamUtils.toByteArray(content.getData()));
assertTrue(data.startsWith("<?xml"));
assertEquals(1384, data.length());
}
/**
* Test that books with invalid XML can still be read, as all the information
* is available in book-info.json
*/
@Test
public void testParseBookWithInvalidXML() throws Exception {
BBBEPubBook book = bookFromResource("books/9780330462716.epub");
assertEquals("application/epub+zip", book.getMimeType());
BBBEPubContent content = book.getContentAtUrl("/META-INF/book-info.json");
assertNotNull(content);
assertNotNull(content.getData());
String data = new String(StreamUtils.toByteArray(content.getData()));
assertTrue(data.startsWith("{\"version\":"));
assertEquals(1423, data.length());
}
/**
* Parse an invalid epub book
*/
@Test
public void testParseInvalidEPub() throws Exception {
try {
BBBEPubBook book = bookFromResource("books/encrypted/invalidxml.epub");
assertEquals(book.getBaseUrl(), "DesignatedTargets/");
} catch (BBBEPubParseException e) {
fail();
}
}
/**
* Test that BBBEPubFileNotFoundException is thrown if the book is missing
*/
@Test
public void testParseMissingBook() throws Exception {
try {
bbBBBEPubFactory.createFromURL(null, "books/missing.epub", null);
fail();
} catch (BBBEPubFileNotFoundException e) {
assertTrue(true);
}
}
private String extractFile(String resource) throws Exception {
File fileOutput = new File("test.epub");
InputStream inputStream = getClass().getClassLoader().getResourceAsStream(resource);
OutputStream outputStream = new FileOutputStream(fileOutput);
// transfer bytes from the input file to the output file
byte[] buffer = new byte[1024];
int length;
while ((length = inputStream.read(buffer)) > 0) {
outputStream.write(buffer, 0, length);
}
// Close the streams
outputStream.flush();
outputStream.close();
inputStream.close();
return fileOutput.getAbsolutePath();
}
private BBBEPubBook bookFromResource(final String resource) throws Exception {
String fullPath = extractFile(resource);
System.out.println("url " + fullPath);
final long startTime = System.currentTimeMillis();
BBBEPubBook book = bbBBBEPubFactory.createFromURL(null, fullPath, "M0bc45T".toCharArray());
final long elapsedTimeMillis = System.currentTimeMillis() - startTime;
System.out.println("Parsed " + resource + " in " + elapsedTimeMillis + " ms");
return book;
}
}