Skip to content

Java SDK API 说明 ​

Ti 云存 API 位于 com.tange.ai.tirtc.storage,媒体帧、Output 和临时文件复用 com.tange.ai.tirtc 中的类型。

Client 与托管鉴权 ​

java
ClientOptions options = ClientOptions.builder()
    .appId(appId)
    .accessKeyId(accessKeyId)
    .accessKeySecret(accessKeySecret)
    .cacheDir(Paths.get("/absolute/path/to/cache"))
    .build();

try (CloudStorageClient client = new CloudStorageClient(options)) {
    String logId = client.uploadLogs();
}

App ID、AK/SK 和绝对 cache 路径必填。endpoint 可选。一个进程可以创建多个 CloudStorageClient,各自使用不同应用身份和 Endpoint;所有活动 Runtime 产品的 cache 路径与 console log 配置必须一致。

普通接入不要调用 endpoint(String)。只有在开通时收到其他服务地址,才把交付的完整地址原样传给这个 Builder 方法。

每次查询、Replay 和 Export 都显式接收 device ID。Runtime 按需签发和刷新设备 Token,Java API 不接收外部 Token。

父对象关闭时会取消或关闭所属操作与子资源,排空已接受的回调,并释放 Native 引用;不会影响其他 Client 或已经交给应用的临时文件。

查询录像 ​

java
CompletableFuture<List<RecordingDay>> listRecordingDays(
    String deviceId, LocalDate startDate, LocalDate endDate, ZoneId zoneId);

CompletableFuture<List<RecordingRange>> listRecordings(
    String deviceId, Instant start, Instant end);

LocalDate date = day.date();
boolean hasRecording = day.hasRecording();
Instant start = range.startTime();
Instant end = range.endTime();

RecordingDay 使用 LocalDate,单次日期查询最多覆盖包含首尾在内的 31 天。RecordingRange 使用 UTC Instant,区间左闭右开,单次范围查询最长 10 天。取消查询 Future 会请求取消 Native 操作;请求在 Native 完成或 Client 越过关闭边界前仍由 Client 持有。

Replay 与 Output ​

java
try (Replay replay = client.newReplay(deviceId, listener);
     VideoOutput video = new VideoOutput(
         replay, videoChannelId, frame -> consume(frame))) {
    replay.play(start, end);
    replay.pause();
    replay.resume();
    replay.seek(target);
    replay.setSpeed(ReplaySpeed.X2);
}

Replay 提供 play、playAt、pause、resume、seek、stop、setSpeed、speed 和 currentTime。当前进度使用 Optional<Instant>。listener 报告进度、来源耗尽、错误和确认的录像缺口。

AudioOutput、VideoOutput、EncodedAudioOutput 和 EncodedVideoOutput 都支持 Replay 来源。Channel ID 范围是 0..255。Video Output 提供同步的 takeSnapshot();Replay 通过 startRecording(StartRecordingOptions) 保存正在播放的内容。

独立导出 ​

java
try (ExportTask export = client.exportRecording(
         deviceId,
         new ExportOptions(start, end, videoChannelId, audioChannelId))) {
    ExportResult result = export.completion().toCompletableFuture().get();
    try (RecordingFile file = result.file()) {
        Files.copy(file.path(), destination);
        boolean completeCoverage = result.report().complete();
    }
}

Export 不需要 Replay。progress() 返回扫描比例和已覆盖时长。cancel() 是非阻塞的取消入口。每次 completion() 都返回独立的结果视图;取消或手工完成这个视图不会改变 ExportTask,自身结果仍可从新的视图取得。

部分可播放 MP4 会正常完成。ExportReport 包含请求范围、覆盖时长、输出片段、确认缺口、未处理范围、完整标记、终止原因和可选的 Native 错误。只有扫描完成、所选媒体没有确认缺口且没有未处理范围时,complete() 才为 true。没有可交付文件的失败通过 ExportException 返回,异常中仍包含当前报告。

请求起点落在 GOP 中间时,Runtime 可以在同一段连续录像中回看前一个安全解码点,并把预卷写入 MP4。预卷不计入 coveredDuration(),但会计入文件时长。确认缺失的来源时间不会用黑帧、重复帧或静音填充,而是从输出时间线压缩。

原始音视频诊断采集 ​

Replay 可以按 Channel ID 采集用于问题排查的原始音视频数据:

java
RawDumpOptions options = new RawDumpOptions(
    new int[] {audioChannelId},
    new int[] {videoChannelId});

try (RawDump capture = replay.startRawDump(options)) {
    // 复现问题后停止采集。
    RawDumpArchive archive = capture.stop();
}

两个 Channel ID 数组至少填写一个。停止后检查 RawDumpArchive 的 captureComplete()、stopReason()、unsavedPacketCount()、unsavedByteCount() 和 empty(),再调用 CloudStorageClient.uploadLogs() 将采集文件随下一次日志上传提交。完整流程、限制和隐私要求见接入客户端诊断能力。

临时文件、异常与释放 ​

Recording、Export 和 Snapshot 文件位于 Runtime cache。先使用标准 Java 文件 API 保存,再调用 delete() 或 close() 清理临时源文件。已交付文件独立于 Task 和 Client;关闭父对象不会删除它。

公开方法使用 TiRtcException 表示稳定错误,通过 category() 判断类别,通过 code() 取得 Runtime 原始错误码。没有可交付文件的 Export 失败使用 ExportException,并通过 report() 提供当前报告。

不要在 listener 中调用会等待同一对象树回调排空的 close()。把关闭动作交给应用线程。ExportTask.cancel() 不等待回调,可以从进度 listener 请求取消。

覆盖查询、Replay、Output、截图和导出完整能力的可运行程序见 Java API 示例。

Ti 云存开发文档