Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -1664,6 +1664,60 @@ class SeforimRepository(databasePath: String, private val driver: SqlDriver) : L
forward + inverse
}

/**
* The lines that the cross-reference links of [lineIds] point to: REFERENCE and MESORAT_HASHAS in
* both directions (these links are unoriented and stored once), EIN_MISHPAT forward only (its
* reverse is the SOURCE view). A line is returned once, however many links reach it; the lines of
* [lineIds] themselves are left out.
*/
suspend fun getReferencesForLines(lineIds: Collection<Long>): List<LineReference> =
withContext(Dispatchers.IO) {
if (lineIds.isEmpty()) return@withContext emptyList()
database.linkQueriesQueries.selectReferencesByLineIds(lineIds, lineIds) {
_, connectionType, fromLineId, lineId, bookId, lineIndex, heRef, content, bookTitle, categoryId, bookOrderIndex ->
lineReference(connectionType, fromLineId, lineId, bookId, lineIndex, heRef, content, bookTitle, categoryId, bookOrderIndex)
}.executeAsList()
.filter { it.line.id !in lineIds }
.distinctBy { it.line.id }
}

/**
* The lines that [lineIds] comment on (the SOURCE view), as [getReferencesForLines] returns its
* lines, in the SOURCE view's order. A line is returned once, however many links reach it.
*/
suspend fun getSourcesForLines(lineIds: Collection<Long>): List<LineReference> =
withContext(Dispatchers.IO) {
if (lineIds.isEmpty()) return@withContext emptyList()
database.linkQueriesQueries.selectSourcesByLineIds(lineIds) {
_, _, fromLineId, lineId, bookId, lineIndex, heRef, content, bookTitle, categoryId, bookOrderIndex ->
lineReference(
ConnectionType.SOURCE.name, fromLineId, lineId, bookId, lineIndex, heRef, content, bookTitle, categoryId,
bookOrderIndex,
)
}.executeAsList()
.distinctBy { it.line.id }
}

private fun lineReference(
connectionType: String,
fromLineId: Long,
lineId: Long,
bookId: Long,
lineIndex: Long,
heRef: String?,
content: String,
bookTitle: String,
categoryId: Long,
bookOrderIndex: Long,
) = LineReference(
connectionType = ConnectionType.fromString(connectionType),
fromLineId = fromLineId,
line = Line(id = lineId, bookId = bookId, lineIndex = lineIndex.toInt(), content = content, heRef = heRef),
bookTitle = bookTitle,
categoryId = categoryId,
bookOrderIndex = bookOrderIndex.toInt(),
)

/**
* Lightweight variant for prefetch/navigation use cases; omits target text content.
* When [includeSources] is false (default), only forward links are returned — callers
Expand Down Expand Up @@ -2984,3 +3038,14 @@ data class CommentarySummary(
val link: Link,
val targetBookTitle: String
)

/** A line a cross-reference link reaches, with what its book's grouping needs. */
data class LineReference(
val connectionType: ConnectionType,
/** The line of the request this link starts from. */
val fromLineId: Long,
val line: Line,
val bookTitle: String,
val categoryId: Long,
val bookOrderIndex: Int,
)
Original file line number Diff line number Diff line change
Expand Up @@ -343,3 +343,37 @@ WHERE l.targetBookId = ?
AND l.sourceBookId != l.targetBookId
GROUP BY l.sourceBookId, b.title, a.name
ORDER BY MAX(l.isDeclaredBase) DESC, b.isBaseBook DESC, b.orderIndex, b.title;

-- The cross-reference links of lines: the line on the other side of each link, with its book.
-- REFERENCE and MESORAT_HASHAS are unoriented (stored once): both directions. EIN_MISHPAT runs from
-- a line to the codes that rule on it: forward only, its reverse being the SOURCE view.
selectReferencesByLineIds:
SELECT l.id AS linkId, ct.name AS connectionType, l.sourceLineId AS fromLineId, ol.id AS lineId, ol.bookId, ol.lineIndex, ol.heRef, ol.content,
b.title AS bookTitle, b.categoryId, b.orderIndex AS bookOrderIndex
FROM link l
JOIN connection_type ct ON l.connectionTypeId = ct.id
JOIN line ol ON ol.id = l.targetLineId
JOIN book b ON b.id = ol.bookId
WHERE ct.name IN ('REFERENCE', 'MESORAT_HASHAS', 'EIN_MISHPAT') AND l.sourceLineId IN ?
UNION ALL
SELECT l.id AS linkId, ct.name AS connectionType, l.targetLineId AS fromLineId, ol.id AS lineId, ol.bookId, ol.lineIndex, ol.heRef, ol.content,
b.title AS bookTitle, b.categoryId, b.orderIndex AS bookOrderIndex
FROM link l
JOIN connection_type ct ON l.connectionTypeId = ct.id
JOIN line ol ON ol.id = l.sourceLineId
JOIN book b ON b.id = ol.bookId
WHERE ct.name IN ('REFERENCE', 'MESORAT_HASHAS') AND l.targetLineId IN ?;

-- The SOURCE view of lines in the shape of selectReferencesByLineIds: the lines these lines comment
-- on, with their book, in the SOURCE view's order (declared bases first, then base books, then catalog).
selectSourcesByLineIds:
SELECT l.id AS linkId, ct.name AS connectionType, l.targetLineId AS fromLineId, ol.id AS lineId, ol.bookId, ol.lineIndex, ol.heRef, ol.content,
b.title AS bookTitle, b.categoryId, b.orderIndex AS bookOrderIndex
FROM link l
JOIN connection_type ct ON l.connectionTypeId = ct.id
JOIN line ol ON ol.id = l.sourceLineId
JOIN book b ON b.id = ol.bookId
WHERE l.targetLineId IN ?
AND ct.name IN ('COMMENTARY','SUPER_COMMENTARY','TARGUM','MIDRASH','PARSHANUT','DIBUR_HAMATCHIL','EIN_MISHPAT')
AND l.sourceBookId != l.targetBookId
ORDER BY l.isDeclaredBase DESC, b.isBaseBook DESC, b.orderIndex, ol.lineIndex;
Loading