1

I'm saving Images in Documents Directory and I allow user to edit Images, so if user want to change Image, I'm deleting previous image and then I'm saving new one. At the same path.

There is my deleting function:

func deleteItemInDirectory(imageName: String) {
    let fileManager = FileManager.default
    let imagePath = (self.getDirectoryPath() as NSString).appendingPathComponent(imageName)
    do {
        if fileManager.fileExists(atPath: imagePath) {
            try fileManager.removeItem(atPath: imagePath)
            print("Confirmed")
        }
        else {
            print("nothing happened")
        }
    }
    catch let error as NSError {
        print("An error took place: \(error)")
    }
}

And there is function when I'm trying to overwrite image:

func saveItem() {
    if self.nick != ""{
        self.ShowingEmptyFieldsAlert = false
        let imageName = self.user.imageName!

        self.user.name = self.nick
        self.user.birthday = self.birthday
        if self.pickedImage != nil {
            ImageToDirectory().deleteItemInDirectory(imageName: imageName)
            ImageToDirectory().saveImageToDocumentDirectory(image: self.pickedImage!, filename: imageName)
        }

        try? self.moc.save()
        self.presentationMode.wrappedValue.dismiss()
    }
    else {
        self.ShowingEmptyFieldsAlert = true
    }

When I'm changing image, print("Confirmed") is on Console.

And I've thought it works fine, because User can see new image and this image is shown for user. But When I go to iPhone Data settings, I can see whenever I change image, my App Data is growing. Now I have 100mb of data.

Why It doesn't work properly?

Jawad Ali
  • 13,556
  • 3
  • 32
  • 49
Maciekx7
  • 135
  • 1
  • 8

2 Answers2

2

At first you can see the size of the directory using below function to see what is happening there

func directorySize(url: URL) -> Int64 {
    let contents: [URL]
    do {
        contents = try FileManager.default.contentsOfDirectory(at: url, includingPropertiesForKeys: [.fileSizeKey, .isDirectoryKey])
    } catch {
        return 0
    }

    var size: Int64 = 0

    for url in contents {
        let isDirectoryResourceValue: URLResourceValues
        do {
            isDirectoryResourceValue = try url.resourceValues(forKeys: [.isDirectoryKey])
        } catch {
            continue
        }

        if isDirectoryResourceValue.isDirectory == true {
            size += directorySize(url: url)
        } else {
            let fileSizeResourceValue: URLResourceValues
            do {
                fileSizeResourceValue = try url.resourceValues(forKeys: [.fileSizeKey])
            } catch {
                continue
            }

            size += Int64(fileSizeResourceValue.fileSize ?? 0)
        }
    }
    return size
}

Also Create Temp Folder in Document Directory

func getDocumentsDirectory() -> URL {
        //        let paths = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)
        //        return paths[0]

        let fileManager = FileManager.default
        if let tDocumentDirectory = fileManager.urls(for: .documentDirectory, in: .userDomainMask).first {
            let filePath =  tDocumentDirectory.appendingPathComponent("MY_TEMP")
            if !fileManager.fileExists(atPath: filePath.path) {
                do {
                    try fileManager.createDirectory(atPath: filePath.path, withIntermediateDirectories: true, attributes: nil)
                } catch {
                    NSLog("Couldn't create folder in document directory")
                    NSLog("==> Document directory is: \(filePath)")
                    return fileManager.urls(for: .documentDirectory, in: .userDomainMask).first!
                }
            }

            NSLog("==> Document directory is: \(filePath)")
            return filePath
        }
        return fileManager.urls(for: .documentDirectory, in: .userDomainMask).first!

    }

Remove Files From Temp Directory:

func clearAllFilesFromTempDirectory(){        
        let fileManager = FileManager.default
        do {
            let strTempPath = getDocumentsDirectory().path
            let filePaths = try fileManager.contentsOfDirectory(atPath: strTempPath)
            for filePath in filePaths {
                try fileManager.removeItem(atPath: strTempPath + "/" + filePath)
            }
        } catch {
            print("Could not clear temp folder: \(error)")
        }
    }
Jawad Ali
  • 13,556
  • 3
  • 32
  • 49
  • OK, I've used Your directorySize() function and It says that App directory works properly - when I pick smaller photo, directorySize() is smaller, not bigger. So why My DataApp (in iPhone settings) is growing and growing despite the fact that photos are deleted correctly? – Maciekx7 Dec 29 '19 at 17:15
  • are you using temp folder ? – Jawad Ali Dec 29 '19 at 17:20
  • I've used temp folder and still DataApp is growing after changing image. It's a problem with saveItem() function, because if I want to delete whole userProfile, photo is definitely deleted, (I'm using the same function). But in changing picture, image is still existing somewhere – Maciekx7 Dec 29 '19 at 17:36
  • It's great that you suggest to prefer the URL related API. But why not with `contentsOfDirectory(atPath`, `removeItem(atPath` and `createDirectory(atPath`. There are also equivalent APIs which take URL parameters. Then you can get rid of ugly *` + "/" + `* concatenation. – vadian Dec 29 '19 at 19:03
0

Problem solved!

My functions are working fine. I found that every picked photo (from UIPicker) is saved in tmp folder in my app.

A solution to this is cleaning tmp folder: [How to remove tmp directory files of an ios app?

Maciekx7
  • 135
  • 1
  • 8