swift2 在ISO-8859-1中编码NSURL

dfuffjeb  于 2022-11-06  发布在  Swift
关注(0)|答案(3)|浏览(227)

我有一个包含TextFields的ViewController,我需要将这些值发送到一个专用的HTTP服务。我主要关心的是编码类型,因为这个应用程序是法语的,可能包含一些重音符号('é','è',等等,...),但我还需要正确地格式化我的字段,因为它可能包含空格,以及...
我尝试使用不同的方法,但我仍然有一个错误的编码在服务器端。
下面是我代码的一个示例:

let url_to_request = "http://11.22.33.44:8080/SRV/addRepertoire"

    var params = "owner=\(User.sharedInstance.email)&adresse=\(adresse.text!)&nom=\(nom.text!)&telephone=\(telephone.text!)&commentaires=\(commentaires.text!)"

    //trying to encode in ISO-8859-1
    let dt = NSString(CString: params, encoding: NSISOLatin1StringEncoding)
    //preparing string to be used in a NSURL
    let final_url = dt!.stringByAddingPercentEncodingWithAllowedCharacters(NSCharacterSet.URLQueryAllowedCharacterSet())

    print("URL loadRepertoire: \(url_to_request+"?"+final_url!)")

例如,字段“nom”包含编码为“b%C4%82%C5%A0b%C4%82%C5%A0”的“bébé”,而我的服务器需要的是“b%E9b%E9”
编辑2:
我尝试使用以下代码:

let url_to_request = "http://11.22.33.44:8080/SRV/addRepertoire"

    let params = "owner=\(User.sharedInstance.email)&adresse=\(adresse.text!)&nom=\(nom.text!)&telephone=\(telephone.text!)&commentaires=\(commentaires.text!)"

    let tmp_url = url_to_request + "?" + params
    let final_url = tmp_url.stringByAddingPercentEncodingWithAllowedCharacters(NSCharacterSet.URLQueryAllowedCharacterSet())!

    print("URL addRepertoire: \(final_url)")

但结果仍然是:

b%C3%83%C2%A9b%C3%83%C2%A9, diplayed bébé instead of bébé
c8ib6hqw

c8ib6hqw1#

stringByAddingPercentEncodingWithAllowedCharacters总是使用UTF-8表示,所以恐怕您需要自己完成。

extension String {
    func stringByAddingPercentEncodingForISOLatin1() -> String? {
        let allowedCharacterSet = NSCharacterSet(charactersInString:
                    "0123456789"
                    + "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
                    + "abcdefghijklmnopqrstuvwxyz"
                    + "_-.~"
                    + "=&" //You'd better remove this and encode each param.
        )
        if let data = self.dataUsingEncoding(NSISOLatin1StringEncoding) {
            var result = ""
            for i in 0..<data.length {
                let ch = UnsafePointer<UInt8>(data.bytes)[i]
                if ch >= 0x80 || !allowedCharacterSet.characterIsMember(unichar(ch)) {
                    result += String(format: "%%%02X", ch)
                } else {
                    result.append(UnicodeScalar(ch))
                }
            }
            return result
        } else {
            return nil
        }
    }
}
"bébé".stringByAddingPercentEncodingForISOLatin1()! //->"b%E9b%E9"
r3i60tvu

r3i60tvu2#

下面是Swift 4中的一个解决方案:

extension String {

  // Url percent encoding according to RFC3986 specifications
  // https://tools.ietf.org/html/rfc3986#section-2.1
  func urlPercentEncoded(withAllowedCharacters allowedCharacters: 
    CharacterSet, encoding: String.Encoding) -> String {
    var returnStr = ""

    // Compute each char seperatly
    for char in self {
      let charStr = String(char)
      let charScalar = charStr.unicodeScalars[charStr.unicodeScalars.startIndex]
      if allowedCharacters.contains(charScalar) == false,
        let bytesOfChar = charStr.data(using: encoding) {
        // Get the hexStr of every notAllowed-char-byte and put a % infront of it, append the result to the returnString
        for byte in bytesOfChar {
          returnStr += "%" + String(format: "%02hhX", byte as CVarArg)
        }
      } else {
        returnStr += charStr
      }
    }

    return returnStr
  }

}

用法:

"aouäöü!".urlPercentEncoded(withAllowedCharacters: .urlQueryAllowed,
                                         encoding: .isoLatin1) 
// Results in -> "aou%E4%F6%FC!"
eh57zj3b

eh57zj3b3#

对于Objective-C:

- (NSString *)stringByAddingPercentEncodingForISOLatin1 {

NSCharacterSet *allowedCharacterSet = [NSCharacterSet characterSetWithCharactersInString:@"0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz_-.~=&"];

NSData *data = [self dataUsingEncoding:NSISOLatin1StringEncoding];
if (data) {
    NSMutableString *result = [@"" mutableCopy];
    const char *bytes = [data bytes];
    for (NSUInteger i = 0; i < [data length]; i++)
    {
        unsigned char ch = (unsigned char)bytes[i];
        if (ch >= 0x80 || ![allowedCharacterSet characterIsMember:ch]) {
            [result appendFormat:@"%%%02X", ch];
        } else {
            [result appendFormat:@"%c", ch];
        }
    }

    return [result copy];
}

return nil;}

相关问题