I'm trying to write a reusable asynctask where I define the type of a class that Gson should deserialize to in the asynctask's constructor. Having never worked with Java Generics before, I'm a little lost on how to proceed. I can't figure out the correct syntax for the fromJson method.
The error I receive is
Cannot resolve method'fromJson(java.io.InputStream, java.lang.Class<T>)'
The full AsyncTask...
public class AsyncGet<T> extends AsyncTask<String,String,ApiResponse> {
private String TAG = "AsyncGet";
private HttpURLConnection mConnection;
private IApiCallback mCallback;
private Context mContext;
private Class<T> type;
public AsyncGet(IApiCallback callback, Class<T> classType, Context context) {
this.mCallback = callback;
this.mContext = context;
this.type = classType;
}
#Override
protected ApiResponse doInBackground(String... uri) {
try {
URL url = new URL(uri[0]);
mConnection = (HttpURLConnection) url.openConnection();
mConnection.setConnectTimeout(5000);
mConnection.setReadTimeout(60000);
mConnection.addRequestProperty("Accept-Encoding", "gzip");
mConnection.addRequestProperty("Cache-Control", "no-cache");
mConnection.connect();
String encoding = mConnection.getContentEncoding();
InputStream inStream;
if (encoding != null && encoding.equalsIgnoreCase("gzip")) {
inStream = new GZIPInputStream(mConnection.getInputStream());
} else {
inStream = mConnection.getInputStream();
}
if (inStream != null) {
try {
Gson gson = new Gson();
ApiResponse response = new ApiResponse();
response.data = gson.fromJson(inStream, type); // What is wrong here?
response.responseCode = mConnection.getResponseCode();
response.responseMessage = mConnection.getResponseMessage();
return response;
} catch (Exception e) {
Log.i(TAG, "Exception");
if (e.getMessage() != null) {
Log.e(TAG, e.getMessage());
}
} finally {
inStream.close();
}
}
} catch (SocketTimeoutException e) {
Log.i(TAG, "Socket Timeout occurred");
FileLogger.getFileLogger(mContext).ReportException(TAG + ", SocketTimeoutException ", e);
} catch (MalformedURLException e) {
FileLogger.getFileLogger(mContext).ReportException(TAG + ", MalformedUrlException ", e);
} catch (IOException e) {
Log.i(TAG," IO Exception");
FileLogger.getFileLogger(mContext).ReportException(TAG + ", IOException ", e);
if (e.getMessage() != null) {
Log.i(TAG, e.getMessage());
}
} finally {
mConnection.disconnect();
}
return null;
}
#Override
protected void onPostExecute(ApiResponse response) {
if (!isCancelled())
mCallback.Execute(response);
}
}
The class Gson does not have a method fromJson(..) that expects an InputStream as its first argument. It does, however, have such a method that accepts a Reader. So just wrap your InputStream in a Reader implementation, InputStreamReader to be exact.
response.data = gson.fromJson(new InputStreamReader(inStream), type);
Go through the javadoc before you use a class.
Related
I'm programming an app that calculates, in route, two locations. I've implemented the google places API to get the lat/lon based on name or address but I can't implement the Distance API. The classes/methods don't appear when I try to import. Below is an example of what I'm trying to do.
private static final String API_KEY = "YOUR_API_KEY";
private static final GeoApiContext context = new
GeoApiContext().setApiKey(API_KEY);
public DistanceMatrix estimateRouteTime(DateTime time, Boolean isForCalculateArrivalTime, DirectionsApi.RouteRestriction routeRestriction, LatLng departure, LatLng... arrivals) {
try {
DistanceMatrixApiRequest req = DistanceMatrixApi.newRequest(context);
if (isForCalculateArrivalTime) {
req.departureTime(time);
} else {
req.arrivalTime(time);
}
if (routeRestriction == null) {
routeRestriction = DirectionsApi.RouteRestriction.TOLLS;
}
DistanceMatrix trix = req.origins(departure)
.destinations(arrivals)
.mode(TravelMode.DRIVING)
.avoid(routeRestriction)
.language("fr-FR")
.await();
return trix;
} catch (ApiException e) {
System.out.println(e.getMessage());
} catch (Exception e) {
System.out.println(e.getMessage());
}
return null;
}
The GeoApiContext and DistanceMatrix don't appear at import.
Tks for help.
Answering my question...
public class GetJson extends AsyncTask<Void, Void, DeliveryData> {
#Override
protected void onPreExecute() {
// progressDialog
}
#Override
protected DeliveryData doInBackground(Void... params) {
Utils util = new Utils();
DeliveryData json = util.getInfo("https://maps.googleapis.com/maps/api/distancematrix/json?units=metric&origins="+latLngCompany.latitude+","+latLngCompany.longitude+
"&destinations="+latPlace+","+lonPlace+"&key=" + APISERVERKEY);
deliveryData.saveDeliveryData();
return json;
}
#Override
protected void onPostExecute(DeliveryData deliveryData) {
//progressDialog.dismiss
}
}
Created a AsyncTask to get json from url with the especifics parameters.
public class Utils {
public DeliveryData getInfo(String end){
String json;
DeliveryData output;
json = NetworkUtils.getJSONFromAPI(end);
output = parseJson(json);
return output;
}
private DeliveryData parseJson(String json){
try {
DeliveryData deliveryData = new DeliveryData();
JSONObject distanceJson = new JSONObject(json)
.getJSONArray("rows")
.getJSONObject(0)
.getJSONArray("elements")
.getJSONObject(0)
.getJSONObject("distance");
Double distanceDouble = null ;
String distance = distanceJson.get("text").toString();
if (distance.contains("km")){
distanceDouble = Double.parseDouble(distance.replace("km", ""));
}else {
distanceDouble = Double.parseDouble("0." + distance.replace("m", ""));
}
deliveryData.setDistance(distanceDouble);
return deliveryData;
}catch (JSONException e){
e.printStackTrace();
return null;
}
}
}
At getInfo, the data from url is passed to string. Then, parseJson is call to transform the string to JsonObject.
My Json there is only one position. So, the object is selected at array and the String is parse to Double, excluding the chars. In the end, the distance is saved at object.
public class NetworkUtils {
public static String getJSONFromAPI (String url){
String output = "";
try {
URL apiEnd = new URL(url);
int responseCode;
HttpURLConnection connection;
InputStream is;
connection = (HttpURLConnection) apiEnd.openConnection();
connection.setRequestMethod("GET");
connection.setReadTimeout(15000);
connection.setConnectTimeout(15000);
connection.connect();
responseCode = connection.getResponseCode();
if(responseCode < HttpURLConnection.HTTP_BAD_REQUEST){
is = connection.getInputStream();
}else {
is = connection.getErrorStream();
}
output = convertISToString(is);
is.close();
connection.disconnect();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (ProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return output;
}
private static String convertISToString(InputStream is){
StringBuffer buffer = new StringBuffer();
try {
BufferedReader br;
String row;
br = new BufferedReader(new InputStreamReader(is));
while ((row = br.readLine())!= null){
buffer.append(row);
}
br.close();
} catch (IOException e) {
e.printStackTrace();
}
return buffer.toString();
}
}
This class is resposible for connecting to server and get the data from url.
I am having an error in the method that retrieves the JSONObject and converts it to a string, the error says "!DOCTYPE of type java.lang.String cannot be converted to JSONObject"
public class FindSentimentTask extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... url) {
String toReturn= "DID NOT WORK";
try
{
toReturn=getResponseFromHttpUrl(url[0]);
}catch (Exception e)
{
Log.d("ErrorInApp","exception on get Response from HTTP call" + e.getMessage());
return toReturn;
}
return toReturn;
}
protected void onPostExecute(String sentimentData) {
try {
JSONObject sentimentJSON = new JSONObject(sentimentData);
((TextView)findViewById(R.id.output)).setText(sentimentJSON.toString());
//String testOutput = sentimentJSON.get("docs").toString();
//((TextView)findViewById(R.id.output)).setText(testOutput.toString());
} catch (Exception e) {
Log.d("ErrorInApp","exception in onPostExecute" + e.getMessage());
}
}
}
public static String getResponseFromHttpUrl(String url) throws IOException {
URL theURL = new URL(url);
HttpURLConnection urlConnection = (HttpURLConnection) theURL.openConnection();
try {
InputStream in = urlConnection.getInputStream();
Scanner scanner = new Scanner(in);
scanner.useDelimiter("\\A");
boolean hasInput = scanner.hasNext();
if (hasInput) {
return scanner.next();
} else {
return null;
}
} finally {
urlConnection.disconnect();
}
}
More specificaly the error is here where I retrieve the JSONObject and turn it into a string to display in a TextView
protected void onPostExecute(String sentimentData) {
try {
JSONObject sentimentJSON = new JSONObject(sentimentData);
((TextView)findViewById(R.id.output)).setText(sentimentJSON.toString());
} catch (Exception e) {
Log.d("ErrorInApp","exception in onPostExecute" + e.getMessage());
}
}
The API I am using is https://developer.nytimes.com/article_search_v2.json
I have a problem with connecting to WAMP server with my android program that I made with eclipse....
This is my class:
public class Webservice {
public static String readurl(String url)
{
try {
HttpClient client = new DefaultHttpClient();
HttpPost method = new HttpPost(url);
HttpResponse response = client.execute(method);
InputStream inputStream = response.getEntity().getContent();
String resault = ConvertInputStream(inputStream);
return resault;
}
catch (ClientProtocolException e) {
//e.printStackTrace();
Log.i("Log", "Protocol");
}
catch (IOException e) {
//e.printStackTrace();
Log.i("Log", "IOException");
}
return "read";
}
private static String ConvertInputStream(InputStream inputStream)
{
try
{
BufferedReader reader = new BufferedReader(new
InputStreamReader(inputStream));
StringBuilder builder = new StringBuilder();
String line = null;
while ((line = reader.readLine()) != null)
{
builder.append(line);
}
return builder.toString();
}
catch (IOException e)
{
e.printStackTrace();
}
return null;
}
}
And this is my activity code:
public class NotesActivity extends Activity {
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
String resault = Webservice.readurl("http://localhost/note-server");
Log.i("Log", "Resault: " + resault);
When I run, it gives me "IOException" because of the "Log" in my class under the IOException, and at the end give me "Result: read"!!!!!
How can I fix that?
If you are running on an emulator then you should use 10.0.2.2 instead of localhost.
See this post.
I don't understand why can't I read this json link but Browser Chrome can read, I tried with different link and I read them.
this is the link for requesting json response:
My Code:
runOnUiThread(new Runnable() {
#Override
public void run() {
new sendToken().execute("http://admin:123#qlvb-snv.newsaigonsoft.com/push-notifications-portlet/api/secure/jsonws/pushnotificationsdevice/add-push-notifications-device?token=cNAXYNQSPHk:APA91bF86THzkPE_ol9euea1M40x6jVgN9RjUOISVtL-UEXDYpAP62aeRnUwkLrSt6z8C4saTJPKW5CJ57VSRmovZ5OBX4NsZg3U-zoDdXB64dWzAQGB7WllGvqGEO3Nt4_Fbg-vUyok&platform=android");
}
});
and My AsyncTask:
class sendToken extends AsyncTask<String, Integer, String> {
#Override
protected String doInBackground(String... params) {
return docNoiDung_Tu_URL(params[0]);
}
#Override
protected void onPostExecute(String s) {
Log.d("Respones: ", s + "");
}
}
and it does not respond with anything.
Two things may be the cause
either your method
docNoiDung_Tu_URL is not correct or correctly written
or, You have no permissions to access Internet.
change your doInBackground Like this
class sendToken extends AsyncTask<String, Integer, String> {
#Override
protected void onPreExecute() {
super.onPreExecute();
}
#Override
protected String doInBackground(String... params) {
try {
HttpClient httpclient = getNewHttpClient();
HttpGet httpget = new HttpGet(arg0[0]);
// Execute HTTP get Request
HttpResponse response = httpclient.execute(httpget);
HttpEntity entity = response.getEntity();
String responseString = EntityUtils.toString(entity, "UTF-8");
return responseString;
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(String s) {
Log.d("Respones: ", s);
}
Also add the dependencies to build.gradle
compile('org.apache.httpcomponents:httpcore:4.4.1') {
exclude group: 'org.apache.httpcomponents', module: 'httpclient'
}
don't forget to add the internet permission to manifest
<uses-permission android:name="android.permission.INTERNET"/>
you have to make http call
HttpURLConnection urlConnection = null;
String My_URL = "YOUR URL";
BufferedReader reader = null;
URL url = null;
String Json;
InputStreamReader inputStream1 = null;
InputStream inputStream = null;
inside do in background
#Override
protected String doInBackground(Void... params) {
try {
url = new URL(My_URL);
urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.setRequestMethod("GET");
urlConnection.connect();
if(urlConnection.getResponseCode() == 200)
{
inputStream = urlConnection.getInputStream();
Json = readData(inputStream);
}
else {
urlConnection.getResponseCode();
}
}catch (Exception e){
Json = e.toString();
}
finally {
if (urlConnection!=null)
urlConnection.disconnect();
try {
if (inputStream!=null)
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return Json;
}
#Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
// your work
}
public String readData(InputStream inputStream)
{
StringBuilder builder = new StringBuilder();
try {
if (inputStream != null) {
inputStream1 = new InputStreamReader(inputStream);
reader = new BufferedReader(inputStream1);
String line = reader.readLine();
while (line != null) {
builder.append(line);
line = reader.readLine();
}
} else {
Toast.makeText(MainActivity.this, "errorwa", Toast.LENGTH_SHORT).show();
}
}catch (Exception e){}
return builder.toString();
}
You can not directly read the response from the url.
Try out below code:
public JSONObject getJSONFromUrl(String url) {
static InputStream is = null;
static JSONObject jObj = null;
static String json = "";
// Making HTTP request
try {
// defaultHttpClient
DefaultHttpClient httpClient = new DefaultHttpClient();
HttpPost httpPost = new HttpPost(url);
HttpResponse httpResponse = httpClient.execute(httpPost);
HttpEntity httpEntity = httpResponse.getEntity();
is = httpEntity.getContent();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
try {
BufferedReader reader = new BufferedReader(new InputStreamReader(
is, "iso-8859-1"), 8);
StringBuilder sb = new StringBuilder();
String line = null;
while ((line = reader.readLine()) != null) {
sb.append(line + "n");
}
is.close();
json = sb.toString();
} catch (Exception e) {
Log.e("Buffer Error", "Error converting result " + e.toString());
}
// try parse the string to a JSON object
try {
jObj = new JSONObject(json);
} catch (JSONException e) {
Log.e("JSON Parser", "Error parsing data " + e.toString());
}
// return JSON String
return jObj;
}
Add the below permission in manifest
<uses-permission android:name="android.permission.INTERNET"/>
I am coding my first Android application and I just started to work with JSON. I need to transfer username and password using JSON to the router and get response from the router. But, I cannot figure out how to make JSON call to the router. My JSON string is made of a JSON object, an Array and an object again and I don't know how to make a JSON call to the router to transfer this complex JSON. I am using Jackson.2.2.2 library. So, my question is, how to make a JSON call to the router to transfer this complex JSON string.
Below is my JSON string:
{ "jsonrpc": "2.0", "id": 1, "method": "call", "params": [ "00000000000000000000000000000000", "session", "login", { "username": "uname", "password": "upassword" } ] } http://192.168.1.1/ubus
I need to transfer Username and Password.
Adding some of my code below:
RESTRequest.java
public class RESTRequest {
private static final String TAG = JacksonUtil.class.getSimpleName();
static String response = null;
public final static int GET = 1;
public final static int POST = 2;
//Constructor with no parameter
public RESTRequest(){
}
/**
* Making web service call
*/
public String makeWebServiceCall(String url, int requestmethod){
return this.makeWebServiceCall(url, requestmethod, null);
}
/**
* Making service call
*/
public String makeWebServiceCall(String urladdress, int requestmethod, HashMap<String, String> params){
URL url;
String responce = "";
try {
url = new URL(urladdress);
HttpURLConnection urlconn = (HttpURLConnection) url.openConnection();
urlconn.setReadTimeout(15000);
urlconn.setConnectTimeout(15000);
urlconn.setDoInput(true);
urlconn.setDoOutput(true);
if(requestmethod == POST){
urlconn.setRequestMethod("POST");
}else if(requestmethod == GET){
urlconn.setRequestMethod("GET");
}
if(params != null){
OutputStream outputstream = urlconn.getOutputStream();
BufferedWriter bufferedWriter = new BufferedWriter(
new OutputStreamWriter(outputstream, "UTF-8"));
StringBuilder result = new StringBuilder();
boolean first = true;
for(Map.Entry<String, String> entry : params.entrySet()){
if (first)
first = false;
else
result.append("&");
result.append(URLEncoder.encode(entry.getKey(), "UTF-8"));
result.append("=");
result.append(URLEncoder.encode(entry.getValue(), "UTF-8"));
}
bufferedWriter.write(result.toString());
bufferedWriter.flush();
bufferedWriter.close();
outputstream.close();
}
int responceCode = urlconn.getResponseCode();
if(responceCode == HttpsURLConnection.HTTP_OK){
String line;
BufferedReader br = new BufferedReader(new InputStreamReader(urlconn.getInputStream()));
while ((line = br.readLine()) != null){
responce += line;
}
}else {
responce = "";
}
} catch (Exception e){
Log.e(TAG, "IOException parsing to json", e);
}
return response;
}
JacksonUtil
public class JacksonUtil {
private static final String TAG = JacksonUtil.class.getSimpleName();
private static ObjectMapper mapper;
private static TypeFactory factory;
private JacksonUtil() {
}
private static ObjectMapper getMapper() {
if (mapper == null) {
mapper = new ObjectMapper();
mapper.configure(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS, false);
factory = mapper.getTypeFactory();
mapper.registerModule(new JodaModule());
mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
mapper.setSerializationInclusion(JsonInclude.Include.NON_EMPTY);
}
return mapper;
}
public static <T> String fromObject(T object) {
try {
return getMapper().writeValueAsString(object);
} catch (IOException e) {
Log.e(TAG, "IOException parsing to json", e);
} /*catch (Exception e) {
Log.e(App.class.getSimpleName(), "Exception", e);
Log.e("JacksonUtil", "FromObject");
}*/
return null;
}
public static <T> T toObject(InputStream is, Class<T> o) {
try {
return getMapper().readValue(is, o);
} catch (IOException e) {
Log.e(TAG, "IOException parsing from json", e);
} catch (Exception e) {
Log.e(TAG, "Exception parsing from json", e);
}
return null;
}
public static <T> T toObject(String json, Class<T> o) {
if (json == null) {
return null;
}
try {
return getMapper().readValue(json, o);
} catch (IOException e) {
Log.e(TAG, "IOException parsing from json", e);
} catch (Exception e) {
Log.e(TAG, "Exception parsing from json", e);
}
return null;
}
public static <T> T toObject(String json, TypeReference<T> type) {
try {
return getMapper().readValue(json, type);
} catch (IOException e) {
Log.e(TAG, "IOException parsing from json", e);
} catch (Exception e) {
Log.e(TAG, "Exception parsing from json", e);
}
return null;
}
public static <T> T toCollection(String json, Class<? extends Collection> list, Class types) {
try {
return getMapper().readValue(json, factory.constructCollectionType(list, types));
} catch (IOException e) {
Log.e(TAG, "IOException parsing from json", e);
} catch (Exception e) {
Log.e(TAG, "Exception parsing from json", e);
}
return null;
}
public static <T> T toCollection(InputStream is, Class<? extends Collection> list, Class types) throws Exception {
return getMapper().readValue(is, factory.constructCollectionType(list, types));
}