Java URL encodage des paramètres de chaîne de requête
Dire que j'ai une URL
http://example.com/query?q=
et j'ai une requête entrée par l'utilisateur tel que:
mot aléatoire £500 banque $
je veux que le résultat soit une URL correctement encodée:
http://example.com/query?q=random%20word%20%A3500%20bank%20%24
Quelle est la meilleure façon d'y parvenir? J'ai essayé URLEncoder
et de créer des objets URI/URL mais aucun d'eux ne sort tout à fait bien.
9 réponses
URLEncoder
ça devrait être la solution. Vous devez seulement garder à l'esprit de coder seulement le nom et/ou la valeur du paramètre de chaîne de requête individuel, pas L'URL entière, pour sûr pas le caractère de séparateur de paramètre de chaîne de requête &
ni le caractère de séparateur de nom-valeur de paramètre =
.
String q = "random word £500 bank $";
String url = "http://example.com/query?q=" + URLEncoder.encode(q, "UTF-8");
notez que les espaces dans les paramètres de requête sont représentés par +
, et non %20
, qui est légitimement valable. Le %20
doit généralement être utilisé pour représenter des espaces dans URI lui-même (la partie avant le caractère de séparateur de chaîne de requête ?
), pas dans la chaîne de requête (la partie après ?
).
il y a aussi deux méthodes encode()
. Une sans argument de charset et une autre avec. Celui sans argument charset est déprécié. Ne l'utilisez jamais et spécifiez toujours l'argument charset. Le javadoc recommande même explicitement D'utiliser L'encodage UTF-8, comme prescrit par RFC3986 et W3C .
tous les autres caractères sont dangereux et sont d'abord convertis en un ou plusieurs octets à l'aide d'un schéma d'encodage. Ensuite chaque octet est représenté par la chaîne de 3 caractères "%xy", où xy est la représentation hexadécimale à deux chiffres du octet. l'encodage recommandé schéma à utiliser est UTF-8 . Cependant, pour des raisons de compatibilité, si l'encodage n'est pas spécifié, alors l'encodage par défaut de la plate-forme est utilisée.
voir aussi:
Je n'utiliserais pas URLEncoder
. En plus d'être mal nommé ( URLEncoder
n'a rien à voir avec les URLs), inefficace (il utilise un StringBuffer
au lieu de Builder et fait un couple d'autres choses qui sont lents) sa façon aussi trop facile de le faire foirer.
à la place, j'utiliserais URIBuilder
ou "Spring's org.springframework.web.util.UriUtils.encodeQuery
ou" Commons Apache HttpClient
.
La raison étant que vous devez échapper aux paramètres de requête nom (réponse de BalusC q
) différent de la valeur du paramètre.
le seul inconvénient de ce qui précède (que j'ai trouvé douloureusement) est que les URL ne sont pas un vrai sous-ensemble de D'URI .
code échantillon:
import org.apache.http.client.utils.URIBuilder;
URIBuilder ub = new URIBuilder("http://example.com/query");
ub.addParameter("q", "random word £500 bank $");
String url = ub.toString();
// Result: http://example.com/query?q=random+word+%C2%A3500+bank+%24
comme je ne fais que lier à d'autres réponses, j'ai noté ceci comme un wiki communautaire. N'hésitez pas à modifier.
vous devez d'abord créer un URI comme:
String urlStr = "http://www.example.com/CEREC® Materials & Accessories/IPS Empress® CAD.pdf"
URL url= new URL(urlStr);
URI uri = new URI(url.getProtocol(), url.getUserInfo(), url.getHost(), url.getPort(), url.getPath(), url.getQuery(), url.getRef());
convertissez alors cet Uri en chaîne ASCII:
urlStr=uri.toASCIIString();
maintenant votre chaîne d'url est entièrement encodée d'abord nous avons fait l'encodage d'url simple et ensuite nous l'avons converti en chaîne ASCII pour s'assurer qu'aucun caractère en dehors de nous-ASCII ne reste dans la chaîne. C'est exactement ce que font les navigateurs.
Guava 15 a maintenant ajouté un ensemble d'échappements d'URL .
Apache bibliothèque de composants Http fournit une option soignée pour la construction et l'encodage des paramètres de requête -
With Httpcomposants 4.x utilisation - URLEncodedUtils
Pour HttpClient 3.x utilisation - EncodingUtil
Voici une méthode que vous pouvez utiliser dans votre code pour convertir une chaîne d'url et une carte de paramètres en une chaîne d'url encodée valide contenant les paramètres de la requête.
String addQueryStringToUrlString(String url, final Map<Object, Object> parameters) throws UnsupportedEncodingException {
if (parameters == null) {
return url;
}
for (Map.Entry<Object, Object> parameter : parameters.entrySet()) {
final String encodedKey = URLEncoder.encode(parameter.getKey().toString(), "UTF-8");
final String encodedValue = URLEncoder.encode(parameter.getValue().toString(), "UTF-8");
if (!url.contains("?")) {
url += "?" + encodedKey + "=" + encodedValue;
} else {
url += "&" + encodedKey + "=" + encodedValue;
}
}
return url;
}
1. divise L'URL en parties structurelles. Utilisez java.net.URL
pour cela.
2. encodez chaque pièce de structure correctement!
3. utiliser IDN.toASCII(putDomainNameHere)
à Punycode encoder le nom d'hôte!
4. Utiliser java.net.URI.toASCIIString()
% -encoder, NFC codé en unicode (mieux serait NFKC!). Pour plus d'info voir: comment coder correctement cette URL
URL url= new URL("http://example.com/query?q=random word £500 bank $");
URI uri = new URI(url.getProtocol(), url.getUserInfo(), IDN.toASCII(url.getHost()), url.getPort(), url.getPath(), url.getQuery(), url.getRef());
String correctEncodedURL=uri.toASCIIString();
System.out.println(correctEncodedURL);
Imprime
http://example.com/query?q=random%20word%20%C2%A3500%20bank%20$
sous android j'utiliserais ce code:
Uri myUI = Uri.parse ("http://example.com/query").buildUpon().appendQueryParameter("q","random word A3500 bank 24").build();
où Uri
est un android.net.Uri
- utilisez cette URLEncoder.encoder (query, StandardCharsets.UTF_8.displayName()); ou Ceci: URLEncoder.encoder (query, "UTF-8");
-
vous pouvez utiliser le code suivant.
String encodedUrl1 = UriUtils.encodeQuery(query, "UTF-8");//not change String encodedUrl2 = URLEncoder.encode(query, "UTF-8");//changed String encodedUrl3 = URLEncoder.encode(query, StandardCharsets.UTF_8.displayName());//changed System.out.println("url1 " + encodedUrl1 + "\n" + "url2=" + encodedUrl2 + "\n" + "url3=" + encodedUrl3);