webentwicklung-frage-antwort-db.com.de

URL für die schnelle Codierung

Wenn ich eine Zeichenfolge wie folgt codiere: 

var escapedString = originalString.stringByAddingPercentEscapesUsingEncoding(NSUTF8StringEncoding)

es entgeht nicht den Schrägstrichen /

Ich habe diesen Ziel-C-Code gesucht und gefunden: 

NSString *encodedString = (NSString *)CFURLCreateStringByAddingPercentEscapes(
                        NULL,
                        (CFStringRef)unencodedString,
                        NULL,
                        (CFStringRef)@"!*'();:@&=+$,/?%#[]",
                        kCFStringEncodingUTF8 );

Gibt es eine einfachere Methode, eine URL zu kodieren, und wenn nicht, wie schreibe ich diese in Swift?

234
MegaCookie

Swift 3

In Swift 3 gibt es addingPercentEncoding

let originalString = "test/test"
let escapedString = originalString.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)
print(escapedString!)

Ausgabe:

test% 2Ftest

Schnell 1

In iOS 7 und höher gibt es stringByAddingPercentEncodingWithAllowedCharacters

var originalString = "test/test"
var escapedString = originalString.stringByAddingPercentEncodingWithAllowedCharacters(.URLHostAllowedCharacterSet())
println("escapedString: \(escapedString)")

Ausgabe: 

test% 2Ftest

Die folgenden sind nützliche (invertierte) Zeichensätze: 

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

Wenn Sie eine andere Gruppe von Zeichen mit Escapezeichen versehen möchten, erstellen Sie eine Gruppe:
Beispiel mit hinzugefügtem "=" Zeichen:

var originalString = "test/test=42"
var customAllowedSet =  NSCharacterSet(charactersInString:"=\"#%/<>[email protected]\\^`{|}").invertedSet
var escapedString = originalString.stringByAddingPercentEncodingWithAllowedCharacters(customAllowedSet)
println("escapedString: \(escapedString)")

Ausgabe: 

test% 2Ftest% 3D42

Beispiel zum Überprüfen von ASCII-Zeichen, die nicht im Set enthalten sind:

func printCharactersInSet(set: NSCharacterSet) {
    var characters = ""
    let iSet = set.invertedSet
    for i: UInt32 in 32..<127 {
        let c = Character(UnicodeScalar(i))
        if iSet.longCharacterIsMember(i) {
            characters = characters + String(c)
        }
    }
    print("characters not in set: \'\(characters)\'")
}
504
zaph

Sie können URLComponents verwenden, um zu vermeiden, dass Ihre Abfragezeichenfolge manuell prozentualisiert wird:

let scheme = "https"
let Host = "www.google.com"
let path = "/search"
let queryItem = URLQueryItem(name: "q", value: "Formula One")


var urlComponents = URLComponents()
urlComponents.scheme = scheme
urlComponents.Host = Host
urlComponents.path = path
urlComponents.queryItems = [queryItem]

if let url = urlComponents.url {
    print(url)   // "https://www.google.com/search?q=Formula%20One"
}

extension URLComponents {
    init(scheme: String = "https",
         Host: String = "www.google.com",
         path: String = "/search",
         queryItems: [URLQueryItem]) {
        self.init()
        self.scheme = scheme
        self.Host = Host
        self.path = path
        self.queryItems = queryItems
    }
}

let query = "Formula One"
if let url = URLComponents(queryItems: [URLQueryItem(name: "q", value: query)]).url {
    print(url)  // https://www.google.com/search?q=Formula%20One
}
43
Leo Dabus

Swift 3:

let allowedCharacterSet = (CharacterSet(charactersIn: "!*'();:@&=+$,/?%#[] ").inverted)

if let escapedString = originalString.addingPercentEncoding(withAllowedCharacters: allowedCharacterSet) {
//do something with escaped string
}
32
Hong Wei

Swift 3:

let originalString = "http://www.ihtc.cc?name=htc&title=iOS开发工程师"

1. codingQuery:

let escapedString = originalString.addingPercentEncoding(withAllowedCharacters:NSCharacterSet.urlQueryAllowed)

Ergebnis:

"http://www.ihtc.cc?name=htc&title=iOS%E5%BC%80%E5%8F%91%E5%B7%A5%E7%A8%8B%E5%B8%88" 

2. encodingURL:

let escapedString = originalString.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)

Ergebnis:

"http:%2F%2Fwww.ihtc.cc%3Fname=htc&title=iOS%E5%BC%80%E5%8F%91%E5%B7%A5%E7%A8%8B%E5%B8%88"
21
iHTCboy

Schnell 4

Um einen Parameter in eine URL zu kodieren, finde ich die Verwendung von .alphanumerics-Zeichensatz die einfachste Option:

let encoded = parameter.addingPercentEncoding(withAllowedCharacters: .alphanumerics)
let url = "http://www.example.com/?name=\(encoded!)"

Die Verwendung eines der Standard-Zeichensätze für die URL-Codierung (wie URLQueryAllowedCharacterSet oder URLHostAllowedCharacterSet) funktioniert nicht, da sie =- oder &-Zeichen nicht ausschließen.

Beachten Sie, dass durch die Verwendung von .alphanumerics einige Zeichen codiert werden, die nicht codiert werden müssen (wie -, ., _- oder ~-– siehe 2.3. Nicht reservierte Zeichen in RFC 3986. Ich finde die Verwendung von .alphanumerics einfacher als das Erstellen eines benutzerdefinierten Zeichensatzes, und es sind einige zusätzliche Zeichen, die zu codieren sind, uninteressant. Wenn Sie dies stört, erstellen Sie einen benutzerdefinierten Zeichensatz, wie in How to Prozentcodieren eines URL-Strings beschrieben. Beispiel:

var allowed = CharacterSet.alphanumerics
allowed.insert(charactersIn: "-._~") // as per RFC 3986
let encoded = parameter.addingPercentEncoding(withAllowedCharacters: allowed)
let url = "http://www.example.com/?name=\(encoded!)"

Warnung: Der Parameter encoded wird erzwungen. Bei ungültiger Unicode-Zeichenfolge kann es zum Absturz kommen. Siehe Warum ist der Rückgabewert von String.addingPercentEncoding () optional? . Anstelle des Erzwingens des Auspackens von encoded! können Sie encoded ?? "" oder if let encoded = ... verwenden.

15
Marián Černý

Alles ist gleich

var str = CFURLCreateStringByAddingPercentEscapes(
    nil,
    "test/test",
    nil,
    "!*'();:@&=+$,/?%#[]",
    CFStringBuiltInEncodings.UTF8.rawValue
)

// test%2Ftest
12
Bryan Chen

Swift 4 (nicht getestet - bitte kommentieren, ob es funktioniert oder nicht. Danke @sumizome für den Vorschlag)

var allowedQueryParamAndKey = NSCharacterSet.urlQueryAllowed
allowedQueryParamAndKey.remove(charactersIn: ";/?:@&=+$, ")
paramOrKey.addingPercentEncoding(withAllowedCharacters: allowedQueryParamAndKey)

Swift 3

let allowedQueryParamAndKey =  NSCharacterSet.urlQueryAllowed.remove(charactersIn: ";/?:@&=+$, ")
paramOrKey.addingPercentEncoding(withAllowedCharacters: allowedQueryParamAndKey)

Swift 2.2 (Ausleihen von Zaphs und Korrigieren von URL-Abfrageschlüssel- und Parameterwerten)

var allowedQueryParamAndKey =  NSCharacterSet(charactersInString: ";/?:@&=+$, ").invertedSet
paramOrKey.stringByAddingPercentEncodingWithAllowedCharacters(allowedQueryParamAndKey)

Beispiel:

let paramOrKey = "https://some.website.com/path/to/page.srf?a=1&b=2#top"
paramOrKey.addingPercentEncoding(withAllowedCharacters: allowedQueryParamAndKey)
// produces:
"https%3A%2F%2Fsome.website.com%2Fpath%2Fto%2Fpage.srf%3Fa%3D1%26b%3D2%23top"

Dies ist eine kürzere Version von Bryan Chens Antwort. Ich würde vermuten, dass urlQueryAllowed die Steuerzeichen erlaubt, durch die alles in Ordnung ist, sofern sie nicht Teil des Schlüssels oder Werts in Ihrer Abfragezeichenfolge sind, an dem sie maskiert werden müssen.

10
AJP

Schnell 4:

Dies hängt von den Kodierungsregeln Ihres Servers ab.

Apple bietet diese Klassenmethode an, aber es wird nicht angegeben, welche Art von RCF-Protokoll es folgt.

var escapedString = originalString.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)!

Nach diesem nützlichen tool sollten Sie die Kodierung dieser Zeichen für Ihre Parameter garantieren:

  • $ (Dollarzeichen) wird zu% 24
  • & (Kaufmännisches Und) wird zu% 26
  • + (Plus) wird zu% 2B
  • , (Komma) wird zu% 2C
  • : (Doppelpunkt) wird zu% 3A
  • ; (Semikolon) wird zu% 3B
  • = (Gleich) wird zu% 3D
  • ? (Fragezeichen) wird zu% 3F
  • @ (Kommerzielles A/At) wird zu% 40

Mit anderen Worten, wenn Sie über die URL-Kodierung sprechen, sollten Sie das Protokoll RFC 1738 befolgen.

Und Swift behandelt nicht die Codierung von + char zum Beispiel, aber es funktioniert gut mit diesen drei @:? Zeichen.

Um jeden Ihrer Parameter korrekt zu kodieren, reicht die .urlHostAllowed-Option nicht aus. Sie sollten auch die Sonderzeichen hinzufügen, z.

encodedParameter = parameter.replacingOccurrences(of: "+", with: "%2B")

Hoffe, das hilft jemandem, der verrückt wird, diese Informationen zu suchen.

8

Ich brauchte dies selbst, also schrieb ich eine String-Erweiterung, die sowohl URLEncoding-Strings als auch das üblichere Endziel zulässt, indem ein Parameterwörterbuch in URL-Parameter des Typs "GET" konvertiert wird:

extension String {
    func URLEncodedString() -> String? {
        var escapedString = self.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)
        return escapedString
    }
    static func queryStringFromParameters(parameters: Dictionary<String,String>) -> String? {
        if (parameters.count == 0)
        {
            return nil
        }
        var queryString : String? = nil
        for (key, value) in parameters {
            if let encodedKey = key.URLEncodedString() {
                if let encodedValue = value.URLEncodedString() {
                    if queryString == nil
                    {
                        queryString = "?"
                    }
                    else
                    {
                        queryString! += "&"
                    }
                    queryString! += encodedKey + "=" + encodedValue
                }
            }
        }
        return queryString
    }
}

Genießen!

4
BadPirate

Dieser arbeitet für mich.

func stringByAddingPercentEncodingForFormData(plusForSpace: Bool=false) -> String? {

    let unreserved = "*-._"
    let allowed = NSMutableCharacterSet.alphanumericCharacterSet()
    allowed.addCharactersInString(unreserved)

    if plusForSpace {
        allowed.addCharactersInString(" ")
    }

    var encoded = stringByAddingPercentEncodingWithAllowedCharacters(allowed)

    if plusForSpace {
        encoded = encoded?.stringByReplacingOccurrencesOfString(" ", withString: "+")
    }
    return encoded
}

Ich fand oben Funktion von diesem Link: http://useyourloaf.com/blog/how-to-percent-encode-a-url-string/ .

2
Gaurav Singla

Schnell 4.2

Eine schnelle einzeilige Lösung. Ersetzen Sie originalString durch den String, den Sie kodieren möchten.

var encodedString = originalString.addingPercentEncoding(withAllowedCharacters: CharacterSet(charactersIn: "!*'();:@&=+$,/?%#[]{} ").inverted)

Online-Spielplatz-Demo

0
ajzbc

Swift 4.2

Manchmal geschah dies nur deshalb, weil in slug OR keine URL-Codierung für Parameter vorhanden ist, die über die API-URL übergeben werden.

let myString = self.slugValue
                let csCopy = CharacterSet(bitmapRepresentation: CharacterSet.urlPathAllowed.bitmapRepresentation)
                let escapedString = myString!.addingPercentEncoding(withAllowedCharacters: csCopy)!
                //always "info:hello%20world"
                print(escapedString)

HINWEIS: Vergessen Sie nicht, bitmapRepresentation zu erkunden.

0
Vrushal Raut