I am trying to write a very basic text string to my documents directory and work from there to later save other files etc.
I am currently stuck with it not writing anything into my Documents directory
(In my viewDidLoad)
NSArray *pathArray = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)
NSString *documentsDirectory = [pathArray objectAtIndex:0];
NSString *textPath = [documentsDirectory stringByAppendingPathComponent:#"file1.txt"];
NSString *text = #"My cool text message";
[[NSFileManager defaultManager] createFileAtPath:textPath contents:nil attributes:nil];
[text writeToFile:textPath atomically:NO encoding:NSUTF8StringEncoding error:NULL];
NSLog(#"Text file data: %#",[[NSFileManager defaultManager] contentsAtPath:textPath]);
This is what gets printed out:
2011-06-27 19:04:43.485 MyApp[5731:707] Text file data: (null)
If I try this, it also prints out null:
NSLog(#"My Documents: %#", [[NSFileManager defaultManager] contentsOfDirectoryAtPath:documentsDirectory error:NULL]);
What have I missed or am I doing wrong while writing to this file?
Might it be something I need to change in my plist or some frameworks/imports needed?
Thanks
[EDIT]
I passed a NSError object through the writeToFile and got this error:
Error: Error Domain=NSCocoaErrorDomain Code=512 "The operation couldn’t be completed. (Cocoa error 512.)" UserInfo=0x12aa00 {NSFilePath=/var/mobile/Applications/887F4691-3B75-448F-9384-31EBF4E3B63E/Documents/file1.txt, NSUnderlyingError=0x14f6b0 "The operation couldn’t be completed. Not a directory"}
[EDIT 2]
This works fine on the simulator but not on my phone :/
Instead of using NSFileManager to get the contents of that file, try using NSString as such:
NSArray *pathArray = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)
NSString *documentsDirectory = [pathArray objectAtIndex:0];
NSString *textPath = [documentsDirectory stringByAppendingPathComponent:#"file1.txt"];
NSError *error = nil;
NSString *str = [NSString stringWithContentsOfFile:textPath encoding:NSUTF8StringEncoding error:&error];
if (error != nil) {
NSLog(#"There was an error: %#", [error description]);
} else {
NSLog(#"Text file data: %#", str);
}
Edit: Added error checking code.
How are you getting documentsDirectory?
You should be using something like this:
NSArray *pathArray = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)
NSString *documentsDirectory = [pathArray lastObject];
Put an NSLog statement after every line where you are setting a variable's value, so that you can inspect those values. This should help you quickly pinpoint where things start to go wrong.
The problem got solved by setting a non standard Bundle ID in die info.plist
I used the Bundle ID from iTunes Connect for this specific app. Now everything works perfectly.
You can also use NSFileHandle for writing data in file and save to document directory:
Create a variable of NSFileHandle
NSFileHandle *outputFileHandle;
use the prepareDataWrittenHandle function with passing file name in parameter with file extension
-(void)prepareDataWrittenHandle:(NSString *)filename
{
//Create Path of file in document directory.
NSString *documentsDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
NSString *outputFilePath = [documentsDirectory stringByAppendingPathComponent:filename];
//Check file with above name is already exits or not.
if ([[NSFileManager defaultManager] fileExistsAtPath:outputFilePath] == NO) {
NSLog(#"Create the new file at outputFilePath: %#", outputFilePath);
//Create file at path.
BOOL suc = [[NSFileManager defaultManager] createFileAtPath:outputFilePath
contents:nil
attributes:nil];
NSLog(#"Create file successful?: %u", suc);
}
outputFileHandle = [NSFileHandle fileHandleForWritingAtPath:outputFilePath];
}
then write the string value to file as:
//Create a file
[self prepareDataWrittenHandle:#"file1.txt"];
//String to save in file
NSString *text = #"My cool text message";
//Convert NSString to NSData to save data in file.
NSData* data = [text dataUsingEncoding:NSUTF8StringEncoding]
//Write NSData to file
[_outputFileHandle writeData:data];
//close the file if written complete
[_outputFileHandle closeFile];
at the end of file written you should close the file.
You can also check the content written in file as NSString for debug point of view as mention above by #Glenn Smith:
NSString *documentsDirectory = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
NSString *outputFilePath = [documentsDirectory stringByAppendingPathComponent:#"file1.txt"];
NSError *error;
NSString *str = [NSString stringWithContentsOfFile:outputFilePath encoding:NSUTF8StringEncoding error:&error];
if (error != nil) {
NSLog(#"There was an error: %#", [error description]);
} else {
NSLog(#"Text file data: %#", str);
}
Related
I want to read and print the file's content which downloaded from dropbox but my "readFile" method prints null. I am sure the file is downloaded successfully.
-(void)download
{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *filePath = [documentsDirectory stringByAppendingPathComponent:[NSString stringWithFormat:#"%#", #"File.txt"]];
[[self restClient] loadFile:#"/File.txt" intoPath:filePath];
}
- (void)restClient:(DBRestClient*)client loadedFile:(NSString*)localPath
contentType:(NSString*)contentType metadata:(DBMetadata*)metadata {
[self readFile:#"File.txt"];
NSLog(#"File loaded into path: %#", localPath);
}
-(void)readFile:(NSString *)fileName
{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *fileNameData=[NSString stringWithFormat:#"%#",fileName];
NSString *filePath = [documentsDirectory stringByAppendingPathComponent:fileNameData];
NSString *str = [NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:NULL];
NSError *error;
NSString *str = [NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:&error];
NSLog(#"%#", error);
}
and this is output:
---------******** CONTENT OF THE DOWNLOADED FILE *********------------(null)
I updated my code for capture erorr and I am getting this error from stringWithContentsOfFile:
Error Domain=NSCocoaErrorDomain Code=261 "The operation couldn’t be completed. (Cocoa error 261.)" UserInfo=0x1669c2b0 {NSFilePath=/var/mobile/Applications/11B10727-E372-1147-26BD-1D24S60B8E54/Documents/File.txt, NSStringEncoding=4} 2013-08-05 22:06:03.229 DBApp[496:60b]
It looks like your code is reading a file called "File.txt" rather than the actual file that was downloaded from Dropbox. Am I missing something?
EDIT
Based on the comments below, it looks like the error is 261, related to string encoding. You might want to try a different encoding or ensure that the text file is encoded the way you expect it to be.
I am facing problem to move image file in Cache Directory. My requirement is when I am deleting one file for example image3.png then all other files (suppose there is 9 files like image1.png,image2.png,.....image9.png)after that position (image4.png,....,image9.png) will move to their previous position. I want to rename that files like image4.png to image 3.png.
Below is my code
NSError *error=nil;
NSString *imgName = [NSString stringWithFormat:#"image%d.png",3];
NSFileManager *fileManager = [NSFileManager defaultManager];
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *fullPath = [documentsDirectory stringByAppendingPathComponent:imgName];
[fileManager removeItemAtPath: fullPath error:NULL];
for (int i=3; i<=9 ; i++) {
NSString *imgName1 = [NSString stringWithFormat:#"image%d.png",i];
NSString *getImagePath1 = [documentsDirectory stringByAppendingPathComponent:imgName1];
NSString *imgName2 = [NSString stringWithFormat:#"image%d.png",i+1];
NSString *getImagePath2 = [documentsDirectory stringByAppendingPathComponent:imgName2];
if ([fileManager moveItemAtPath:getImagePath2 toPath:getImagePath1 error:&error] != YES)
NSLog(#"Unable to move file: %#", [error localizedDescription]);
// Show contents of Documents directory
NSLog(#"Documents directory: %#",
[fileManager contentsOfDirectoryAtPath:documentsDirectory error:&error]);
}
But its showing following error
Unable to move file: The operation couldn’t be completed. (Cocoa error 516.)
Please help me .
Thanks in advance.
From NSFileManager docs on moveItemAtPath:toPath:error::
If an item with the same name already exists at dstPath, this method
aborts the move attempt and returns an appropriate error
Delete the file you want to overwrite first.
i am new developer in iphone application. i would like write a content in xml file for that, i have created xml file and write tags with element, attribute and value with some data in that xml as follows.
-(void)writexmlfile:(NSString *)data toFile:(NSString *)fileName NodeName:(NSString *)Node{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
// the path to write file
NSString *fileExtension = [NSString stringWithFormat:#"%#%#",fileName,#".xml"];
NSString *appFile = [documentsDirectory stringByAppendingPathComponent:fileExtension];
BOOL fileExists = [[NSFileManager defaultManager] fileExistsAtPath:appFile];
if(fileExists) {
NSError *error = nil;
NSString *docStr;
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
// the path to write file
NSString *appFile = [documentsDirectory stringByAppendingPathComponent:fileName];
BOOL fileExists = [[NSFileManager defaultManager] fileExistsAtPath:appFile];
if(fileExists)
{
NSLog(#"file exist in document");
NSData *myData1 = [NSData dataWithContentsOfFile:appFile];
if (myData1) {
docStr = [[NSString alloc] initWithData:myData1 encoding:NSASCIIStringEncoding];
XMLString = [[NSMutableString alloc]initWithString:docStr];
[self XMLString];
NSLog(#"data%#",XMLString);
}
}
// [XMLString insertString:data atIndex:index];
[XMLString appendFormat:#"<%#>%#</%#> \n",Node,data,Node];
BOOL success = [XMLString writeToFile:appFile atomically:YES encoding:NSUTF8StringEncoding error:&error];
if (!success) {
NSLog(#"Error: %#", [error userInfo]);
}
else {
NSLog(#"File write is successful");
}
}
}
i want add new tag with new elements,new attributes,etc.,if i enter element at the place of tag it is modifying with previous tag .
here how can i append the new tag to previous appended tags
please any body could help me
Thanks in advance
As a suggestion, you can use APXML to create XML documents it is very simple and easy to use. This post can guide you further.
i must write (at start of app) and delete is content (at the end of app) a csv in my sandbox file with a stream of data.
For your experience, what's the best way to do this?
edit:
i'm trying with this:
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *filename =#"test.csv";
NSString *fullPathToFile = [documentsDirectory stringByAppendingPathComponent:filename];
if(![[NSFileManager defaultManager] fileExistsAtPath: fullPathToFile]) {
[[NSFileManager defaultManager] createFileAtPath: fullPathToFile contents:nil attributes:nil];
}
NSFileHandle *handle = [NSFileHandle fileHandleForWritingAtPath: fullPathToFile];
NSString *data = [NSString stringWithFormat:#"%#,%#\n", latitudine.text, longitudine.text];
[handle writeData:[data dataUsingEncoding:NSUTF8StringEncoding]];
it work but.... every time writedata is call i got only one row, no append. i want to collect all values of my two textlabel.
Where my mistake?
edit2:
yessss, find the solution with this code:
first i've create this one:
- (NSString *)dataFilePath {
NSArray *paths = NSSearchPathForDirectoriesInDomains(
NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
return [documentsDirectory stringByAppendingPathComponent:#"myfile.csv"];
}
and in my viewDidLoad i check and if does not exist, create my file
if (![[NSFileManager defaultManager] fileExistsAtPath:[self dataFilePath]]) {
[[NSFileManager defaultManager] createFileAtPath: [self dataFilePath] contents:nil attributes:nil];
NSLog(#"Route creato");
}
and in one of my method i add the code for retrieve data and append to my file:
NSString *data = [NSString stringWithFormat:#"%#,%# ", latitudine.text, longitudine.text];
//create my data to append
NSFileHandle *handle;
handle = [NSFileHandle fileHandleForWritingAtPath: [self dataFilePath] ];
//say to handle where's the file fo write
[handle truncateFileAtOffset:[handle seekToEndOfFile]];
//position handle cursor to the end of file
[handle writeData:[data dataUsingEncoding:NSUTF8StringEncoding]];
//write data to with the right encoding
Hope this helps!
If you put it in NSTemporaryDirectory(), I think it's supposed to be cleaned up on app exit — it's probably worth checking if this is the case.
im getting a "CFDictionaryAddValue(): immutable collection 0xd5aea0 given to mutating function"
error when i try to write a string to a file using the follwowing code
NSString *xmlString = [NSString stringWithString:xmlData];
NSError *error = nil;
if ([xmlString writeToFile:filePath atomically:NO encoding:NSASCIIStringEncoding error:&error])
xmlData was a mutable string but xmlString is not.
any ideas?
It works for me in cocoa.
NSString * xmlData = #"This is some random string";
NSString * xmlString = [NSString stringWithString:xmlData];
NSError * error = nil;
if (![xmlString writeToFile:#"data.txt"
atomically:NO
encoding:NSASCIIStringEncoding
error:&error])
{
NSLog(#"writeToFile failed: %#", error);
}
I would check:
How do you get xmlData? Is it a NSString?
Do you specify file path within your app bundle? You will not be able to write outside your application directory apart from Documents (?) I think.
This is how you would specify file in Documents directory:
// Documents directory
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,
NSUserDomainMask, YES);
NSString *documentsPath = [paths objectAtIndex:0];
// <Application Home>/Documents/foo.plist
NSString *fooPath = [documentsPath stringByAppendingPathComponent:#“foo.plist”];