get file attributes with nsfilesustem in cocoa no such file exists - cocoa

I've searching for about 3 hours of how to get the creation date of a file, I get the URL with an enumerator, after that I pass it to path correcting the percents, and finally I try to get the file attributes...so, I don no alter the path in anyway but I always get the same error "The operation couldn’t be completed. No such file or directory", and the path "file:///Users/raul/Desktop/DSC_0386.JPG".
The code sample:
NSError* error = nil;
//NSDictionary* fileAttribs = [[NSFileManager defaultManager] attributesOfItemAtPath:[[url absoluteString] stringByRemovingPercentEncoding] error:&error];
NSDictionary* fileAttribs = [[NSFileManager defaultManager] attributesOfItemAtPath:#"file://Users/raul/Desktop/DSC_0386.JPG" error:&error];
NSLog(#"%#",error);
NSDate *fecha = [fileAttribs objectForKey:NSFileCreationDate];
I've commented the first NSDictionary to try out the second statement with the nsstring directly.
I've checked that my file already exists.
Please, any help?? I'm missing anything?

Several issues:
1) In most cases, you shouldn't have to convert an NSURL to a path string in order to operate on a file. In particular, you can use the "resource value" API of NSURL to get the creation time directly:
NSDate* creationDate;
NSError* error;
if ([url getResourceValue:&creationDate forKey:NSURLCreationDateKey error:&error])
/* use creationDate */;
else
/* handle error */;
2) If you do need to get a path string from NSURL, don't use -absoluteString. That will still be a URL string, with things like "file://", etc. A URL string is not a valid path string. The error message you quoted in your question was already telling you this. It showed you a file "path" of "file:///Users/raul/Desktop/DSC_0386.JPG", but that's not a path at all.
You should just use the -path method. You do not need to do anything with percent encoding when you get the -path.
3) You should ignore any error output parameter until you have checked whether the method you called succeeded or failed, usually by examining its return value. That is, the code you posted should be reorganized like this:
NSError* error = nil;
NSDictionary* fileAttribs = [[NSFileManager defaultManager] attributesOfItemAtPath:#"file://Users/raul/Desktop/DSC_0386.JPG" error:&error];
if (fileAttribs)
{
NSDate *fecha = [fileAttribs objectForKey:NSFileCreationDate];
// ... use fecha ...
}
else
NSLog(#"%#",error);

Related

NSFileManager rename file using "moveItemAtURL:" with a name contains path separator like "foo/bar.extension"

This feels weird, my code goes as simple as
// something like "foo/bar"
NSString *correctFileName = seriesDict[seriesNumber];
if (correctFileName.length > 0)
{
// So I'll have a fileName like "foo/bar.extension" which looks like a directory and a file in it...
NSString *pathExtension = [filePath pathExtension];
NSString *correctFilePath = [[[filePath stringByDeletingLastPathComponent]
stringByAppendingPathComponent:correctFileName]
stringByAppendingPathExtension:pathExtension];
NSError *error = nil;
[[NSFileManager defaultManager] moveItemAtPath:filePath toPath:correctFilePath error:&error];
// And NSFileManager can not treat it as a legal fileName, kind of expected...
if (error)
{
NSLog(#"Rename file at %# failed, error: %#", filePath, error);
}
}
Seems it's ok to rename my file to "foo/bar.extension" in Finder, like this
there might be a solution to do that in code.
If anybody could shred in some light, it'll be highly appreciated.
The / in Finder is converted to a :. / is invalid in POSIX-style paths, while : is invalid in HFS-style paths, so macOS maps those two characters to each other.
The technically correct way would be to create a CFURL using CFURLCreateWithFileSystemPathRelativeToBase specifying kCFURLHFSPathStyle as the path style, and resolving against a base URL you've already created. You'd then copy the path of the full URL using CFURLCopyFileSystemPath.
Pragmatically speaking though, you can simply do a string replace between / and :.

initWithContentsOfURL often returns nil

NSError *error;
NSString *string = [[NSString alloc]
initWithContentsOfURL:URL
encoding:NSUTF8StringEncoding
error:&error];
When I test this on my iPhone it always works when I have wifi turned on. However when I'm on 3G I often get nil. If I try perhaps 15 times in a row (I have an update button for this) I finally get the desired result.
My question is, is this problem located at the server side or is my code unstable? Should I use a different approach to get a more secure fetch of data?
You haven't provided enough information to give anything but a vague answer, but you do have some options here.
Most importantly, you have an "error" parameter that you should be printing out the results of. There's also a slightly better API you could be using in the NSString class.
Change your code to something like this:
NSError *error = NULL;
NSStringEncoding actualEncoding;
// variable names in Objective-C should usually start with lower case letters, so change
// URL in your code to "url", or even something more descriptive, like "urlOfOurString"
NSString *string = [[NSString alloc] initWithContentsOfURL:urlOfOurString usedEncoding:&actualEncoding error:&error];
if(string)
{
NSLog( #"hey, I actually got a result of %#", string);
if(actualEncoding != NSUTF8StringEncoding)
{
// I also suspect the string you're trying to load really isn't UTF8
NSLog( #"and look at that, the actual encoding wasn't NSUTF8StringEncoding");
}
} else {
NSLog( #"error when trying to fetch from URL %# - %#", [urlOfOurString absoluteString], [error localizedDescription]);
}
I'm now using STHTTPRequest instead. I recommend this library very much, easy to use yet powerful.

NSFileManager says a file not writable Mac

I have been trying to use AVFoundation to record screen outputs. For reasons unknown it stopped working after I moved to the latest version of Mac (Mountain Lion). I have been trying to getting it work but is not fruitful so far. I know that the AVFoundation method startRecordingToOutputFileURL will not work if the output file already exists. So, I tried using NSFileManager to see if my destination file exists and if it is writable. My Filemanager always returns the values corresponding to non-existence of the destination file and not writable. I tried to set file permissions to no avail, could anyone throw some light on my possible mistake:
dest = [[NSURL alloc] initFileURLWithPath:#"~/Desktop/myMovie.mov"];
NSFileManager *fileManager = [NSFileManager defaultManager];
NSMutableDictionary *attributes = [[NSMutableDictionary alloc] init];
[attributes setObject:[NSNumber numberWithInt:777] forKey:NSFilePosixPermissions]; //I tried 511 too, no avail
[fileManager setAttributes:attributes ofItemAtPath:[dest path] error:nil];
if (![fileManager fileExistsAtPath:[dest path]]) {
if ([fileManager isWritableFileAtPath:[dest path]]) {
/* Starts recording to a given URL. */
[captureMovieFileOutput startRecordingToOutputFileURL:dest recordingDelegate:self];
}
else{
NSLog(#"File doesnot exist but is not writable"); //This is the message I get as result
}
}
else
{
NSLog(#"File Exists...");
}
Unexpanded tildes are not valid paths in Cocoa. You must use -stringByExpandingTildeInPath or better, -stringByStandardizingPath on the string passed into NSURL's -initFileURLWithPath:.
Because of this, NSFileManager will return NO for isWritableFileAtPath because it's an invalid path (so it's not writable). This leads you to your NSLog() being fired.
Update based on comments:
You may still find NSURL is returning nil upon creation (so calling -path will return nil) because the path is still invalid. Also worth noting, the documentation says for -isWritableFileAtPath:, "It's far better to attempt an operation (such as loading a file or creating a directory), check for errors, and handle those errors gracefully than it is to try to figure out ahead of time whether the operation will succeed."
Take Peter Hosey's suggestion and make use of the NSError if the call fails as you attempt to write to the file and don't try to figure it out ahead of time.

NSData's writeToFile method failing with server address

I am trying to write an NSData object to a directory like so;
[myData writeToFile:[NSString stringWithFormat:#"%#/%#.txt", path, filename] atomically:YES];
I receive no errors or warnings but I am assuming the write fails because the path variable has the format of afp://10.0.0.20/username/Desktop. I am connected to the networked share.
Do I need to modify the string or take a different approach here?
EDIT: Tried the following approach after recommendation but it failed
NSMutableURLRequest *post = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:#"afp://10.0.0.20/username/Desktop/filename.txt"]];
[post setHTTPMethod: #"POST"];
[post setHTTPBody:horreumImageDataNewThread];
NSURLResponse *response;
NSError *error;
[NSURLConnection sendSynchronousRequest:post returningResponse:&response error:&error];
TIA,
Ricky.
Where are you getting the afp path string from? You would normally write to a networked volume by using a path like:
/Volumes/NameOfMountedVolume/path/to/file
Also, you should use the -stringByAppendingPathComponent: method of NSString to concatenate paths:
NSString* fullPath = [path stringByAppendingPathComponent:filename];

Declare String then open string from Path with Cocoa

I've Declared a string Like so
NSString* fileName = [files objectAtIndex:i];
NSLog(fileName);
NSImage* imageFromBundle = [[NSImage alloc] initWithContentsOfFile:fileName];
and want to use that filename to open a file in a different directory.
I came up with this
NSImage* imageFromBundle2;
imageFromBundle2 = [[NSImage alloc] initWithContentsOfFile:#"/Users/rhaynes/Documents/works4/" filename ];
Any help would be appreciated
I'll assume that your fileName string is actually a file name, like "myImage.png". A lot of the Objective-C docs refer to a file name when they really mean file path - so sometimes it's confusing.
What you want to do is create an NSString that represents the complete path to the file you want to load. For instance, you could say:
NSString * path = [NSString stringWithFormat: #"/Users/rhaynes/Documents/works4/%#", fileName];
That line creates a new NSString using the format string and parameters provided (the %# in the format string indicates that the string value of fileName should be inserted there.) StringWithFormat is a really powerful function, so you should definitely check it out in the docs.
Then you could call initWithContentsOfFile:path, and it should give you the image you want.
NSString* fileName = [files objectAtIndex:i]; NSLog(fileName);
Don't pass non-hard-coded strings as format-string arguments. If they contain format specifiers, you'll get garbage or a crash. (Try this with fileName = #"foo%sbar", for example. Then try it with fileName = #"foo%fbar" for even more fun.)
Your NSLog statement should be:
NSLog(#"%#", fileName);
[I] want to use that filename to open a file in a different directory. I came up with this
NSImage* imageFromBundle2; imageFromBundle2 = [[NSImage alloc] initWithContentsOfFile:#"/Users/rhaynes/Documents/works4/" filename ];
You can only concatenate string literals this way; as you've no doubt seen for yourself, this is a syntax error when one of the strings isn't a literal.
First off, if fileName is actually a pathname, you'll need to use lastPathComponent to get the actual filename. So:
NSString *path = [files objectAtIndex:i];
NSString *filename = [path lastPathComponent];
Then, use stringByAppendingPathComponent: to tack this onto the new superpath.
NSString *desiredFilenamePath = [directoryPath stringByAppendingPathComponent:filename];
Now you have the pathname you wanted to pass to NSImage's initializer.

Resources