Aggiunge bitrate adattivo con qualità minima da regia e telemetria del telefono.
L'encoder scende in congestione e risale piano; la regia imposta il pavimento, mostra lo stato del telefono e apre il selettore dal bitrate colorato. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -0,0 +1,92 @@
|
||||
import XCTest
|
||||
@testable import MatchLiveTv
|
||||
|
||||
final class AdaptiveBitrateTests: XCTestCase {
|
||||
private func controller() -> AdaptiveBitrateController {
|
||||
let abr = AdaptiveBitrateController()
|
||||
abr.configure(ceiling: 2_500_000, floor: AdaptiveBitrateController.autoFloor)
|
||||
return abr
|
||||
}
|
||||
|
||||
func testCongestionDropsTowardMeasuredAndRespectsFloor() {
|
||||
let abr = controller()
|
||||
let next = abr.onCongestion(measuredBitsPerSecond: 1_200_000)
|
||||
XCTAssertEqual(next, 1_200_000 - 128_000)
|
||||
XCTAssertEqual(abr.currentBitrate, 1_072_000)
|
||||
}
|
||||
|
||||
func testCongestionDoesNotGoBelowFloor() {
|
||||
let abr = controller()
|
||||
abr.setFloor(1_500_000)
|
||||
let next = abr.onCongestion(measuredBitsPerSecond: 400_000)
|
||||
XCTAssertEqual(next, 1_500_000)
|
||||
}
|
||||
|
||||
func testHealthyRampsUpAfterEnoughSamples() {
|
||||
let abr = controller()
|
||||
abr.onCongestion(measuredBitsPerSecond: 1_200_000)
|
||||
for _ in 0..<7 {
|
||||
XCTAssertNil(abr.onHealthy())
|
||||
}
|
||||
XCTAssertEqual(abr.onHealthy(), 1_072_000 + 250_000)
|
||||
}
|
||||
|
||||
func testThermalCeilingClampsCurrent() {
|
||||
let abr = controller()
|
||||
let applied = abr.setCeiling(1_250_000)
|
||||
XCTAssertEqual(applied, 1_250_000)
|
||||
XCTAssertEqual(abr.ceiling, 1_250_000)
|
||||
XCTAssertLessThanOrEqual(abr.floor, abr.ceiling)
|
||||
}
|
||||
|
||||
func testMinFloorBumpsCurrentUp() {
|
||||
let abr = controller()
|
||||
abr.onCongestion(measuredBitsPerSecond: 1_200_000)
|
||||
XCTAssertEqual(abr.setFloor(2_000_000), 2_000_000)
|
||||
}
|
||||
|
||||
func testAutoOptionsExclude1080On720Session() {
|
||||
XCTAssertEqual(
|
||||
StreamQualityLadder.availableIds(sessionQualityPreset: "720p_30_2.5mbps"),
|
||||
[
|
||||
StreamQualityLadder.auto,
|
||||
"720p_30_1.5mbps",
|
||||
"720p_30_2.5mbps",
|
||||
"720p_30_4mbps"
|
||||
]
|
||||
)
|
||||
}
|
||||
|
||||
func testMeasuredZeroWithoutCongestionDoesNotDrop() {
|
||||
let abr = controller()
|
||||
XCTAssertNil(abr.onMeasured(measuredBitsPerSecond: 0, congested: false))
|
||||
XCTAssertEqual(abr.currentBitrate, 2_500_000)
|
||||
}
|
||||
|
||||
func testMeasuredLowThroughputDropsWithoutCongestionFlag() {
|
||||
let abr = controller()
|
||||
XCTAssertEqual(
|
||||
abr.onMeasured(measuredBitsPerSecond: 1_200_000, congested: false),
|
||||
1_200_000 - 128_000
|
||||
)
|
||||
}
|
||||
|
||||
func testThermalDropThenRecoverRestoresUserFloor() {
|
||||
let abr = controller()
|
||||
abr.setFloor(1_500_000)
|
||||
abr.setCeiling(1_000_000)
|
||||
XCTAssertEqual(abr.floor, 1_000_000)
|
||||
abr.setCeiling(2_500_000)
|
||||
XCTAssertEqual(abr.floor, 1_000_000)
|
||||
XCTAssertEqual(abr.setFloor(1_500_000), 1_500_000)
|
||||
}
|
||||
|
||||
func testEncoderCeilingRisesWhenMinExceedsSessionTarget() {
|
||||
let ceiling = StreamQualityLadder.encoderCeiling(
|
||||
sessionTarget: 2_500_000,
|
||||
minPresetId: "720p_30_4mbps"
|
||||
)
|
||||
XCTAssertEqual(ceiling, 4_000_000)
|
||||
XCTAssertEqual(StreamQualityLadder.encoderFloor(minPresetId: "720p_30_4mbps", ceiling: ceiling), 4_000_000)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user