Does not save data to documents direction - ios

I try to save data into document directory. I do not get any error but it never saves the data. Always it says "File does not exist, create it".
let fileManager = FileManager.default
if let documentsDirectory = fileManager.urls(for: .documentDirectory, in: .userDomainMask).last {
let fileURL = documentsDirectory.appendingPathComponent("example")
if fileManager.fileExists(atPath: fileURL.absoluteString) {
print("File exists")
} else {
print("File does not exist, create it")
do {
try myData.write(to: fileURL)
print("data saved")
} catch {
print(error)
}
}
}

Replace
if fileManager.fileExists(atPath: fileURL.absoluteString) {
with
if fileManager.fileExists(atPath: fileURL.path) {
Never use absoluteString in a file system URL

Related

How to copy a bundle html file to a document directory in iOS Swift?

I have been trying to save local index.html file to document directory but it does not save to local document directory.
here is my folder structure:
sampleHtml.xcodeproj
---->sampleHtml
-------->Web_Assets
------------> index.html
---->ViewController.swift
Here is the code for saving and checking file path exist is not, if path exist then overwrite it else copy the new one.
func saveHtmlDoc(){
let filemgr = FileManager.default
let docURL = filemgr.urls(for: .documentDirectory, in: .userDomainMask)[0]
let destPath = docURL.path+"/www/"
print("des path", destPath)
let sourcePath = Bundle.main.resourceURL!.appendingPathComponent("Web_Assets").path
print("sourc", sourcePath.appending("/index.html"))
//COPY Web_Assets content from Bundle to Documents/www
do {
try filemgr.removeItem(atPath: destPath)
} catch {
print("Error: \(error.localizedDescription)")
}
do {
try filemgr.copyItem(atPath: sourcePath + "/", toPath: destPath)
} catch {
print("Error: \(error.localizedDescription)")
}
}
My issue is how to save index.html file to document directory and check the file path exist are not, if exist overwrite it or copy the new one.
Any help much appreciates it...
I have just done this code in a test project which works.
You should ensure that you are performing checks along the way and ensure that your HTML file is in your Copy resources build phase
import UIKit
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
moveHtmlFile()
}
private func moveHtmlFile() {
let fileManager = FileManager.default
let documentsDirectory = fileManager.urls(for: .documentDirectory, in: .userDomainMask).first!
guard let sourcePath = Bundle.main.path(forResource: "index", ofType: "html") else {
return
}
if fileManager.fileExists(atPath: sourcePath) {
let sourceUrl = URL(fileURLWithPath: sourcePath)
try? fileManager.createDirectory(atPath: documentsDirectory.appendingPathComponent("www").path,
withIntermediateDirectories: false,
attributes: nil)
let destination = documentsDirectory.appendingPathComponent("www/index.html", isDirectory: false)
try? fileManager.copyItem(at: sourceUrl, to: destination)
if fileManager.fileExists(atPath: destination.path) {
print("file copied")
} else {
print("file copy failed")
}
}
}
}
Result:
I try and test below code, it work okey. Before add file, you need create folder first.
func saveHtmlDoc() {
let filemgr = FileManager.default
let docURL = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).first!
let destPath = URL(string:docURL)?.appendingPathComponent("www")
guard let newDestPath = destPath, let sourcePath = Bundle.main.path(forResource: "image", ofType: ".png"), let fullDestPath = NSURL(fileURLWithPath: newDestPath.absoluteString).appendingPathComponent("image.png") else { return }
//CREATE FOLDER
if !filemgr.fileExists(atPath: newDestPath.path) {
do {
try filemgr.createDirectory(atPath: newDestPath.path, withIntermediateDirectories: true, attributes: nil)
} catch {
print(error.localizedDescription);
}
}
else {
print("Folder is exist")
}
if filemgr.fileExists(atPath: fullDestPath.path) {
print("File is exist in \(fullDestPath.path)")
}
else {
do {
try filemgr.copyItem(atPath: sourcePath, toPath: fullDestPath.path)
} catch {
print("Error: \(error.localizedDescription)")
}
}
}

Can users access files directly from iOS?

I am a beginner in iOS development.
I'm copying this by looking at an example of making a file.
override func viewDidLoad() {
super.viewDidLoad()
let fileName = "Test"
let DocumentDirURL = try! FileManager.default.url(for: .documentDirectory, in: .userDomainMask, appropriateFor: nil, create: true)
let fileURL = DocumentDirURL.appendingPathComponent(fileName).appendingPathExtension("")
let writeString = "write test sting"
do {
try writeString.write(to: fileURL, atomically: true, encoding: String.Encoding.utf8)
} catch _ as NSError {
print("write error")
}
}
My question is that my current code is making and saving a file in document directory.
Can user see this file with user own eyes?
And is there anything else that I need to have permission to execute
this code?
This is an old Swift code. If there is a code that has a better way, please recommend it to me. Please help me a lot. Thank you in advance.
This will create a path of the directory you wanna saveit
let fileManager = NSFileManager.defaultManager()
let urls = fileManager.URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask)
if let documentDirectory: NSURL = urls.first as? NSURL {
// This is where the database should be in the documents directory
let finalDatabaseURL = documentDirectory.URLByAppendingPathComponent("items.db")
if finalDatabaseURL.checkResourceIsReachableAndReturnError(nil) {
// The file already exists, so just return the URL
return finalDatabaseURL
} else {
// Copy the initial file from the application bundle to the documents directory
if let bundleURL = NSBundle.mainBundle().URLForResource("items", withExtension: "db") {
let success = fileManager.copyItemAtURL(bundleURL, toURL: finalDatabaseURL, error: nil)
if success {
return finalDatabaseURL
} else {
println("Cant found!")
}
} else {
println("Couldn't find !")
}
}
} else {
println("Couldn't get documents directory!")
}

How can i copy Folder from Project to Document Directory ios swift

Here is my Folder Structure
I want to copy this Stickers folder to Document Directory for this purpose i have used following code
let fileManager = FileManager.default
let documentsUrl = fileManager.urls(for: .documentDirectory,
in: .userDomainMask)
guard documentsUrl.count != 0 else {
return // Could not find documents URL
}
let finalDatabaseURL = documentsUrl.first!.appendingPathComponent("Stickers")
if !( (try? finalDatabaseURL.checkResourceIsReachable()) ?? false) {
print("DB does not exist in documents folder")
let documentsURL = Bundle.main.resourceURL?.appendingPathComponent("Stickers")
do {
try fileManager.copyItem(atPath: (documentsURL?.path)!, toPath: finalDatabaseURL.path)
} catch let error as NSError {
print("Couldn't copy file to final location! Error:\(error.description)")
}
} else {
print("Database file found at path: \(finalDatabaseURL.path)")
}
but it won't work. I am getting an Error as
NOTE: If Copying folder is not possible then i want to copy Assets.xcassets to Document Directory. How can i achieve it?
Please below code..
I update your code in two functions to copy all files from folder to document directory.
Hope it will work.
func copyFolders() {
let fileManager = FileManager.default
let documentsUrl = fileManager.urls(for: .documentDirectory,
in: .userDomainMask)
guard documentsUrl.count != 0 else {
return // Could not find documents URL
}
let finalDatabaseURL = documentsUrl.first!.appendingPathComponent("Stickers")
if !( (try? finalDatabaseURL.checkResourceIsReachable()) ?? false) {
print("DB does not exist in documents folder")
let documentsURL = Bundle.main.resourceURL?.appendingPathComponent("Stickers")
do {
if !FileManager.default.fileExists(atPath:(finalDatabaseURL?.path)!)
{
try FileManager.default.createDirectory(atPath: (finalDatabaseURL.path), withIntermediateDirectories: false, attributes: nil)
}
copyFiles(pathFromBundle: (documentsURL?.path)!, pathDestDocs: finalDatabaseURL.path)
} catch let error as NSError {
print("Couldn't copy file to final location! Error:\(error.description)")
}
} else {
print("Database file found at path: \(finalDatabaseURL.path)")
}
}
func copyFiles(pathFromBundle : String, pathDestDocs: String) {
let fileManagerIs = FileManager.default
do {
let filelist = try fileManagerIs.contentsOfDirectory(atPath: pathFromBundle)
try? fileManagerIs.copyItem(atPath: pathFromBundle, toPath: pathDestDocs)
for filename in filelist {
try? fileManagerIs.copyItem(atPath: "\(pathFromBundle)/\(filename)", toPath: "\(pathDestDocs)/\(filename)")
}
} catch {
print("\nError\n")
}
}

Try throwing an error, but why?

I'm trying to retrieve images from the documents directory in order to populate a collection view but my try block returns an error but I don't know what the error is or why it is occurring.
func refreshCollectionView() {
let path = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)[0] as String
let url = NSURL(fileURLWithPath: path)
let filePath = url.appendingPathComponent(imagesDirectoryPath)?.path
let fileManager = FileManager.default
if fileManager.fileExists(atPath: filePath!) {
print("FILE AVAILABLE")
do {
titles = try FileManager.default.contentsOfDirectory(atPath: imagesDirectoryPath)
print(titles.count)
for image in titles {
let data = FileManager.default.contents(atPath: imagesDirectoryPath + "/\(image)")
let image = UIImage(data: data!)
myImages.append(image!)
}
self.collectionView?.reloadData()
}
catch {
print("Error")
}
}
else {
print("FILE NOT AVAILABLE")
}
}
The line print(titles.count) is never executed and the error is caught but what is the error?
if fileManager.fileExists(atPath: filePath!) {
print("FILE AVAILABLE")
do {
// ...
} catch {
print("Error:", error)
}
}
This will show you actual error

Delete files in iOS directory using Swift

I downloaded some PDF files in my app and want to delete these on closing the application.
For some reason it does not work:
Creating the file:
let reference = "test.pdf"
let RequestURL = "http://xx/_PROJEKTE/xx\(self.reference)"
let ChartURL = NSURL(string: RequestURL)
//download file
let documentsUrl = NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask).first! as NSURL
let destinationUrl = documentsUrl.URLByAppendingPathComponent(ChartURL!.lastPathComponent!)
if NSFileManager().fileExistsAtPath(destinationUrl.path!) {
print("The file already exists at path")
} else {
// if the file doesn't exist
// just download the data from your url
if let ChartDataFromUrl = NSData(contentsOfURL: ChartURL!){
// after downloading your data you need to save it to your destination url
if ChartDataFromUrl.writeToURL(destinationUrl, atomically: true) {
print("file saved")
print(destinationUrl)
} else {
print("error saving file")
}
}
}
Then I want to call the test() function to remove the items, like this:
func test(){
let fileManager = NSFileManager.defaultManager()
let documentsUrl = NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask).first! as NSURL
do {
let filePaths = try fileManager.contentsOfDirectoryAtPath("\(documentsUrl)")
for filePath in filePaths {
try fileManager.removeItemAtPath(NSTemporaryDirectory() + filePath)
}
} catch {
print("Could not clear temp folder: \(error)")
}
}
This code works for me. I removed all the images that were cached.
private func test(){
let fileManager = NSFileManager.defaultManager()
let documentsUrl = NSFileManager.defaultManager().URLsForDirectory(.CachesDirectory, inDomains: .UserDomainMask).first! as NSURL
let documentsPath = documentsUrl.path
do {
if let documentPath = documentsPath
{
let fileNames = try fileManager.contentsOfDirectoryAtPath("\(documentPath)")
print("all files in cache: \(fileNames)")
for fileName in fileNames {
if (fileName.hasSuffix(".png"))
{
let filePathName = "\(documentPath)/\(fileName)"
try fileManager.removeItemAtPath(filePathName)
}
}
let files = try fileManager.contentsOfDirectoryAtPath("\(documentPath)")
print("all files in cache after deleting images: \(files)")
}
} catch {
print("Could not clear temp folder: \(error)")
}
}
**** Update swift 3 ****
let fileManager = FileManager.default
let documentsUrl = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first! as NSURL
let documentsPath = documentsUrl.path
do {
if let documentPath = documentsPath
{
let fileNames = try fileManager.contentsOfDirectory(atPath: "\(documentPath)")
print("all files in cache: \(fileNames)")
for fileName in fileNames {
if (fileName.hasSuffix(".png"))
{
let filePathName = "\(documentPath)/\(fileName)"
try fileManager.removeItem(atPath: filePathName)
}
}
let files = try fileManager.contentsOfDirectory(atPath: "\(documentPath)")
print("all files in cache after deleting images: \(files)")
}
} catch {
print("Could not clear temp folder: \(error)")
}
I believe your problem is on this line:
let filePaths = try fileManager.contentsOfDirectoryAtPath("\(documentsUrl)")
You're using contentsOfDirectoryAtPath() with something that is an NSURL. You choose either path strings or URLs, not try to mix them both. To pre-empty your possible next question, URLs are preferred. Try using contentsOfDirectoryAtURL() and removeItemAtURL().
Another curious thing you should look at once you resolve the above: why are you using NSTemporaryDirectory() for the file path when you try to delete? You're reading the document directory and should use that.
Swift 5:
Check out the FileManager.removeItem() method
// start with a file path, for example:
let fileUrl = FileManager.default.urls(
for: .documentDirectory,
in: .userDomainMask
).deletingPathExtension()
.appendingPathComponent(
"someDir/customFile.txt",
isDirectory: false
)
// check if file exists
// fileUrl.path converts file path object to String by stripping out `file://`
if FileManager.default.fileExists(atPath: fileUrl.path) {
// delete file
do {
try FileManager.default.removeItem(atPath: fileUrl.path)
} catch {
print("Could not delete file, probably read-only filesystem")
}
}

Resources