136 lines
4.7 KiB
Swift
136 lines
4.7 KiB
Swift
import XCTest
|
|
@testable import AIStudyApp
|
|
|
|
final class ReadingPositionAdapterTests: XCTestCase {
|
|
|
|
private func makeValue(
|
|
type: String?,
|
|
blockId: String? = nil,
|
|
blockProgress: Float? = nil,
|
|
lineNumber: UInt32? = nil,
|
|
pageNumber: UInt32? = nil,
|
|
scrollProgress: Float? = nil,
|
|
pageProgress: Float? = nil,
|
|
overallProgress: Float? = nil,
|
|
zoomScale: Float? = nil,
|
|
offsetX: Float? = nil,
|
|
offsetY: Float? = nil,
|
|
chapterId: String? = nil,
|
|
chapterProgress: Float? = nil
|
|
) -> ReadingPositionValue {
|
|
ReadingPositionValue(
|
|
type: type,
|
|
pageNumber: pageNumber,
|
|
blockId: blockId,
|
|
blockProgress: blockProgress,
|
|
scrollProgress: scrollProgress,
|
|
lineNumber: lineNumber,
|
|
pageProgress: pageProgress,
|
|
overallProgress: overallProgress,
|
|
zoomScale: zoomScale,
|
|
offsetX: offsetX,
|
|
offsetY: offsetY,
|
|
chapterId: chapterId,
|
|
chapterProgress: chapterProgress,
|
|
offset: nil,
|
|
percent: nil,
|
|
section: nil
|
|
)
|
|
}
|
|
|
|
func test_fromValue_markdown_with_blockId() {
|
|
let v = makeValue(type: "Markdown", blockId: "b1", scrollProgress: 0.5)
|
|
let pos = ReadingPositionAdapter.fromValue(v)
|
|
guard case let .markdown(blockId, scrollProgress) = pos else {
|
|
return XCTFail("Expected .markdown, got \(String(describing: pos))")
|
|
}
|
|
XCTAssertEqual(blockId, "b1")
|
|
XCTAssertEqual(scrollProgress, 0.5)
|
|
}
|
|
|
|
func test_fromValue_markdown_nil_blockId_returns_nil() {
|
|
let v = makeValue(type: "Markdown")
|
|
XCTAssertNil(ReadingPositionAdapter.fromValue(v))
|
|
}
|
|
|
|
func test_fromValue_text_with_optional_fields() {
|
|
let v = makeValue(type: "Text", lineNumber: 42, scrollProgress: 0.8)
|
|
guard case let .text(lineNumber, scrollProgress) = ReadingPositionAdapter.fromValue(v) else {
|
|
return XCTFail("Expected .text")
|
|
}
|
|
XCTAssertEqual(lineNumber, 42)
|
|
XCTAssertEqual(scrollProgress, 0.8)
|
|
}
|
|
|
|
func test_fromValue_pdf_with_all_fields() {
|
|
let v = makeValue(type: "Pdf", pageNumber: 5, pageProgress: 0.3, overallProgress: 0.15)
|
|
guard case let .pdf(pageNumber, pageProgress, overallProgress) = ReadingPositionAdapter.fromValue(v) else {
|
|
return XCTFail("Expected .pdf")
|
|
}
|
|
XCTAssertEqual(pageNumber, 5)
|
|
XCTAssertEqual(pageProgress, 0.3)
|
|
XCTAssertEqual(overallProgress, 0.15)
|
|
}
|
|
|
|
func test_fromBlockScroll_markdown_returns_position() {
|
|
let blocks: [DocumentBlock] = [
|
|
.heading(id: "h1", level: 1, text: "Title"),
|
|
.paragraph(id: "p1", text: "Content"),
|
|
]
|
|
let pos = ReadingPositionAdapter.fromBlockScroll(
|
|
materialType: .markdown, blocks: blocks, scrollProgress: 0.5, blockIndex: 0
|
|
)
|
|
guard case .block(let blockId, let blockProgress, let overallProgress) = pos else {
|
|
return XCTFail("Expected .block")
|
|
}
|
|
XCTAssertEqual(blockId, "h1")
|
|
XCTAssertEqual(blockProgress, 0.5)
|
|
XCTAssertEqual(overallProgress, 0.5)
|
|
}
|
|
|
|
func test_blockIdForRestore_prefers_existing_blockId() {
|
|
let blocks: [DocumentBlock] = [
|
|
.heading(id: "h1", level: 1, text: "Title"),
|
|
.paragraph(id: "p1", text: "Content"),
|
|
.paragraph(id: "p2", text: "Tail"),
|
|
]
|
|
|
|
let restored = ReadingPositionAdapter.blockIdForRestore(
|
|
from: .block(blockId: "p1", blockProgress: 0.25, overallProgress: 0.8),
|
|
in: blocks
|
|
)
|
|
|
|
XCTAssertEqual(restored, "p1")
|
|
}
|
|
|
|
func test_blockIdForRestore_fallsBack_to_progress_when_blockId_missing() {
|
|
let blocks: [DocumentBlock] = [
|
|
.heading(id: "h1", level: 1, text: "Title"),
|
|
.paragraph(id: "p1", text: "Content"),
|
|
.paragraph(id: "p2", text: "Tail"),
|
|
]
|
|
|
|
let restored = ReadingPositionAdapter.blockIdForRestore(
|
|
from: .block(blockId: "missing", blockProgress: 0.1, overallProgress: 0.9),
|
|
in: blocks
|
|
)
|
|
|
|
XCTAssertEqual(restored, "p2")
|
|
}
|
|
|
|
func test_blockIdForRestore_text_out_of_range_fallsBack_to_scroll_progress() {
|
|
let blocks: [DocumentBlock] = [
|
|
.heading(id: "h1", level: 1, text: "Title"),
|
|
.paragraph(id: "p1", text: "Content"),
|
|
.paragraph(id: "p2", text: "Tail"),
|
|
]
|
|
|
|
let restored = ReadingPositionAdapter.blockIdForRestore(
|
|
from: .text(lineNumber: 99, scrollProgress: 0.45),
|
|
in: blocks
|
|
)
|
|
|
|
XCTAssertEqual(restored, "p1")
|
|
}
|
|
}
|