开发者

Check if path is folder/bundle/alias in ObjC

I come from the AppleScript land and there we use

alias of (info for thePath)
package folder of (info for thePath)
folder 开发者_运维百科of (info for thePath)

to see if a path is either of the above. But I can't seem to find out how to do it in ObjC/Cocoa. I'm pretty sure it's quite easy but I fail to find any info about it.

Thanks...


Typically you use either NSFileManager or NSWorkspace.

To see if a path is a folder/directory, use NSFileManager's -fileExistsAtPath:isDirectory:.

To see if a path is a package, use NSWorkspace's isFilePackageAtPath:.

I don't know any native Cocoa way to check if a path is an alias (it's a pre-OS X concept...). I always use Nathan Day's Cocoa wrapper for Alias, NDAlias. See finderInfoFlags:type:creator: in his NSString category. To use it, do

UInt16 flags;
OSType type;
OSType creator;
if([@"/path/to/file" finderInfoFlags:&flags type:&type creator:&creator]){
    if(flags&kIsAlias){
         the file is an alias...
    }
}else{
   some error occurred... 
}

Well it looks unnecessarily complicated, but that's life. Alias belongs to Classic Mac OS technology, while Cocoa belongs to the NeXTStep heritage.


There is resource value key NSURLIsAliasFileKey that you can use on macOS 10.6+

NSNumber * number = nil;
[fileUrl getResourceValue:&number forKey:NSURLIsAliasFileKey error:nil];
BOOL isAlias = [number boolValue];


NSString *path;
BOOL isAliasFile=NO;  
FSRef fsRef;
FSPathMakeRef((const UInt8 *)[path fileSystemRepresentation], &fsRef, NULL);
Boolean isAliasFileBoolean, isFolder;
FSIsAliasFile (&fsRef, &isAliasFileBoolean, &isFolder);
if(isAliasFileBoolean)
    isAliasFile=YES;
NSLog([NSString stringWithFormat:@"%d %@",isAliasFile,path]);

The fastest I've found. You can use it to check if it's a folder - check the link FSIsAliasFile.


From OS X 10.6 on you can do the following to determine if a file is an alias:

- (BOOL) fileIsAlias: (NSString*) thePath {
    NSURL* url = [NSURL fileURLWithPath:thePath];
    CFURLRef cfurl = (__bridge CFURLRef) url;
    CFBooleanRef cfisAlias = kCFBooleanFalse;
    BOOL success = CFURLCopyResourcePropertyForKey(cfurl, kCFURLIsAliasFileKey, &cfisAlias, NULL);

    BOOL isAlias = CFBooleanGetValue(cfisAlias);
    return isAlias && success;
}

(The solution by Yahoo is deprecated in OS X 10.8)


My way to check NSURL is an alias (works for me):

// url - is alias?
NSData * bookmarkData = [NSURL bookmarkDataWithContentsOfURL:url error:nil];
BOOL isAlias = (bookmarkData) ? YES : NO;

Good luck!


I ve been searching a solution to detect aliases and symlinks using Swift 3.0 and found a response In core Foundation

So you can create an URL extension

extension URL{

    var isAnAlias:Bool{
        // Alias? https://github.com/apple/swift-corelibs-foundation/blob/master/Foundation/URL.swift#L417
        let resv:URLResourceValues? = try? self.resourceValues(forKeys: [URLResourceKey.isAliasFileKey])
        return resv?.isAliasFile ?? false
    }

}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜