NSString stringByAppendingPathComponent: удаляет '/' в http: // - PullRequest
25 голосов
/ 05 апреля 2010

Я модифицировал некоторый код для работы между Mac OS X и iPhone OS.

Я столкнулся с кодом, который использовал NSURL URLByAppendingPathComponent: (добавлен в 10.6), который, как некоторые могут знать, недоступен в iPhone SDK.

Мое решение, чтобы этот код работал между ОС, заключается в использовании

NSString *urlString = [myURL absoluteString];
urlString = [urlString stringByAppendingPathComponent:@"helloworld"];
myURL = [NSURL urlWithString:urlString];

Проблема в том, что NSString stringByAppendingPathComponent:, кажется, удаляет один из / из http: // части URL.

Это предполагаемое поведение или ошибка?


Редактировать

Хорошо, я слишком быстро задал вопрос выше. Я перечитал документацию, и она действительно говорит:

Обратите внимание, что этот метод работает только с путями к файлам (не, например, для строковых представлений URL-адресов)

Однако он не дает указателей в правильном направлении для того, что делать, если вам нужно добавить компонент пути к URL-адресу на iPhone ...

Я всегда мог сделать это вручную, добавив / при необходимости и дополнительную строку, но я старался максимально приблизить ее к исходному коду Mac OS X ...

Ответы [ 6 ]

15 голосов
/ 05 апреля 2010

Я бы реализовал метод myURLByAppendingPathComponent: в NSURL, который делает то же самое. Причина для присвоения ему другого имени в том, что он не переопределяет метод, предоставленный Apple, когда Apple пытается перенести API 10.6 на iPhone (так что «my» - всего лишь пример - дело в том, что вряд ли иначе написал бы метод с таким именем).

Мне кажется, вы просто хотите связываться с путем, а не со всем URL. Вот непроверенный пример:

- (NSURL *)myURLByAppendingPathComponent:(NSString *)component {
    NSString *newPath = [[self path] stringByAppendingPathComponent:component];
    return [[[NSURL alloc] initWithScheme: [self scheme] 
                                     host: [self host] 
                                     path: newPath]
                                     autorelease];
}

Он будет корректно работать только с URL-адресами, имеющими файловые пути, но я уверен, что метод Apple работает точно так же. В любом случае, надеюсь, это поможет вам в правильном направлении.

12 голосов
/ 09 мая 2013

URLByAppendingPathComponent

Начиная с iOS 4, URLByAppendingPathComponent доступна на iOS и правильно обрабатывает две косые черты. (OS X имел это с 10.6., Как указывает Чак)

myURL = [myURL URLByAppendingPathComponent:@"hello world"]
// http://foo/bar/hello%20world

Обратите внимание, что в отличие от stringByAppendingPathComponent, этот метод экранирует аргумент.

URLWithString: relativeToURL:

В качестве альтернативы есть URLWithString:relativeToURL:, который не сбегает. Поэтому, если компонент url уже экранирован, используйте:

myURL = [NSURL URLWithString:@"hello%20world" relativeToURL:myURL]
// http://foo/bar/hello%20world

Обратите внимание, что myURL должен заканчиваться косой чертой, а добавленный сегмент не должен иметь начальную косую черту.

4 голосов
/ 05 апреля 2010

Ссылка NSString говорит об этом stringByAppendingPathComponent:

Обратите внимание, что этот метод работает только с пути к файлам (не, например, строка представления URL).

Итак, я думаю, что это случай "Не делай этого".

Использовать -stringByAppendingString: вместо?

2 голосов
/ 18 октября 2012

Есть простая работа вокруг. Использование [NSString stringWithFormat: @ "% @ /% @", сервер, файл] работает нормально.

например. сервер: ftp: //www.server.com и файл: file.txt

1 голос
/ 13 августа 2016
+ (NSString *)urlStringPathWithComponents:(NSArray *)paths
{
    NSString *url = @"";
    for( NSString *item in paths)
    {
        if([item isEqualToString:paths.firstObject])
        {
            url = [url stringByAppendingString:[NSString stringWithFormat:@"%@", item]];
        }else{
            url = [url stringByAppendingString:[NSString stringWithFormat:@"/%@", item]];
        }

    }
    return url;
}

Как вы видите, приведенный выше код является методом класса, и это разрешение разрешено использовать в любом месте без экземпляра объекта.

Примечание. Всегда первый объект массива должен быть базовым URL-адресом.

0 голосов
/ 14 апреля 2012

Я сделал доступным некоторый код, который обрабатывает это: https://gist.github.com/1256354

В своем блоге я написал дополнительное объяснение: http://koolistov.net/blog/2011/10/02/right-path-to-url-parameters/

...