[英]Android: how to parse URL String with spaces to URI object?
I have a string representing an URL containing spaces and want to convert it to an URI object. 我有一个字符串表示包含空格的URL,并希望将其转换为URI对象。 If I simply try to create it via
如果我只是尝试通过它创建它
String myString = "http://myhost.com/media/File Name that has spaces inside.mp3";
URI myUri = new URI(myString);
it gives me 它给了我
java.net.URISyntaxException: Illegal character in path at index X
where index X
is the position of the first space in the URL string. 其中索引
X
是URL字符串中第一个空格的位置。
How can i parse myString
into a URI
object? 如何将
myString
解析为URI
对象?
You should in fact URI-encode the "invalid" characters. 实际上,您应该对 “无效”字符进行URI编码 。 Since the string actually contains the complete URL, it's hard to properly URI-encode it.
由于字符串实际上包含完整的URL,因此很难对其进行正确的URI编码。 You don't know which slashes
/
should be taken into account and which not. 你不知道哪些斜线
/
应该考虑哪些斜线,哪些斜线不应该考虑。 You cannot predict that on a raw String
beforehand. 您无法预先在原始
String
上预测。 The problem really needs to be solved at a higher level. 问题确实需要在更高层次上解决。 Where does that
String
come from? 这个
String
来自哪里? Is it hardcoded? 它是硬编码的吗? Then just change it yourself accordingly.
然后相应地自己更改。 Does it come in as user input?
它是否以用户输入的形式出现? Validate it and show error, let the user solve itself.
验证它并显示错误,让用户解决自己。
At any way, if you can ensure that it are only the spaces in URLs which makes it invalid, then you can also just do a string-by-string replace with %20
: 无论如何,如果您可以确保它只是 URL中的空格使其无效,那么您也可以只用
%20
进行逐字符串替换:
URI uri = new URI(string.replace(" ", "%20"));
Or if you can ensure that it's only the part after the last slash which needs to be URI-encoded, then you can also just do so with help of android.net.Uri
utility class: 或者,如果你可以确保它只是最后一个斜杠之后需要进行URI编码的部分,那么你也可以在
android.net.Uri
实用程序类的帮助下这样做:
int pos = string.lastIndexOf('/') + 1;
URI uri = new URI(string.substring(0, pos) + Uri.encode(string.substring(pos)));
Do note that URLEncoder
is insuitable for the task as it's designed to encode query string parameter names/values as per application/x-www-form-urlencoded
rules (as used in HTML forms). 请注意
URLEncoder
对于任务是不可或缺的,因为它被设计为根据application/x-www-form-urlencoded
规则(在HTML表单中使用)对查询字符串参数名称/值进行编码。 See also Java URL encoding of query string parameters . 另请参阅查询字符串参数的Java URL编码 。
java.net.URLEncoder.encode(finalPartOfString, "utf-8");
This will URL-encode the string. 这将对字符串进行URL编码 。
finalPartOfString
is the part after the last slash - in your case, the name of the song, as it seems. finalPartOfString
是最后一个斜杠之后的部分 - 在你的情况下,是歌曲的名字,看起来如此。
URL url = Test.class.getResource(args[0]); // reading demo file path from
// same location where class
File input=null;
try {
input = new File(url.toURI());
} catch (URISyntaxException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
To handle spaces, @, and other unsafe characters in arbitrary locations in the url path, Use Uri.Builder in combination with a local instance of URL as I have described here : 为了处理空间,@,并在URL路径的任意位置等不安全字符,请使用Uri.Builder与URL的本地实例组合我所描述的在这里 :
private Uri.Builder builder;
public Uri getUriFromUrl(String thisUrl) {
URL url = new URL(thisUrl);
builder = new Uri.Builder()
.scheme(url.getProtocol())
.authority(url.getAuthority())
.appendPath(url.getPath());
return builder.build();
}
I wrote this function: 我写了这个函数:
public static String encode(@NonNull String uriString) {
if (TextUtils.isEmpty(uriString)) {
Assert.fail("Uri string cannot be empty!");
return uriString;
}
// getQueryParameterNames is not exist then cannot iterate on queries
if (Build.VERSION.SDK_INT < 11) {
return uriString;
}
// Check if uri has valid characters
// See https://tools.ietf.org/html/rfc3986
Pattern allowedUrlCharacters = Pattern.compile("([A-Za-z0-9_.~:/?\\#\\[\\]@!$&'()*+,;" +
"=-]|%[0-9a-fA-F]{2})+");
Matcher matcher = allowedUrlCharacters.matcher(uriString);
String validUri = null;
if (matcher.find()) {
validUri = matcher.group();
}
if (TextUtils.isEmpty(validUri) || uriString.length() == validUri.length()) {
return uriString;
}
// The uriString is not encoded. Then recreate the uri and encode it this time
Uri uri = Uri.parse(uriString);
Uri.Builder uriBuilder = new Uri.Builder()
.scheme(uri.getScheme())
.authority(uri.getAuthority());
for (String path : uri.getPathSegments()) {
uriBuilder.appendPath(path);
}
for (String key : uri.getQueryParameterNames()) {
uriBuilder.appendQueryParameter(key, uri.getQueryParameter(key));
}
String correctUrl = uriBuilder.build().toString();
return correctUrl;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.