ioscocoansurlcore-foundationnsurlcomponents

Why does NSURL parse strings with a double forward slash after the scheme differently to a string with a single forward slash?


When parsing strings into NSURL objects, NSURL treats a string using a single forward slash differently to a string with a double forward slash after the scheme.

Why is this the case?

Here's some examples:

NSURL *url = [NSURL URLWithString:@"app-id://path1/path2"];

NSLog(@"%@",url.scheme);    // "app-id"
NSLog(@"%@",url.path);      // "/path2"
NSLog(@"%@",url.host);      // "path1"


NSURL *url = [NSURL URLWithString:@"app-id:/path1/path2"];

NSLog(@"%@",url.scheme);    // "app-id"
NSLog(@"%@",url.path);      // "/path1/path2"
NSLog(@"%@",url.host);      // nil

Solution

  • The two strings are treated differently because the first one with // complies with RFC 1808 and the second string does not.

    The first string is a standard internet URL, and the second string omits the 'Authority Component' (see RFC 2396 Section 3.2) and begins the path component immediately, therefore not conforming to RFC 1808.

    RFC1808

    RFC 1808 defines the "Relative Uniform Resource Locators" which are the most familiar URIs these days and use the // format:

    <scheme>://<net_loc>/<path>;<params>?<query>#<fragment>
    

    The //<net_loc> is a required component of 1808 and RFC 2396 states that the component after the // is called the Authority Component (see seciton 3.2) which acts as the top element, or namespace for the path. The path begins at the next forward slash.

    The authority component is preceded by a double slash "//" and is terminated by the next slash "/", question-mark "?", or by the end of the URI.

    The single forward slash

    Using a single forward slash ommits the Authority Component and starts the path component immediately.

    NSURL

    NSURL exposes the Authority Component of a URL as the host parameter and mentions that it's only available as part of URLs conforming to 1808:

    [host] Return Value

    The host of the URL. If the receiver does not conform to RFC 1808, returns nil.

    This is why NSURL treats them differently, why the host component is nil in the second case and why the path contains everything after the colon.