rainbow-dragon/Tests/ForgeCameraTests/ArriSimTests.swift

107 lines
4.1 KiB
Swift
Raw Normal View History

import XCTest
import Foundation
#if canImport(FoundationNetworking)
import FoundationNetworking
#endif
@testable import ForgeSim
final class ArriSimTests: XCTestCase {
var sim: ArriSimulator!
override func setUp() async throws {
sim = ArriSimulator()
try await sim.start(port: 0) // ephemeral
}
override func tearDown() async throws {
try await sim.stop()
sim = nil
}
func get(_ path: String) async throws -> (Int, Data) {
let port = await sim.boundPort!
let url = URL(string: "http://127.0.0.1:\(port)\(path)")!
let (data, resp) = try await URLSession.shared.data(from: url)
return ((resp as! HTTPURLResponse).statusCode, data)
}
func put(_ path: String, body: Data) async throws -> (Int, Data) {
let port = await sim.boundPort!
var req = URLRequest(url: URL(string: "http://127.0.0.1:\(port)\(path)")!)
req.httpMethod = "PUT"
req.httpBody = body
let (data, resp) = try await URLSession.shared.data(for: req)
return ((resp as! HTTPURLResponse).statusCode, data)
}
// System info endpoint serves model + serial JSON.
func testSystemInfo() async throws {
let (status, data) = try await get("/api/v1/system/info")
XCTAssertEqual(status, 200)
let obj = try JSONSerialization.jsonObject(with: data) as? [String: Any]
XCTAssertEqual(obj?["model"] as? String, "ALEXA 35")
XCTAssertNotNil(obj?["serialNumber"])
}
// Rec state reflects scripted changes.
func testRecStateScriptable() async throws {
var (_, data) = try await get("/api/v1/recording/status")
var obj = try JSONSerialization.jsonObject(with: data) as? [String: Any]
XCTAssertEqual(obj?["recording"] as? Bool, false)
await sim.setRecording(true, clipName: "A001C003_250710_R1CD")
(_, data) = try await get("/api/v1/recording/status")
obj = try JSONSerialization.jsonObject(with: data) as? [String: Any]
XCTAssertEqual(obj?["recording"] as? Bool, true)
XCTAssertEqual(obj?["clipName"] as? String, "A001C003_250710_R1CD")
}
// Metadata endpoint.
func testMetadata() async throws {
await sim.setMetadata(ei: 1280, wb: 3200, tint: -2, fps: 25, timecode: "10:20:30:12")
let (status, data) = try await get("/api/v1/camera/metadata")
XCTAssertEqual(status, 200)
let obj = try JSONSerialization.jsonObject(with: data) as? [String: Any]
XCTAssertEqual(obj?["exposureIndex"] as? Int, 1280)
XCTAssertEqual(obj?["whiteBalance"] as? Int, 3200)
XCTAssertEqual(obj?["tint"] as? Int, -2)
XCTAssertEqual(obj?["timecode"] as? String, "10:20:30:12")
}
// Look upload stored and retrievable.
func testLookUploadStored() async throws {
let payload = try JSONSerialization.data(withJSONObject: [
"name": "shot42",
"cdl": ["slope": [1.1, 1.0, 0.9], "offset": [0, 0, 0], "power": [1, 1, 1], "saturation": 1.2],
"lut3dSize": 2,
"lut3dTable": Array(repeating: 0.5, count: 24),
])
let (status, _) = try await put("/api/v1/look/current", body: payload)
XCTAssertEqual(status, 200)
let stored = await sim.uploadedLooks
XCTAssertEqual(stored.count, 1)
let storedObj = try JSONSerialization.jsonObject(with: stored[0]) as? [String: Any]
XCTAssertEqual(storedObj?["name"] as? String, "shot42")
// Retrievable over HTTP too.
let (gs, gd) = try await get("/api/v1/look/current")
XCTAssertEqual(gs, 200)
let obj = try JSONSerialization.jsonObject(with: gd) as? [String: Any]
XCTAssertEqual(obj?["name"] as? String, "shot42")
}
// Malformed look rejected 400.
func testMalformedLookRejected() async throws {
let (status, _) = try await put("/api/v1/look/current", body: Data("not json".utf8))
XCTAssertEqual(status, 400)
}
// Unknown path 404.
func testUnknownPath404() async throws {
let (status, _) = try await get("/api/v1/warp/drive")
XCTAssertEqual(status, 404)
}
}