簡體   English   中英

將縮略圖附加到通知時,文件去哪兒了?

[英]When attaching thumbnails to notifications, where does the file go?

我正在向豐富的通知添加縮略圖。 我生成要用作附件的圖像,如下所示:

let url = URL(fileURLWithPath: NSTemporaryDirectory(), isDirectory: true)
let fileURL = url.appendingPathComponent("someImageName", isDirectory: false).appendingPathExtension("png")
do{
    try UIImagePNGRepresentation(image)?.write(to: fileURL)
}catch{
    print("Could not write: ", error)
}

這是成功的。 如果我現在運行此代碼:

let content = try? FileManager.default.contentsOfDirectory(atPath: NSTemporaryDirectory())
print(content ?? "error")

它打印出這個: ["someImageName.png"]

然后我創建附件,如下所示:

let attachment = try? UNNotificationAttachment(identifier: "image", url: url, options: nil)
let content = UNMutableNotificationContent()
content.title = "Test"
content.attachments = [attachment!]
let request = UNNotificationRequest(identifier: "someID", content:content, trigger: /*someTrigger*/)
UNUserNotificationCenter.current().add(request, withCompletionHandler:...)

這一切都在起作用。 發送通知,並附加附件。 但是如果我現在打印出我的臨時文件夾的內容,它是空的! 我之前保存的圖像已從此文件夾中刪除。

經過大量的反復試驗,我發現在我添加通知時圖像已被刪除。 為什么我的通知會刪除我的圖片? 我找不到任何關於此的文檔!

如果我做了以上所有操作,但注釋掉這一行: //content.attachments = [attachment!] ,這意味着我存儲的圖像不會作為附件添加到我的通知中,那么我的圖像不會從臨時文件夾中刪除!

這些文件在使用后會被清理嗎? 或者我是否必須在通知消失后查看不同的文件夾並手動清理它們? 我不希望我的應用程序創建數百個永遠不會再使用的圖像,而無法刪除它們。

這些天我面臨同樣的問題,答案在文檔中,乍一看不是很容易,但它就在那里:

關於UNNotificationAttachment

...驗證后,附加文件將移入附件數據存儲,以便所有適當的進程都可以訪問它們。

關於 init 方法:

當您安排包含附件的通知請求時,附件的文件將移動到新位置以方便適當進程訪問。 移動后,訪問文件的唯一方法是使用 UNUserNotificationCenter 對象的方法。

請注意:

位於應用程序包內的附件被復制而不是移動。

所以我決定:

像您一樣編寫文件並在NSTemporaryDirectory()NSTemporaryDirectory()它的副本我使用這個示例輕松創建和刪除 TempDirectory (Swift 4.0)(感謝Ole Begemman ):

import Foundation

/// A wrapper around a temporary file in a temporary directory. The directory
/// has been especially created for the file, so it's safe to delete when you're
/// done working with the file.
///
/// Call `deleteDirectory` when you no longer need the file.
struct TemporaryFile {
    let directoryURL: URL
    let fileURL: URL
    /// Deletes the temporary directory and all files in it.
    let deleteDirectory: () throws -> Void
    
    /// Creates a temporary directory with a unique name and initializes the
    /// receiver with a `fileURL` representing a file named `filename` in that
    /// directory.
    ///
    /// - Note: This doesn't create the file!
    init(creatingTempDirectoryForFilename filename: String) throws {
        let (directory, deleteDirectory) = try FileManager.default
            .urlForUniqueTemporaryDirectory()
        self.directoryURL = directory
        self.fileURL = directory.appendingPathComponent(filename)
        self.deleteDirectory = deleteDirectory
    }
}

extension FileManager {
    /// Creates a temporary directory with a unique name and returns its URL.
    ///
    /// - Returns: A tuple of the directory's URL and a delete function.
    ///   Call the function to delete the directory after you're done with it.
    ///
    /// - Note: You should not rely on the existence of the temporary directory
    ///   after the app is exited.
    func urlForUniqueTemporaryDirectory(preferredName: String? = nil) throws
        -> (url: URL, deleteDirectory: () throws -> Void)
    {
        let basename = preferredName ?? UUID().uuidString
        
        var counter = 0
        var createdSubdirectory: URL? = nil
        repeat {
            do {
                let subdirName = counter == 0 ? basename : "\(basename)-\(counter)"
                let subdirectory = temporaryDirectory
                    .appendingPathComponent(subdirName, isDirectory: true)
                try createDirectory(at: subdirectory, withIntermediateDirectories: false)
                createdSubdirectory = subdirectory
            } catch CocoaError.fileWriteFileExists {
                // Catch file exists error and try again with another name.
                // Other errors propagate to the caller.
                counter += 1
            }
        } while createdSubdirectory == nil
        
        let directory = createdSubdirectory!
        let deleteDirectory: () throws -> Void = {
            try self.removeItem(at: directory)
        }
        return (directory, deleteDirectory)
    }
}

使用 TempURL 附加文件后,文件將被移動,您可以刪除 TempDirectory。

后來進行了一些測試,可以肯定的是,我終於發現我的文件(在我的情況下是圖像)存儲在這里:

URL: file:///var/mobile/Library/SpringBoard/PushStore/Attachments/com.YourApp.Name/8e52c6673f6e735f83535486bf750ba1118a3ade.png

提交或清理通知中心后,文件被刪除是。

為什么這一切? -> 沙盒! 當我將我的文件附加到觸發器(此處為 UNCalendarNotificationTrigger)時,我將負責我的文件的日歷命名為在我的通知中顯示它,但要處理它,它必須將文件放在 HIS 目錄中。

希望它有所幫助,我花了一段時間才找到所有的奧秘!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM