Parsing query strings on Android
Since Android M things have got more complicated. The answer of android.net.URI.getQueryParameter()
has a bug which breaks spaces before JellyBean.
Apache URLEncodedUtils.parse()
worked, but was deprecated in L, and removed in M.
So the best answer now is UrlQuerySanitizer
. This has existed since API level 1 and still exists. It also makes you think about the tricky issues like how do you handle special characters, or repeated values.
The simplest code is
UrlQuerySanitizer.ValueSanitizer sanitizer = UrlQuerySanitizer.getAllButNullLegal();
// remember to decide if you want the first or last parameter with the same name
// If you want the first call setPreferFirstRepeatedParameter(true);
sanitizer.parseUrl(url);
String value = sanitizer.getValue("paramName");
If you are happy with the default parsing behavior you can do:
new UrlQuerySanitizer(url).getValue("paramName")
but you should make sure you understand what the default parsing behavor is, as it might not be what you want.
Escape encoding while parsing query parameter android
Thanks for the responses, I had done it using UrlQuerySanitizer.
Writing the code here.
First, I extended the UrlQuerySanitizer class as
public class CustomUrlQuerySanitizer extends UrlQuerySanitizer {
@Override
protected void parseEntry(String parameter, String value) {
// String unescapedParameter = unescape(parameter);
ValueSanitizer valueSanitizer =
getEffectiveValueSanitizer(parameter);
if (valueSanitizer == null) {
return;
}
// String unescapedValue = unescape(value);
String sanitizedValue = valueSanitizer.sanitize(value);
addSanitizedEntry(parameter, sanitizedValue);
}
}
Then, parsed the url as,
String id = null;
if (uri != null) {
UrlQuerySanitizer urlQuerySanitizer = new CustomUrlQuerySanitizer();
urlQuerySanitizer.registerParameter("id",
new UrlQuerySanitizer.IllegalCharacterValueSanitizer(
UrlQuerySanitizer.IllegalCharacterValueSanitizer.ALL_OK
));
urlQuerySanitizer.parseUrl(uri.toString());
id = urlQuerySanitizer.getValue("id");
Parse a URI String into Name-Value Collection
If you are looking for a way to achieve it without using an external library, the following code will help you.
public static Map<String, String> splitQuery(URL url) throws UnsupportedEncodingException {
Map<String, String> query_pairs = new LinkedHashMap<String, String>();
String query = url.getQuery();
String[] pairs = query.split("&");
for (String pair : pairs) {
int idx = pair.indexOf("=");
query_pairs.put(URLDecoder.decode(pair.substring(0, idx), "UTF-8"), URLDecoder.decode(pair.substring(idx + 1), "UTF-8"));
}
return query_pairs;
}
You can access the returned Map using <map>.get("client_id")
, with the URL given in your question this would return "SS".
UPDATE URL-Decoding added
UPDATE As this answer is still quite popular, I made an improved version of the method above, which handles multiple parameters with the same key and parameters with no value as well.
public static Map<String, List<String>> splitQuery(URL url) throws UnsupportedEncodingException {
final Map<String, List<String>> query_pairs = new LinkedHashMap<String, List<String>>();
final String[] pairs = url.getQuery().split("&");
for (String pair : pairs) {
final int idx = pair.indexOf("=");
final String key = idx > 0 ? URLDecoder.decode(pair.substring(0, idx), "UTF-8") : pair;
if (!query_pairs.containsKey(key)) {
query_pairs.put(key, new LinkedList<String>());
}
final String value = idx > 0 && pair.length() > idx + 1 ? URLDecoder.decode(pair.substring(idx + 1), "UTF-8") : null;
query_pairs.get(key).add(value);
}
return query_pairs;
}
UPDATE Java8 version
public Map<String, List<String>> splitQuery(URL url) {
if (Strings.isNullOrEmpty(url.getQuery())) {
return Collections.emptyMap();
}
return Arrays.stream(url.getQuery().split("&"))
.map(this::splitQueryParameter)
.collect(Collectors.groupingBy(SimpleImmutableEntry::getKey, LinkedHashMap::new, mapping(Map.Entry::getValue, toList())));
}
public SimpleImmutableEntry<String, String> splitQueryParameter(String it) {
final int idx = it.indexOf("=");
final String key = idx > 0 ? it.substring(0, idx) : it;
final String value = idx > 0 && it.length() > idx + 1 ? it.substring(idx + 1) : null;
return new SimpleImmutableEntry<>(
URLDecoder.decode(key, StandardCharsets.UTF_8),
URLDecoder.decode(value, StandardCharsets.UTF_8)
);
}
Running the above method with the URL
https://stackoverflow.com?param1=value1¶m2=¶m3=value3¶m3
returns this Map:
{param1=["value1"], param2=[null], param3=["value3", null]}
How can I get parameters from URL in Android?
You can use the Uri class in Android to do this; https://developer.android.com/reference/android/net/Uri.html
Uri uri = Uri.parse("http://www.chalklit.in/post.html?chapter=V-Maths-Addition%20&%20Subtraction&post=394");
String server = uri.getAuthority();
String path = uri.getPath();
String protocol = uri.getScheme();
Set<String> args = uri.getQueryParameterNames();
Then you can even get a specific element from the query parameters as such;
String chapter = uri.getQueryParameter("chapter"); //will return "V-Maths-Addition "
Easiest way to parse individual query parameter data from an API URL on Android Kotlin
Use android.net.UrlQuerySanitizer
to parse the individual values from the aforementioned form of API endpoints like this:
import android.net.UrlQuerySanitizer
//..
val sanitizer = UrlQuerySanitizer()
sanitizer.setAllowUnregisteredParamaters(true)
sanitizer.parseUrl(url)
var msg : String? = sanitizer.getValue("msg")
//For removing the "+" signs or any other unwanted signs to get a displayable message like the question:
msg?.let {
if (it.contains("+")) {
msg = it.replace("+", " ")
}
}
Extract parameter values from url android
In Android, you should never use URLEncodedUtils which is now deprecated. A good alternative is to use the Uri class instead: retrieve the query parameter keys using getQueryParameterNames()
then iterate on them and retrieve each value using getQueryParameter()
.
Not able to get query paramter value using android.net.Uri#getQueryParameter
I think that Android's Uri
implementation is getting confused over those square brackets, as those appear to be invalid URL syntax.
If you control the Web service, you might reconsider the use of square brackets, as they may cause problems with other clients. Otherwise, you may need to play some icky regex games to replace those square brackets with escaped equivalents or otherwise find ways to sanitize the URL before fully parsing it with Uri
.
How to parse query param effectively in java?
Here is another possible solution:
Pattern pat = Pattern.compile("([^&=]+)=([^&]*)");
Matcher matcher = pat.matcher(requestUri);
Map<String,String> map = new HashMap<>();
while (matcher.find()) {
map.put(matcher.group(1), matcher.group(2));
}
System.out.println(map);
How to do a query in Android using Parse?
Your real problem here is your ArrayAdapter. You would need a custom adapter if you want to use Parse objects as your data type. The built in adapter doesn't know how to use Parse objects and is outputting the object as a string for you. Instead you should do something like
arrayAdapter = new ArrayAdapter(this, android.R.layout.simple_list_item_1, MyNamesList);
Where MyNamesList
is of type String
.
It's hard to help on your query without more information but you are getting Parse objects back, you just need to get the name out of them with something like
MyList.get(i).getString("name");
Related Topics
Java Equivalent to PHP'S Preg_Replace_Callback
How to Fix 'Android.Os.Networkonmainthread
exception'
Read/Write String From/To a File in Android
Should I Actually Remove the Valueeventlistener
Java Using Much More Memory Than Heap Size (Or Size Correctly Docker Memory Limit)
What Is a Nullpointerexception, and How to Fix It
Sort Arraylist of Custom Objects by Property
Loop Doesn't See Value Changed by Other Thread Without a Print Statement
What Are the Possible Values of the Hibernate Hbm2Ddl.Auto Configuration and What Do They Do
How to Really Read Text File from Classpath in Java
Signing Pdfs on a Server Document Using a Signature from the User
How to Return Datasnapshot Value as a Result of a Method
How to Save the Current Date/Time When I Add New Value to Firebase Realtime Database
Firebase Android Listview Not Being Displayed
Error: Could Not Find or Load Main Class
How to Compare Strings in Java
Why Does My Arraylist Contain N Copies of the Last Item Added to the List