You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何取消正在进行中的CloudKit保存/上传操作

如何取消正在进行的CloudKit保存/上传操作

可以主动取消正在进行的CloudKit上传/保存任务,针对你代码里用到的两种不同API,处理方式有区别:

1. 针对database.save(_:completionHandler:)便捷API

  • 这个系统封装的便捷方法没有对外暴露可取消的操作对象,一旦调用发起就无法主动终止。
  • 如果你的业务场景需要支持中途取消上传(比如用户关闭页面、主动终止上传),不要使用这个API,替换为CKModifyRecordsOperation实现保存逻辑即可。

2. 针对CKModifyRecordsOperation实现的上传

  • 这个操作类继承自Operation,原生自带cancel()方法,可以随时终止正在执行的上传任务,完全满足你关闭VC时终止上传的需求。

正确实现示例

首先修正你的保存逻辑,去掉重复的便捷save调用,保留operation相关实现:

let database = CKContainer.default().publicCloudDatabase
// 用强引用持有当前上传操作,VC销毁时可以访问到
var currentUploadOperation: CKModifyRecordsOperation?

func save(videoURL: URL) {
    let record = CKRecord(recordType: "MyType")
    let fileURL = URL(fileURLWithPath: videoURL.path)
    let asset = CKAsset(fileURL: fileURL)
    record["videoAsset"] = asset

    // 初始化操作
    let operation = CKModifyRecordsOperation(recordsToSave: [record], recordIDsToDelete: nil)
    operation.savePolicy = .allKeys
    // 可选:设置操作的质量优先级,上传大文件建议设为utility
    operation.qualityOfService = .utility
    
    operation.modifyRecordsCompletionBlock = { [weak self] (savedRecordIDs, deletedRecordsIDs, error) in
        // 页面销毁后回调触发时直接返回
        guard let self = self else { return }
        // 先判断错误类型
        if let ckError = error as? CKError, ckError.code == .operationCancelled {
            // 主动取消触发的回调,直接忽略,不做错误提示
            self.currentUploadOperation = nil
            return
        }
        // 这里处理正常的保存成功、非取消类失败逻辑
        if let err = error {
            // 处理其他业务错误
            return
        }
        // 保存成功逻辑
        self.currentUploadOperation = nil
    }

    currentUploadOperation = operation
    database.add(operation)
}

在VC销毁、或者用户主动触发取消操作时,调用取消方法即可:

// 统一的取消方法,可以在用户点击关闭/返回按钮、deinit时调用
func cancelCurrentUpload() {
    currentUploadOperation?.cancel()
    currentUploadOperation = nil
}

// 页面销毁时自动取消未完成的上传
deinit {
    cancelCurrentUpload()
}

注意事项

  • 调用cancel()后,已经上传到CloudKit服务器的文件分片不会回滚,但后续上传流程会立刻终止,不会继续占用用户带宽、产生额外流量。
  • 取消操作后,操作的completion回调一定会触发,返回CKError.operationCancelled类型的错误,必须在回调里单独判断这个错误,不要给用户弹出"上传失败"类的提示。
  • 不要同时调用便捷save方法和添加CKModifyRecordsOperation,会导致重复上传同一份数据。

内容的提问来源于stack exchange,提问作者Lance Samaria

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.19 16:15:46