Index: src/OFURL.h ================================================================== --- src/OFURL.h +++ src/OFURL.h @@ -101,17 +101,31 @@ relativeToURL: (OFURL *)URL; #ifdef OF_HAVE_FILES /*! * @brief Creates a new URL with the specified local file path. + * + * If a directory exists at the specified path, a slash is appended if there is + * no slash yet. * * @param path The local file path * @return A new, autoreleased OFURL */ + (instancetype)fileURLWithPath: (OFString *)path; #endif +/*! + * @brief Creates a new URL with the specified local file path. + * + * @param path The local file path + * @param isDirectory Whether the path is a directory, in which case a slash is + * appened if there is no slash yet + * @return An Initialized OFURL + */ +- (instancetype)initFileURLWithPath: (OFString *)path + isDirectory: (bool)isDirectory; + - (instancetype)init OF_UNAVAILABLE; /*! * @brief Initializes an already allocated OFURL with the specified string. * @@ -128,10 +142,36 @@ * @param URL A URL to which the string is relative * @return An initialized OFURL */ - (instancetype)initWithString: (OFString *)string relativeToURL: (OFURL *)URL; + +#ifdef OF_HAVE_FILES +/*! + * @brief Initializes an already allocated OFURL with the specified local file + * path. + * + * If a directory exists at the specified path, a slash is appended if there is + * no slash yet. + * + * @param path The local file path + * @return An initialized OFURL + */ +- (instancetype)initFileURLWithPath: (OFString *)path; + +/*! + * @brief Initializes an already allocated OFURL with the specified local file + * path. + * + * @param path The local file path + * @param isDirectory Whether the path is a directory, in which case a slash is + * appened if there is no slash yet + * @return An Initialized OFURL + */ ++ (instancetype)fileURLWithPath: (OFString *)path + isDirectory: (bool)isDirectory; +#endif /*! * @brief Returns the URL as a string. * * @return The URL as a string Index: src/OFURL.m ================================================================== --- src/OFURL.m +++ src/OFURL.m @@ -52,30 +52,18 @@ } #ifdef OF_HAVE_FILES + (instancetype)fileURLWithPath: (OFString *)path { - void *pool = objc_autoreleasePoolPush(); - OFFileManager *fileManager = [OFFileManager defaultManager]; - OFURL *currentDirectoryURL, *URL; - - if (![path hasSuffix: OF_PATH_DELIMITER_STRING] && - [fileManager directoryExistsAtPath: path]) - path = [path stringByAppendingString: @"/"]; - -# if OF_PATH_DELIMITER != '/' - path = [[path pathComponents] componentsJoinedByString: @"/"]; -# endif - - currentDirectoryURL = - [[OFFileManager defaultManager] currentDirectoryURL]; - URL = [[OFURL alloc] initWithString: path - relativeToURL: currentDirectoryURL]; - - objc_autoreleasePoolPop(pool); - - return [URL autorelease]; + return [[[self alloc] initFileURLWithPath: path] autorelease]; +} + ++ (instancetype)fileURLWithPath: (OFString *)path + isDirectory: (bool)isDirectory +{ + return [[[self alloc] initFileURLWithPath: path + isDirectory: isDirectory] autorelease]; } #endif - (instancetype)init { @@ -280,10 +268,62 @@ free(UTF8String2); } return self; } + +#ifdef OF_HAVE_FILES +- (instancetype)initFileURLWithPath: (OFString *)path +{ + @try { + void *pool = objc_autoreleasePoolPush(); + OFFileManager *fileManager = [OFFileManager defaultManager]; + bool isDirectory; + + isDirectory = ([path hasSuffix: OF_PATH_DELIMITER_STRING] || + [fileManager directoryExistsAtPath: path]); + self = [self initFileURLWithPath: path + isDirectory: isDirectory]; + + objc_autoreleasePoolPop(pool); + } @catch (id e) { + [self release]; + @throw e; + } + + return self; +} + +- (instancetype)initFileURLWithPath: (OFString *)path + isDirectory: (bool)isDirectory +{ + @try { + void *pool = objc_autoreleasePoolPush(); + OFURL *currentDirectoryURL; + +# if OF_PATH_DELIMITER != '/' + path = [[path pathComponents] componentsJoinedByString: @"/"]; +# endif + + if (isDirectory && ![path hasSuffix: OF_PATH_DELIMITER_STRING]) + path = [path stringByAppendingString: @"/"]; + + currentDirectoryURL = + [[OFFileManager defaultManager] currentDirectoryURL]; + + self = [self initWithString: path + relativeToURL: currentDirectoryURL]; + + objc_autoreleasePoolPop(pool); + } @catch (id e) { + [self release]; + @throw e; + } + + return self; +} +#endif - (instancetype)initWithSerialization: (OFXMLElement *)element { @try { void *pool = objc_autoreleasePoolPush(); Index: tests/OFURLTests.m ================================================================== --- tests/OFURLTests.m +++ tests/OFURLTests.m @@ -15,10 +15,13 @@ */ #include "config.h" #import "OFURL.h" +#ifdef OF_HAVE_FILES +# import "OFFileManager.h" +#endif #import "OFNumber.h" #import "OFString.h" #import "OFAutoreleasePool.h" #import "OFInvalidFormatException.h" @@ -51,10 +54,17 @@ [[[OFURL URLWithString: @"foo/bar" relativeToURL: [OFURL URLWithString: @"http://h/qux/?x"]] string] isEqual: @"http://h/qux/foo/bar"] && [[[OFURL URLWithString: @"http://foo/?q" relativeToURL: u1] string] isEqual: @"http://foo/?q"]) + +#ifdef OF_HAVE_FILES + TEST(@"+[fileURLWithPath:isDirectory:]", + [[[OFURL fileURLWithPath: @"testfile.txt"] fileSystemRepresentation] + isEqual: [[[OFFileManager defaultManager] currentDirectoryPath] + stringByAppendingPathComponent: @"testfile.txt"]]) +#endif TEST(@"-[string]", [[u1 string] isEqual: url_str] && [[u2 string] isEqual: @"http://foo:80"] && [[u3 string] isEqual: @"http://bar/"] &&