我正在尝试在我的iOS应用程序中实现一个非常简单的功能:将文件压缩到Documents
文件夹中。我写了以下FileManager
扩展名:
extension FileManager {
func zipFile(url: URL, deleteOriginal: Bool = false) {
guard let fileData = try? Data(contentsOf: url) else { return }
let nsdata = fileData as NSData
let zipped: NSData
zipped = (try? nsdata.compressed(using: .zlib)) ?? nsdata
let zip = zipped as Data
let zipUrl = url.deletingPathExtension().appendingPathExtension("zip")
try? FileManager.default.removeItem(at: zipUrl)
try? zip.write(to: zipUrl)
if deleteOriginal {
try? FileManager.default.removeItem(at: url)
}
}
}
但是,创建的文件似乎已损坏。
我进入Xcode-> Window-> 设备和模拟器,选择我的设备,然后在其下面的列表中选择我的应用程序,单击列表下的齿轮按钮,然后单击在下载容器...上查看文件。然后,我打开下载的软件包的内容并检查Documents文件夹-文件夹中有创建的zip文件。但是,我无法打开它。默认情况下,Mac创建的文件扩展名为zip.cpgz
,通常在文件损坏时会这样做。其他提取器应用程序显示一条错误消息,告知文件已损坏。当我尝试使用unzip
在终端中打开它时,看到以下消息:
iMac:Downloads user$ unzip myzip.zip
Archive: myzip.zip
End-of-central-directory signature not found. Either this file is not
a zipfile, or it constitutes one disk of a multi-part archive. In the
latter case the central directory and zipfile comment will be found on
the last disk(s) of this archive.
unzip: cannot find zipfile directory in one of myzip.zip or
myzip.zip.zip, and cannot find myzip.zip.ZIP, period.
我不仅尝试了NSData.compressed
,还尝试了一个名为DataCompression的库,还使用here中的Apple指令实现了“我自己”的压缩。在所有情况下,文件都以相同的方式损坏。
我还尝试调试代码,在调试器中显示压缩的Data对象,并将其导出为文件。再次以相同的症状损坏。
我做错什么了吗?请让我知道如何将内容压缩并保存到文件,而不仅仅是[NS] Data,就像在StackOverflow中的大多数答案中一样。
ZIP是一种存档文件格式,它还支持压缩(但它也可以包含未压缩的文件)。
ZIP归档文件不仅仅包含压缩文件的内容。它还维护所有文件,目录和符号链接的索引。该索引称为中央目录,并附加到文件末尾。此外,存档中的每个文件还附带了一些元数据。此本地文件头包含诸如文件创建日期,文件属性,文件路径等信息。您可以找到ZIP格式here的完整规范。
我发布了一个可用于在Swift中处理ZIP存档的小型框架:https://github.com/weichsel/ZIPFoundation
使用此框架,您可以使用以下代码从单个文件创建档案:
let fileManager = FileManager()
let currentWorkingPath = fileManager.currentDirectoryPath
var sourceURL = URL(fileURLWithPath: currentWorkingPath)
sourceURL.appendPathComponent("file.txt")
var destinationURL = URL(fileURLWithPath: currentWorkingPath)
destinationURL.appendPathComponent("archive.zip")
do {
try fileManager.zipItem(at: sourceURL, to: destinationURL)
} catch {
print("Creation of ZIP archive failed with error:\(error)")
}