NSURL URLWithString:relativeToURL: is clipping relative url
Solution 1
I read [RFC1808] which defines the normative algorithm for resolving relative URLs
2 issues:
-
the relative url may not start with a / or it is considered to be absolute:
Step 4: If the embedded URL path is preceded by a slash "/", the path is not relative and we skip to Step 7."
-
when the base url ends with a non-slash. everything from the last slash on is skipped
Step 6: The last segment of the base URL's path (anything following the rightmost slash "/", or the entire path if no slash is present) is removed and the embedded URL's path is appended in its place. The following operations are then applied, in order, to the new path:"
so that explains it. the baseURL needs to end in a / and the relative url shouldn't start with a /
Solution 2
You have two problems here:
Firstly, the string /files/search
is an absolute path since it starts with a slash. Resolving it against any existing URL will ignore the existing path.
Secondly, https://api.service.com/v1
does not have a trailing slash to indicate it's a directory. Any strings resolved against it will always ignore the v1
portion.
To conclude, you need that combo of a relative path — files/search
— and directory base URL — https://api.service.com/v1/
.
Related videos on Youtube
Pipo
Updated on September 16, 2022Comments
-
Pipo over 1 year
I'm trying to implement an iOS app, which uses RestKit. In all examples I've seen so far the following code is used to create the URLs:
NSURL *baseURL = [NSURL URLWithString:@"https://api.service.com/v1"]; NSURL *relativeURL = [NSURL URLWithString:@"/files/search" relativeToURL:baseURL];
But then
[relativeURL absoluteString]
will returnhttps://api.service.com/files/search
.So I tried a few examples:
NSURL *baseURL1 = [NSURL URLWithString:@"https://api.service.com/v1/"]; NSURL *baseURL2 = [NSURL URLWithString:@"https://api.service.com/v1"]; NSURL *baseURL3 = [NSURL URLWithString:@"/v1" relativeToURL:[NSURL URLWithString:@"https://api.service.com"]]; NSURL *relativeURL1 = [NSURL URLWithString:@"/files/search" relativeToURL:baseURL1]; NSURL *relativeURL2 = [NSURL URLWithString:@"/files/search" relativeToURL:baseURL2]; NSURL *relativeURL3 = [NSURL URLWithString:@"/files/search" relativeToURL:baseURL3]; NSURL *relativeURL4 = [NSURL URLWithString:@"files/search" relativeToURL:baseURL1]; NSURL *relativeURL5 = [NSURL URLWithString:@"files/search" relativeToURL:baseURL2]; NSURL *relativeURL6 = [NSURL URLWithString:@"files/search" relativeToURL:baseURL3]; NSLog(@"1: %@", [relativeURL1 absoluteString]); NSLog(@"2: %@", [relativeURL2 absoluteString]); NSLog(@"3: %@", [relativeURL3 absoluteString]); NSLog(@"4: %@", [relativeURL4 absoluteString]); NSLog(@"5: %@", [relativeURL5 absoluteString]); NSLog(@"6: %@", [relativeURL6 absoluteString]);
And this is the output:
1: https://api.service.com/files/search 2: https://api.service.com/files/search 3: https://api.service.com/files/search 4: https://api.service.com/v1/files/search 5: https://api.service.com/files/search 6: https://api.service.com/files/search
So the only example returning what I want is #4. Can anyone explain why?
-
Daij-Djan almost 11 years@downvoter please explain why ... is it because of the leading /? I get that and therefore edited it and up voted mike.. but please leave comment whenever you down vote
-
Daij-Djan almost 10 yearsagain: latest down voter would you please leave a comment so I can fix it if needed
-
Johnykutty over 8 yearsthe baseURL needs to end in a / and the relative url shouldn't start with a / this is absolutely correct:). I was struggling with some problem wrt base url and path. Can you add the link for [RFC1808]