Thay thế cho stringByAddingPercentEscapesUsingEncoding trong ios9?


112

Trong iOS8 trở về trước, tôi có thể sử dụng:

NSString *str = ...; // some URL
NSString *result = [str stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];

trong iOS9 stringByAddingPercentEscapesUsingEncodingđã được thay thế bằng stringByAddingPercentEncodingWithAllowedCharacters:

NSString *str = ...; // some URL
NSCharacterSet *set = ???; // where to find set for NSUTF8StringEncoding?
NSString *result = [str stringByAddingPercentEncodingWithAllowedCharacters:set];

và câu hỏi của tôi là: tìm cần NSCharacterSet( NSUTF8StringEncoding) ở đâu để thay thế thích hợp stringByAddingPercentEscapesUsingEncoding?

Câu trả lời:


131

Thông báo không dùng nữa cho biết (nhấn mạnh của tôi):

Thay vào đó, hãy sử dụng stringByAddingPercentEncodingWithAllowedCharacters (_ :), luôn sử dụng mã hóa UTF-8 được khuyến nghị và mã hóa cho một thành phần URL cụ thể hoặc thành phần phụ vì mỗi thành phần URL hoặc thành phần phụ có các quy tắc khác nhau cho những ký tự nào là hợp lệ.

Vì vậy, bạn chỉ cần cung cấp một NSCharacterSetđối số thích hợp . May mắn thay, đối với URL, có một phương thức lớp rất tiện dụng được gọi là URLHostAllowedCharacterSetbạn có thể sử dụng như sau:

let encodedHost = unencodedHost.stringByAddingPercentEncodingWithAllowedCharacters(.URLHostAllowedCharacterSet())

Cập nhật cho Swift 3 - phương thức trở thành thuộc tính tĩnh urlHostAllowed:

let encodedHost = unencodedHost.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)

Tuy nhiên, hãy lưu ý rằng:

Phương pháp này nhằm mã hóa phần trăm thành phần URL hoặc chuỗi thành phần phụ, KHÔNG PHẢI toàn bộ chuỗi URL.


6
Ngoài ra, tôi thực sự khuyên bạn nên sử dụng NSURLComponents, có thể xử lý mã hóa phần trăm cho bạn.
Antonio Favata

1
Bất kỳ đề xuất nào để sử dụng cho toàn bộ chuỗi URL?
Kỹ năng M2

1
@ SkillM2 Tôi nghĩ NSURLComponents(với mỗi thành phần được mã hóa theo phần trăm tương ứng NSCharacterSet) là cách phù hợp để đi.
Antonio Favata,

2
Bạn không bao giờ nên cố gắng mã hóa toàn bộ chuỗi URL. Nó có thể gây ra lỗi không mong muốn và trong một số trường hợp, lỗ hổng bảo mật. Cách duy nhất được đảm bảo chính xác để mã hóa một URL là thực hiện từng phần một.
dgatwood

Tuyệt quá. Cảm ơn rất nhiều, bạn đời!
Felipe

100

Đối với Objective-C :

NSString *str = ...; // some URL
NSCharacterSet *set = [NSCharacterSet URLHostAllowedCharacterSet]; 
NSString *result = [str stringByAddingPercentEncodingWithAllowedCharacters:set];

tìm bộ cho NSUTF8StringEncoding ở đâu?

Có các bộ ký tự được xác định trước cho sáu thành phần URL và thành phần phụ cho phép mã hóa phần trăm. Các bộ ký tự này được chuyển đến -stringByAddingPercentEncodingWithAllowedCharacters:.

 // Predefined character sets for the six URL components and subcomponents which allow percent encoding. These character sets are passed to -stringByAddingPercentEncodingWithAllowedCharacters:.
@interface NSCharacterSet (NSURLUtilities)
+ (NSCharacterSet *)URLUserAllowedCharacterSet;
+ (NSCharacterSet *)URLPasswordAllowedCharacterSet;
+ (NSCharacterSet *)URLHostAllowedCharacterSet;
+ (NSCharacterSet *)URLPathAllowedCharacterSet;
+ (NSCharacterSet *)URLQueryAllowedCharacterSet;
+ (NSCharacterSet *)URLFragmentAllowedCharacterSet;
@end

Thông báo không dùng nữa cho biết (nhấn mạnh của tôi):

Thay vào đó, hãy sử dụng stringByAddingPercentEncodingWithAllowedCharacters (_ :), luôn sử dụng mã hóa UTF-8 được khuyến nghị và mã hóa cho một thành phần URL cụ thể hoặc thành phần phụ vì mỗi thành phần URL hoặc thành phần phụ có các quy tắc khác nhau cho những ký tự nào là hợp lệ.

Vì vậy, bạn chỉ cần cung cấp một NSCharacterSetđối số thích hợp . May mắn thay, đối với URL, có một phương thức lớp rất tiện dụng được gọi là URLHostAllowedCharacterSetbạn có thể sử dụng như sau:

NSCharacterSet *set = [NSCharacterSet URLHostAllowedCharacterSet]; 

Tuy nhiên, hãy lưu ý rằng:

Phương pháp này nhằm mã hóa phần trăm thành phần URL hoặc chuỗi thành phần phụ, KHÔNG PHẢI toàn bộ chuỗi URL.


4
Tôi thích khi Apple làm cho cuộc sống dễ dàng hơn. Cảm ơn apple.
Duck

5
Ý nghĩa của "Phương pháp này nhằm mã hóa phần trăm thành phần URL hoặc chuỗi thành phần phụ, KHÔNG PHẢI toàn bộ chuỗi URL." ?
GeneCode

4
URLHostAllowedCharacterSet gặp lỗi "URL không được hỗ trợ", tôi đã sử dụng URLFragmentAllowedCharacterSet và nó hoạt động tốt.
anoop4real

1
điều này không hoạt động với + nó sẽ không mã hóa nó và nó sẽ được thay thế bằng không gian trên phía máy chủ theo đặc điểm kỹ thuật.
Torge

45

URLHostAllowedCharacterSetKHÔNG LÀM VIỆC CHO ME. Tôi sử dụng URLFragmentAllowedCharacterSetthay thế.

MỤC TIÊU -C

NSCharacterSet *set = [NSCharacterSet URLFragmentAllowedCharacterSet];
NSString * encodedString = [@"url string" stringByAddingPercentEncodingWithAllowedCharacters:set];

SWIFT - 4

"url string".addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)

Sau đây là các bộ ký tự hữu ích (đảo ngược):

URLFragmentAllowedCharacterSet  "#%<>[\]^`{|}
URLHostAllowedCharacterSet      "#%/<>?@\^`{|}
URLPasswordAllowedCharacterSet  "#%/:<>?@[\]^`{|}
URLPathAllowedCharacterSet      "#%;<>?[\]^`{|}
URLQueryAllowedCharacterSet     "#%<>[\]^`{|}
URLUserAllowedCharacterSet      "#%/:<>?@[\]^`

Cảm ơn và cùng với bạn cũng
Arpit B Parekh

Đáng lưu ý rằng không có bộ nào trong số này bao gồm +. Vì vậy, các dấu cộng trong chuỗi sẽ bị lộn xộn nếu được truyền vào các tham số truy vấn - được coi như khoảng trắng '' ở phía máy chủ.
Asmo Soinio

21

Objective-C

mã này phù hợp với tôi:

urlString = [urlString stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet URLFragmentAllowedCharacterSet]];

4

Swift 2.2:

extension String {
 func encodeUTF8() -> String? {
//If I can create an NSURL out of the string nothing is wrong with it
if let _ = NSURL(string: self) {

    return self
}

//Get the last component from the string this will return subSequence
let optionalLastComponent = self.characters.split { $0 == "/" }.last


if let lastComponent = optionalLastComponent {

    //Get the string from the sub sequence by mapping the characters to [String] then reduce the array to String
    let lastComponentAsString = lastComponent.map { String($0) }.reduce("", combine: +)


    //Get the range of the last component
    if let rangeOfLastComponent = self.rangeOfString(lastComponentAsString) {
        //Get the string without its last component
        let stringWithoutLastComponent = self.substringToIndex(rangeOfLastComponent.startIndex)


        //Encode the last component
        if let lastComponentEncoded = lastComponentAsString.stringByAddingPercentEncodingWithAllowedCharacters(NSCharacterSet.alphanumericCharacterSet()) {


        //Finally append the original string (without its last component) to the encoded part (encoded last component)
        let encodedString = stringWithoutLastComponent + lastComponentEncoded

            //Return the string (original string/encoded string)
            return encodedString
        }
    }
}

return nil;
}
}

2

Đối với Swift 3.0

Bạn có thể sử dụng urlHostAllowedcharacterSet.

/// Trả về bộ ký tự cho các ký tự được phép trong thành phần phụ URL máy chủ.

public static var urlHostAllowed: CharacterSet { get }

WebserviceCalls.getParamValueStringForURLFromDictionary(settingsDict as! Dictionary<String, AnyObject>).addingPercentEncoding(withAllowedCharacters: CharacterSet.urlHostAllowed)

1

Ý nghĩa của "Phương pháp này nhằm mã hóa phần trăm thành phần URL hoặc chuỗi thành phần phụ, KHÔNG PHẢI toàn bộ chuỗi URL." ? - GeneCode 1 '16 tháng 9 lúc 8:30

Nó có nghĩa là bạn không được phép mã hóa https://xpto.example.com/path/subpathurl, mà chỉ mã hóa những gì sau ?.

Được cho là, vì có các trường hợp sử dụng để thực hiện nó trong các trường hợp như:

https://example.com?redirectme=xxxxx

Trong trường hợp xxxxxlà một URL được mã hóa hoàn toàn.


0

Thêm vào câu trả lời được chấp nhận. Cân nhắc lưu ý này

Phương pháp này nhằm mã hóa phần trăm thành phần URL hoặc chuỗi thành phần phụ, KHÔNG PHẢI toàn bộ chuỗi URL.

toàn bộ URL không được mã hóa:

let param = "=color:green|\(latitude),\(longitude)&\("zoom=13&size=\(width)x\(height)")&sensor=true&key=\(staticMapKey)".addingPercentEncoding(withAllowedCharacters: .urlHostAllowed) 
let url = "https://maps.google.com/maps/api/staticmap?markers" + param!
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.