UNPKG

chapter-and-verse

Version:

Given a bible reference, validates it and returns an object with book, chapter, verse and more

184 lines (162 loc) 4.74 kB
const _ = require('lodash') const books = require('./books.json') const osis = require('./osis.json') const errors = require('./errors') const getChapter = require('./getChapter') const getVerses = require('./getVerses') function CV(book, reason) { this.book = book const vpcBook = _.find(books, {id: book.id}) this.book.versesPerChapter = vpcBook.chapters this.success = true this.reason = reason this.chapter = null this.from = null this.to = null } CV.prototype.toString = function() { let str = this.book.name if (this.chapter) { str += ` ${this.chapter}` if (this.from) { str += `:${this.from}` if (this.from < this.to) { str += `-${this.to}` } } } return str } CV.prototype.toShortString = function() { if (this.book.chapters > 1) return this.toString() let str = this.book.name if (this.from) { str += ` ${this.from}` if (this.from < this.to) { str += `-${this.to}` } } return str } CV.prototype.getType = function() { if (!this.chapter) return 'book' if (!this.from) return 'chapter' if (this.from === this.to) return 'verse' return 'verses' } CV.prototype.toSimpleObject = function() { return { type: this.getType(), asString: this.toString(), asShortString: this.toShortString(), bookId: this.book.id, bookName: this.book.name, testament: this.book.testament, chapter: this.chapter, from: this.from, to: this.to } } CV.prototype.next = function() { const NEXT = { BOOK: 'next book', CHAPTER: 'next chapter', VERSE: 'next verse' } let cv const nextBook = _.find(osis, {order: this.book.order + 1}) if (this.getType() === 'book') { return (nextBook) ? new CV(nextBook, NEXT.BOOK) : errors.nextBook } if (this.getType() === 'chapter') { // current book, next chapter cv = new CV(this.book, NEXT.CHAPTER) cv = getChapter(cv, this.chapter + 1) if (!cv.success) { if (!nextBook) return errors.nextChapter // next book, 1st chapter cv = new CV(nextBook, NEXT.CHAPTER) cv = getChapter(cv, 1) } } if (this.getType() === 'verse' || this.getType() === 'verses') { // current book, current chapter, next verse cv = new CV(this.book, NEXT.VERSE) cv = getChapter(cv, this.chapter) cv = getVerses(cv, this.to + 1) if (!cv.success) { // current book, next chapter, 1st verse cv = new CV(this.book, NEXT.VERSE) cv = getChapter(cv, this.chapter + 1) if (cv.success) { cv = getVerses(cv, 1) } else { if (!nextBook) return errors.nextVerse // next book, 1st chapter, 1st verse cv = new CV(nextBook, NEXT.VERSE) cv = getChapter(cv, 1) cv = getVerses(cv, 1) } } } return cv } CV.prototype.prev = function() { const PREV = { BOOK: 'previous book', CHAPTER: 'previous chapter', VERSE: 'previous verse' } let cv const prevBook = _.find(osis, {order: this.book.order - 1}) if (this.getType() === 'book') { return (prevBook) ? new CV(prevBook, PREV.BOOK) : errors.prevBook } if (this.getType() === 'chapter') { // current book, previous chapter cv = new CV(this.book, PREV.CHAPTER) cv = getChapter(cv, this.chapter - 1) if (!cv.success) { if (!prevBook) return errors.prevChapter // previous book, last chapter cv = new CV(prevBook, PREV.CHAPTER) cv = getChapter(cv, cv.book.chapters) } } if (this.getType() === 'verse' || this.getType() === 'verses') { // current book, current chapter, previous verse cv = new CV(this.book, PREV.VERSE) cv = getChapter(cv, this.chapter) cv = getVerses(cv, this.from - 1) if (!cv.success) { // current book, previous chapter, last verse cv = new CV(this.book, PREV.VERSE) cv = getChapter(cv, this.chapter - 1) if (cv.success) { cv = getVerses(cv, cv.book.versesPerChapter[cv.chapter - 1]) } else { if (!prevBook) return errors.prevVerse // previous book, last chapter, last verse cv = new CV(prevBook, PREV.VERSE) cv = getChapter(cv, cv.book.chapters) cv = getVerses(cv, cv.book.versesPerChapter[cv.chapter - 1]) } } } return cv } const getBook = strBook => { for (let book of osis) { if (strBook === book.id.toLowerCase()) { return new CV(book, 'matches book.id') } if (book.abbr.includes(strBook)) { return new CV(book, 'matches a book.abbr') } if (strBook.startsWith(book.start) && strBook.length <= book.name.replace(/ /g, '').length) { return new CV(book, 'starts with book.start') } } return errors.book } module.exports = getBook