首页 > 解决方案 > 将媒体存储到 CloudKit 作为 CKAsset 仅适用于图像,不再适用于视频

问题描述

我在将视频作为 CKAsset 保存到 CloudKit 时遇到问题。虽然下面的示例代码仅用于保存图像(将 videoSelection 设置为 false),但我过去也可以使用它来将视频存储到 CloudKit。我目前正在使用 XCode 11.3 和 Swift 编程语言以及安装了 iOS 13.2 的模拟器和物理设备。调试器表明在选择具有完整 URL 的视频后,在 func imagePickerController 中正确检索了 Asset 数据。尝试将视频 CKAsset 数据写入 iCloud 时,会生成一条错误消息,包括“连接到名为 com.apple.cloudd 的 pid 0 上的服务”。

import UIKit
import CloudKit
import AVKit
import AVFoundation

class ViewController: UIViewController, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
 let videoSelection: Bool =  false //if true, then select video, if false select image
 var SelectedAsset: CKAsset? = nil
 var imagePicker = UIImagePickerController()

    func iCloud_WriteRecord()
       {
        let newCloudRecord = CKRecord (recordType: "TestRecordType", recordID: CKRecord.ID (recordName: "myRecordID0001"))
        newCloudRecord.setValue (SelectedAsset, forKey: "CKAssetField")
        CKContainer(identifier: "iCloud.CLCO.INT45.Activity01").privateCloudDatabase.save (newCloudRecord) { (record, error) in

            if record != nil {
                   if (error != nil) {
                       print("error 1")
                       return;
                   }

                   print("success")
               }
               else
               {
                   print("error 2")
                   return;
               }

           }
       }

    @IBAction func SelectImageOrMedia(_ sender: UIButton) {

        if videoSelection {imagePicker.mediaTypes = ["public.movie"]} else {imagePicker.mediaTypes = ["public.image"]}

        imagePicker.sourceType =  .photoLibrary
        imagePicker.delegate = self
        imagePicker.allowsEditing = true
        present (imagePicker, animated: true, completion: nil)

    }

          func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any])
           {

               if let image = info[UIImagePickerController.InfoKey.editedImage]
                   as? UIImage //image
               {
                let mediaAsset = CKAsset(fileURL: info[UIImagePickerController.InfoKey.imageURL] as! URL)
                SelectedAsset = mediaAsset
                imagePicker.dismiss(animated: true, completion: nil)
                return;

               }
               else //video
               {

                let mediaAsset = CKAsset(fileURL: info[UIImagePickerController.InfoKey.mediaURL] as! URL)
                let tmpVideoURL: String = mediaAsset.fileURL!.absoluteString
                SelectedAsset = mediaAsset
                imagePicker.dismiss(animated: true, completion: nil)

                return;
               }


           } //func

    @IBAction func SaveTestRecord(_ sender: UIButton) {

               iCloud_WriteRecord()
    }

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view.
    }
}

我可以通过在 CloudKit 仪表板上验证在执行 SelectImageOrMedia()、imagePickerController() 和 iCloud_WriteRecord( ) 以该顺序。当对视频尝试相同的操作时(使用 videoSelection=true),调试器确实表明 mediaAsset (CKAsset) 已使用完整的 url-path 正确初始化。但是,在代码中使用 iCloud_WriteRecord() 写入视频资产的任何尝试都会在不存储记录的情况下生成以下错误消息:

操作 2676FFA25279B538 出现连接错误:错误域 = NSCocoaErrorDomain 代码 = 4097 “连接到名为 com.apple.cloudd 的 pid 0 上的服务” UserInfo={NSDebugDescription=连接到名为 com.apple.cloudd 的 pid 0 上的服务}

上面描述的技术以前曾经工作过,不仅适用于图像,也适用于视频。

任何解决此问题的帮助将不胜感激!

标签: videouiimagepickercontrollercloudkitpidckasset

解决方案


我能够自己弄清楚如何解决这个问题。事实证明,资产文件在资产被分派之前就被自动删除了。在初始化资产之前将视频文件(通过代码)复制到非临时位置就可以了。该解决方案似乎适用于模拟器和物理设备。


推荐阅读