Core Transferable Error

I'm developing an app that uses the SwiftUI .photosPicker modifier to allow the user to open videos from their photos. While many videos successfully load, one video results in the following errors occurring:

Error loading com.apple.quicktime-movie: <decode: bad range for [%@] got [offs:100 len:1229 within:0]> Error loading public.movie: <decode: bad range for [%@] got [offs:87 len:1229 within:0]> "The operation couldn’t be completed. (CoreTransferable.TransferableSupportError error 0.)"

I was able to isolate the line of code within the Transferable where this occurs to be the following:

try FileManager.default.copyItem(at: received.file, to: destination)

Is there something that I can do to ensure the app can reliably open any video?

The entire transferable struct is as follows:

import Foundation

import CoreTransferable

import UniformTypeIdentifiers

struct Video: Transferable {
    let url: URL
    
    let filename: String

    static var transferRepresentation: some TransferRepresentation {
        FileRepresentation(contentType: .mpeg4Movie) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
        
        FileRepresentation(contentType: .quickTimeMovie) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
        
        FileRepresentation(contentType: .avi) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
        
        FileRepresentation(contentType: .mpeg) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
        
        FileRepresentation(contentType: .mpeg2Video) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
        
        FileRepresentation(contentType: .video) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
        
        FileRepresentation(contentType: .movie) { video in
            SentTransferredFile(video.url)
        } importing: { received in
            try Video.transfer(from: received)
        }
    }
    
    static func transfer(from received: ReceivedTransferredFile) throws -> Video {
        let destination = FileManager.default.temporaryDirectory.appendingPathComponent(received.file.lastPathComponent)
        
        if FileManager.default.fileExists(atPath: destination.path) {
            try FileManager.default.removeItem(at: destination)
        }
        
        try FileManager.default.copyItem(at: received.file, to: destination)
        
        return Video(url: destination, filename: received.file.lastPathComponent)
    }
}
Accepted Answer

While the following code should have ensured that the call to copyItem would succeed, throwing the error allowed me to see that there is still some situations were there is an existing file at the destination. As such, the new implementation below first creates a folder using a UUID, ensuring that the destination is unique every time.

if FileManager.default.fileExists(atPath: destination.path) {
    try FileManager.default.removeItem(at: destination)
}

Here is the complete version of the transfer function.

static func transfer(from received: ReceivedTransferredFile) throws -> Video {
        do {
            // note: it was necessary to create a folder with a uuidString to ensure that copying the file would not fail even though existing files are removed.
            let directory = FileManager.default.temporaryDirectory.appendingPathComponent(UUID().uuidString, isDirectory: true)
            
            try FileManager.default.createDirectory(at: directory, withIntermediateDirectories: true, attributes: nil)
            
            let destination = directory.appendingPathComponent(received.file.lastPathComponent)
            
            if FileManager.default.fileExists(atPath: destination.path) {
                try FileManager.default.removeItem(at: destination)
            }
            
            try FileManager.default.copyItem(at: received.file, to: destination)
            
            return Video(url: destination, filename: received.file.lastPathComponent)
        } catch {
            debugPrint("error transferring file: \(error)")
            
            throw error
        }
    }

While there are other approaches, the use of uuidString only has a minimal impact on the size of the temporary data and it ensures that the destination is unique.

Core Transferable Error
 
 
Q