mirror of
https://github.com/MinimalBible/MinimalBible
synced 2024-11-22 07:58:20 -05:00
Use a delegate to make OsisParser cleaner
This commit is contained in:
parent
c57babd68a
commit
c394fce273
@ -0,0 +1,39 @@
|
|||||||
|
package org.bspeice.minimalbible.test;
|
||||||
|
|
||||||
|
import org.bspeice.minimalbible.FinalDelegate;
|
||||||
|
import org.bspeice.minimalbible.MBTestCase;
|
||||||
|
|
||||||
|
import kotlin.PropertyMetadataImpl;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test that the FinalDelegate actually obeys its contract
|
||||||
|
*/
|
||||||
|
public class FinalDelegateTest extends MBTestCase {
|
||||||
|
|
||||||
|
FinalDelegate<String> delegate;
|
||||||
|
|
||||||
|
public void setUp() {
|
||||||
|
delegate = new FinalDelegate<String>();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testDelegateNullSafety() {
|
||||||
|
try {
|
||||||
|
delegate.get(null, new PropertyMetadataImpl(""));
|
||||||
|
} catch (IllegalStateException e) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
fail("Exception not thrown!");
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testDelegateAssignOnce() {
|
||||||
|
try {
|
||||||
|
delegate.set(null, new PropertyMetadataImpl(""), "");
|
||||||
|
delegate.set(null, new PropertyMetadataImpl(""), "");
|
||||||
|
} catch (IllegalStateException e) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
fail("Allowed to set twice!");
|
||||||
|
}
|
||||||
|
}
|
@ -17,7 +17,7 @@ public class OsisParserTest extends MBTestCase {
|
|||||||
OsisParser parser;
|
OsisParser parser;
|
||||||
|
|
||||||
public void setUp() {
|
public void setUp() {
|
||||||
parser = new OsisParser(null);
|
parser = new OsisParser();
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressLint("NewApi")
|
@SuppressLint("NewApi")
|
||||||
|
@ -80,7 +80,8 @@ public class VerseLookupService implements Action1<Verse> {
|
|||||||
BookData bookData = new BookData(book, v);
|
BookData bookData = new BookData(book, v);
|
||||||
try {
|
try {
|
||||||
SAXEventProvider provider = bookData.getSAXEventProvider();
|
SAXEventProvider provider = bookData.getSAXEventProvider();
|
||||||
OsisParser handler = new OsisParser(v);
|
OsisParser handler = new OsisParser();
|
||||||
|
handler.setVerse(v);
|
||||||
provider.provideSAXEvents(handler);
|
provider.provideSAXEvents(handler);
|
||||||
return handler.getVerseContent().toJson();
|
return handler.getVerseContent().toJson();
|
||||||
} catch (BookException e) {
|
} catch (BookException e) {
|
||||||
|
@ -0,0 +1,24 @@
|
|||||||
|
package org.bspeice.minimalbible
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The purpose of this delegate is to guarantee null-safety, while
|
||||||
|
* also ensuring a pseudo-val type. If you try to read before use, error.
|
||||||
|
* If you try to set multiple times, error.
|
||||||
|
*/
|
||||||
|
|
||||||
|
public class FinalDelegate<T : Any>() {
|
||||||
|
private var value: T? = null
|
||||||
|
private var didAssign: Boolean = false
|
||||||
|
|
||||||
|
public fun get(thisRef: Any?, desc: PropertyMetadata): T {
|
||||||
|
return value ?: throw IllegalStateException("Property ${desc.name} should be initialized before get")
|
||||||
|
}
|
||||||
|
|
||||||
|
public fun set(thisRef: Any?, desc: PropertyMetadata, value: T) {
|
||||||
|
if (!didAssign) {
|
||||||
|
this.value = value
|
||||||
|
this.didAssign = true
|
||||||
|
} else
|
||||||
|
throw IllegalStateException("Property ${desc.name} should not be assigned multiple times")
|
||||||
|
}
|
||||||
|
}
|
@ -5,17 +5,20 @@ import org.crosswire.jsword.passage.Verse
|
|||||||
import java.util.ArrayDeque
|
import java.util.ArrayDeque
|
||||||
import org.xml.sax.Attributes
|
import org.xml.sax.Attributes
|
||||||
import org.crosswire.jsword.book.OSISUtil
|
import org.crosswire.jsword.book.OSISUtil
|
||||||
|
import org.bspeice.minimalbible.FinalDelegate
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Created by bspeice on 9/10/14.
|
* Created by bspeice on 9/10/14.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
class OsisParser(v: Verse?) : DefaultHandler() {
|
class OsisParser() : DefaultHandler() {
|
||||||
|
|
||||||
|
// Don't pass a verse as part of the constructor, but still guarantee
|
||||||
|
// that it will exist
|
||||||
|
public var verse: Verse by FinalDelegate()
|
||||||
|
val verseContent: VerseContent
|
||||||
|
get() = VerseContent(verse)
|
||||||
|
|
||||||
val verseContent: VerseContent? = when (v) {
|
|
||||||
is Verse -> VerseContent(v) // not null
|
|
||||||
else -> null
|
|
||||||
}
|
|
||||||
// TODO: Implement a stack to keep min API 8
|
// TODO: Implement a stack to keep min API 8
|
||||||
val doWrite = ArrayDeque<Boolean>()
|
val doWrite = ArrayDeque<Boolean>()
|
||||||
|
|
||||||
@ -33,6 +36,6 @@ class OsisParser(v: Verse?) : DefaultHandler() {
|
|||||||
|
|
||||||
override fun characters(ch: CharArray, start: Int, length: Int) {
|
override fun characters(ch: CharArray, start: Int, length: Int) {
|
||||||
if (doWrite.peek())
|
if (doWrite.peek())
|
||||||
verseContent?.appendContent(String(ch))
|
verseContent.appendContent(String(ch))
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -9,14 +9,17 @@ import java.util.ArrayList
|
|||||||
|
|
||||||
//TODO: JSON Streaming parsing? http://instagram-engineering.tumblr.com/post/97147584853/json-parsing
|
//TODO: JSON Streaming parsing? http://instagram-engineering.tumblr.com/post/97147584853/json-parsing
|
||||||
class VerseContent(v: Verse) {
|
class VerseContent(v: Verse) {
|
||||||
var id = v.getOrdinal()
|
val id = v.getOrdinal()
|
||||||
var bookName = v.getName()
|
val bookName = v.getName()
|
||||||
var chapter = v.getChapter()
|
val chapter = v.getChapter()
|
||||||
var verseNum = v.getVerse()
|
val verseNum = v.getVerse()
|
||||||
|
val chapterTitle = ""
|
||||||
|
val paraTitle = ""
|
||||||
|
val references: MutableList<VerseReference> = ArrayList()
|
||||||
var content = ""
|
var content = ""
|
||||||
var chapterTitle = ""
|
|
||||||
var paraTitle = ""
|
public val json: String
|
||||||
var references: MutableList<VerseReference> = ArrayList()
|
get() = Gson().toJson(this)
|
||||||
|
|
||||||
public fun toJson(): String {
|
public fun toJson(): String {
|
||||||
// Lazy load Gson - not likely that we'll call this method multiple times, so
|
// Lazy load Gson - not likely that we'll call this method multiple times, so
|
||||||
|
Loading…
Reference in New Issue
Block a user