Kiedy kodować spację do znaku plus (+) lub% 20?

Odpowiedzi:

481

+oznacza spację tylko w application/x-www-form-urlencodedtreści, taką jak część adresu URL zapytania:

http://www.example.com/path/foo+bar/path?query+name=query+value

W tym adresie URL nazwa parametru jest query namespacją, a wartość query valuespacją, ale nazwa folderu na ścieżce jest dosłownie foo+bar, a nie foo bar .

%20jest prawidłowym sposobem kodowania spacji w dowolnym z tych kontekstów. Jeśli więc musisz zakodować adres URL ciągu znaków, aby uwzględnić go w części adresu URL, zawsze możesz bezpiecznie zastąpić spacje %20znakiem plus %2B. Oto co np. encodeURIComponent()robi w JavaScript. Niestety, nie jest to, co robi urlencode w PHP ( rawurlencode jest bezpieczniejszy).

Zobacz także Aplikacja do specyfikacji HTML 4.01 / x-www-form-urlencoded

Bobin
źródło
5
naprawdę jestem zdezorientowany, moje pytanie brzmi, kiedy przeglądarka robi pierwszą formę, a kiedy druga?
Muhammad Hewedy
11
Przeglądarka utworzy query+name=query+valueparametr z formularza za pomocą <input name="query name" value="query value">. Nie utworzy query%20namez formularza, ale można go bezpiecznie używać, np. jeśli składasz razem formularz do złożenia XMLHttpRequest. Jeśli masz adres URL ze spacją, na przykład <a href="http://www.example.com/foo bar/">, to przeglądarka go zakoduje, %20abyś mógł naprawić swój błąd, ale prawdopodobnie nie należy na nim polegać.
bobince
6
jaką funkcję on JavaScript make foo bardo foo+bar?
Sisir
21
@Sisir: nie ma funkcji JS, która wykonuje kodowanie formularzy URL. Możesz naturalnie zrobić, encodeURIComponent(s).replace(/%20/g, '+')jeśli naprawdę potrzebujesz+
Bob
2
To bardzo, bardzo mylący przykład czegoś, co zostało zakodowane w formie. Nie ma to nic wspólnego z adresami URL.
Dave Van den Eynde
54

http://www.example.com/some/path/to/resource?param1=value1

Część przed znakiem zapytania musi używać kodowania% (czyli %20spacji), po znaku zapytania można użyć jednej %20lub +spacji. Jeśli potrzebujesz faktury +po znaku zapytania, użyj %2B.

cerberos
źródło
6
@DaveVandenEynde Dlaczego nie?
cerberos
10
bo to źle. Jest to część starego typu mediów / x-www-form-urlencoded, który nie dotyczy adresów URL. Ponadto, decodeURIComponentnie dekoduje go.
Dave Van den Eynde
3
Tak, prawdopodobnie został skopiowany z RFC 1630 i nigdy tak naprawdę nie był standardem. tools.ietf.org/html/rfc3986 to standard (zaktualizowany ponownie dla IPv6 lub coś w tym rodzaju). Jasne, że przeglądarki nadal go obsługują, ale co to oznacza? Kod serwera lub klienta odczytuje ciąg zapytania i dekoduje go, a nie przeglądarka. Przeglądarka po prostu przekazuje go tam iz powrotem, a ponieważ +jest to znak zastrzeżony , zostanie zachowany przez przeglądarkę.
Dave Van den Eynde
18
Google używa + do spacji w swoich adresach wyszukiwania ( google.com/#q=perl+equivalent+to+php+urlencode+spaces+as+%2B ).
Justin
2
FYI: Railsy +domyślnie również dekodują spacje za pomocą ( { foo: 'bar bar'}.to_query=> foo=bar+bar)
wrtsprt
46

Tak więc odpowiedzi tutaj są nieco niekompletne. Użycie „% 20” do zakodowania spacji w adresach URL jest wyraźnie zdefiniowane w RFC3986 , która definiuje sposób budowania identyfikatora URI. W tej specyfikacji nie ma wzmianki o używaniu „+” do kodowania spacji - jeśli przechodzisz wyłącznie przez tę specyfikację, spacja musi być zakodowana jako „% 20”.

Wzmianka o używaniu „+” do kodowania spacji pochodzi z różnych wcieleń specyfikacji HTML - szczególnie w sekcji opisującej typ zawartości „application / x-www-form-urlencoded”. Służy do publikowania danych formularza.

Teraz specyfikacja HTML 2.0 (RFC1866) wyraźnie stwierdza w sekcji 8.2.2, że część zapytania w ciągu znaków adresu URL żądania GET powinna być zakodowana jako „application / x-www-form-urlencoded”. Teoretycznie sugeruje to, że dozwolone jest użycie znaku „+” w adresie URL w ciągu zapytania (po „?”).

Ale ... czy to naprawdę? Pamiętaj, że HTML sam w sobie jest specyfikacją treści, a adresy URL z ciągami zapytań mogą być używane z treściami innymi niż HTML. Ponadto, podczas gdy późniejsze wersje specyfikacji HTML nadal definiują „+” jako dozwolone w treści „application / x-www-form-urlencoded”, całkowicie pomijają tę część, mówiąc, że ciągi zapytań GET są zdefiniowane jako ten typ. W rzeczywistości nie ma żadnej wzmianki o kodowaniu ciągu zapytania w niczym po specyfikacji HTML 2.0.

Które pozostawia nam pytanie - czy jest ważne? Na pewno jest DUŻO starszego kodu, który obsługuje „+” w ciągach zapytań, a także dużo kodu, który go generuje. Tak więc szanse są dobre, że nie złamiesz się, jeśli użyjesz „+”. (I faktycznie przeprowadziłem wszystkie badania na ten temat niedawno, ponieważ odkryłem główną witrynę, która nie zaakceptowała „% 20” w zapytaniu GET jako spacji. W rzeczywistości nie udało im się dekodować ŻADNEGO procentu zakodowanego znaku. Więc usługa może być również istotne).

Ale po czystym przeczytaniu specyfikacji, bez przeniesienia języka ze specyfikacji HTML 2.0 do późniejszych wersji, adresy URL są w całości objęte RFC3986, co oznacza, że ​​spacje powinny zostać przekonwertowane na „% 20”. I zdecydowanie tak powinno być, jeśli żądasz czegoś innego niż dokument HTML.

zgwortz
źródło
Aby dodać do swojej odpowiedzi, Chrome domyślnie koduje spacje w adresach URL jako %20( <a href="?q=a b">), ale podczas wysyłania formularza używa +znaku. Możesz to zmienić, jawnie używając +znaku ( <a href="?q=a+b">) lub wysyłając formularz za pomocą XMLHTTPRequest.
x-yuri,
Naprawdę trudno jest zrozumieć cel dodania URLSearchParams developers.google.com/web/updates/2016/01/urlsearchparams , który działa w jakiś starszy sposób (serializuj SPACJĘ w „+”). To nawet nie jest obsługiwane w IE11!
Nymphetamine
9

Lepiej zawsze kodować spacje jako% 20, a nie jako „+”.

To była RFC-1866 (specyfikacja HTML 2.0), która określa, że ​​znaki spacji powinny być kodowane jako „+” w „pary klucz-wartość typu application / x-www-form-urlencoded”. (patrz ust. 8.2.1. akapit 1). Ten sposób kodowania danych formularza jest również podany w późniejszych specyfikacjach HTML, poszukaj odpowiednich akapitów na temat application / x-www-form-urlencoded.

Oto przykład takiego ciągu w adresie URL, w którym RFC-1866 zezwala na kodowanie spacji jako plusów: „http://example.com/over/there?name=foo+bar”. Tak więc, tylko po „?” Spacje można zastąpić plusami, zgodnie z RFC-1866. W innych przypadkach spacje powinny być kodowane do% 20. Ponieważ jednak trudno jest określić kontekst, najlepszą praktyką jest, aby nigdy nie kodować spacji jako „+”.

Poleciłbym procentowe kodowanie wszystkich znaków oprócz „niezarezerwowanych” zdefiniowanych w RFC-3986, str. 2.3

unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~"
Maxim Masiutin
źródło
1
W .Net Framework UrlEncode używa „+” w QueryString, ale w nowoczesnym .Net Core% 20 jest używany
Michael Freidgeim
@ MiFreidgeimSO-stopbeingevil Dziękujemy za poinformowanie nas. Wygląda na to, że nowoczesny .Net Core postanowił być bardziej spójny i kompatybilny.
Maxim Masiutin
2

Jaka jest różnica: zobacz inne odpowiedzi.

Kiedy używać +zamiast %20? Użyj, +jeśli z jakiegoś powodu chcesz, aby ciąg zapytania URL ( ?.....) lub fragment skrótu ( #....) były bardziej czytelne. Przykład: Możesz to przeczytać:

https://www.google.se/#q=google+doesn%27t+encode+:+and+uses+%2B+instead+of+spaces ( %2B= +)

Ale o wiele trudniej jest przeczytać: (przynajmniej dla mnie)

https://www.google.se/#q=google%20doesn%27t%20oops%20:%20%20this%20text%20%2B%20is%20different%20spaces

Myślę, że +jest mało prawdopodobne, aby cokolwiek zepsuć, ponieważ Google używa +(patrz pierwszy link powyżej) i prawdopodobnie o tym pomyśleli. Użyję +siebie tylko dlatego, że czytelny + Google uważa, że ​​jest OK.

KajMagnus
źródło
7
Mówię, że argument „czytelność” jest najlepszą obroną dla „+”. Argument „google robi to” jest błędny en.wikipedia.org/wiki/Argument_from_authority
FlipMcF
2
@FlipMcF Błędna strona Wikipedii argumentująca autorytet dotyczy „kiedy autorytet jest cytowany na temat poza jego obszarem specjalizacji lub gdy cytowany autorytet nie jest prawdziwym ekspertem ” - myślę jednak, że komputery, HTTP i URL kodowanie jest kwestią podlegającą specjalizacji Google.
KajMagnus,
3
@FlipMcF Powoływanie się na zachowanie google w tym przypadku jest ważnym argumentem przemawiającym za użyciem „+” w adresach URL. To nie jest tak, że Google jest autorytetem, ale ten Google jest prawdopodobnie największą firmą internetową, a jeśli coś zrobią, jest bardzo mało prawdopodobne, aby przeglądarki pewnego dnia przestały wspierać tę praktykę. Ponadto Google Chrome jest jedną z przeglądarek o najwyższym udziale i będą obsługiwać wszystko, co Google zechce. Podsumowując, powiedziałbym, że nikt, kto użyje „+” zamiast „% 20”, nie będzie miał trudności z tego powodu w najbliższej przyszłości.
jdferreira
Chciałbym kontynuować ten argument w innym miejscu, w którym istnieje odwołanie do popularności, aby odmówić uznania odwołania do władzy. Przynajmniej wszyscy możemy się zgodzić co do jednej rzeczy: „+” przewyższa „% 20”
FlipMcF
1
W rzeczywistości adres URL z% 20 jest o wiele łatwiejszy do odczytania, ponieważ przeglądarki (stacjonarne) wyświetlają zdekodowany adres URL na dole okna, jeśli przesuniesz kursor myszy nad linkiem. Znaki plus są wyświetlane bez zmian.
Martin