Using Gson For Json Post in Android - java

Following a tutorial which I didn't fully understand I did the following:
I created four classes.
package com.example.android.wearable.watchface;
import com.google.gson.annotations.SerializedName;
import java.util.ArrayList;
public class Beansubject {
#SerializedName("subject")
private static String subject;
#SerializedName("price")
private static String price;
#SerializedName("author")
private static String author;
#SerializedName("topics")
private static ArrayList<BeanTopic> beanTopics;
public Beansubject(ArrayList<BeanTopic> beanTopics, String subject, String price, String author) {
this.beanTopics = beanTopics;
this.subject = subject;
this.price = price;
this.author = author;
}
public static String getSubject() {
return subject;
}
public static void setSubject(String subj) {
subject = subj;
}
public static String getPrice() {
return price;
}
public static void setPrice(String pric) {
price = pric;
}
public String getAuthor() {
return author;
}
public static void setAuthor(String aue) {
author = aue;
}
public static ArrayList<BeanTopic> getBeanTopics() {
return beanTopics;
}
public static void setBeanTopics(ArrayList<BeanTopic> beantcs) {
beanTopics = beantcs;
}
}
Next
package com.example.android.wearable.watchface;
import com.google.gson.annotations.SerializedName;
public class BeanTopic {
#SerializedName("title")
private String title;
public BeanTopic(String title) {
this.title = title;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
}
Next
package com.example.android.wearable.watchface;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.StatusLine;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
public class API {
private static Reader reader=null;
public static Reader getData(String SERVER_URL) {
try {
DefaultHttpClient httpClient = new DefaultHttpClient();
HttpPost httpPost = new HttpPost(SERVER_URL);
HttpResponse response = httpClient.execute(httpPost);
StatusLine statusLine = response.getStatusLine();
if (statusLine.getStatusCode() == 200) {
HttpEntity entity = response.getEntity();
InputStream content = entity.getContent();
reader = new InputStreamReader(content);
} else {
// Log.e("error:", "Server responded with status code: "+ statusLine.getStatusCode());
}
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IllegalStateException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return reader;
}
}
Finally
package com.example.android.wearable.watchface;
import android.app.Activity;
import android.app.ProgressDialog;
import android.os.AsyncTask;
import android.util.Log;
import android.widget.TextView;
import com.google.gson.GsonBuilder;
import java.io.Reader;
import java.util.ArrayList;
public class MainActivity extends Activity {
ProgressDialog progressDialog;
TextView txtSubject;
TextView txtAuthor;
TextView txtPrice;
TextView txtTopicsList;
Beansubject beanSubject;
StringBuffer topicList;
public void Json() {
new AsyncTask<Void,Void,Void>(){
#Override
protected void onPreExecute() {
super.onPreExecute();
ProgressDialog progressDialog = new ProgressDialog(MainActivity.this);
progressDialog.setCancelable(false);
progressDialog.setMessage("Loading...");
progressDialog.show();
}
#Override
protected Void doInBackground(Void... voids) {
Reader reader=API.getData("http://beta.json-generator.com/api/json/get/OkS85Le");
beanSubject = new GsonBuilder().create().fromJson(reader, Beansubject.class);
Log.e("Subject: ", beanSubject.getSubject() + "");
Log.e("Author: ", beanSubject.getAuthor() + "");
Log.e("Price: ", beanSubject.getPrice() + "");
ArrayList<BeanTopic> topicArrayList = beanSubject.getBeanTopics();
topicList = new StringBuffer();
for(BeanTopic topic: topicArrayList){
Log.e("topic title: ",topic.getTitle()+"");
topicList.append("* " + topic.getTitle()+"\n");
}
return null;
}
#Override
protected void onPostExecute(Void aVoid) {
super.onPostExecute(aVoid);
progressDialog.dismiss();
txtSubject.setText("Subject: " + beanSubject.getSubject());
txtPrice.setText("price: "+beanSubject.getPrice());
txtAuthor.setText("Author: "+beanSubject.getAuthor());
txtTopicsList.setText("Topics: "+"\n" + topicList);
}
}.execute();
}
}
The error is that I'm not sure how to create the objects that are in the tutorial in the last part for the activity class.
For the parts I did not understand in this last part of the tutorial where objects are being created which are possibly linked and possibly not to other classes I took random guesses for what they are.
I even made some stuff static in the other classes and removed "this." to get something to work. Please help me understand that last part of the tutorial so I could understand fully how to do this simple task. Thanks.
Here is the link to this simple tutorial:
http://www.nkdroid.com/2014/11/json-object-parsing-using-url-in-android.html
Okay, so these are my unknown variables: MyActivity.this, progressdialog, txtpostlist, postlist, beanpostarraylist. I am using a different tutorial now -> more basic. So I'm not sure why the tutorial is so vague with creating the MainActivity Class. What is missing? http://nkdroid.com/2014/11/json-parsing-using-gson-in-android.html

May help to look at the data being provided by API call.
paste result belo to http://json.parser.online.fr/
curl -v http://beta.json-generator.com/api/json/get/OkS85Le
{"topics": [{"title": "how to add fontawesome icons in android example"},
{"title": "how to parse json parsing using gson library"},
{"title": "how to store arraylist in sharedpreferences"}],
"auther": "nirav kalola",
"price": "free",
"subject": "Android Application Development Tutorial"}
So , the 3 "title" elements in the JSON wind up in UI because of the following :
beanSubject = new GsonBuilder().create().fromJson(reader, Beansubject.class);
ArrayList<BeanTopic> topicArrayList = beanSubject.getBeanTopics();
for(BeanTopic topic: topicArrayList){
topicList.append("* " + topic.getTitle()+"\n");
}
txtTopicsList.setText("Topics: "+"\n" + topicList);
code gets data
MVC model/collection objs created from JSON Array
UI list set from collection obj
see here for more on Adapters getting data from the collection Object holders.

You would need to create a layout that have some TextView components with the corresping ids. So create one xml file with some textviews with the proper ids. Then override the onCreate method, and call the JSON method:
#Override
public void onCreate(Bundle b) {
super.onCreate(b);
setContentView(R.id.my_layout);
txtSubject = (TextView) findViewById(R.id.txtSubject);
...
Json();
}
If something is unclear, I recommend you to read a basic android tutorial (the one from the official site is great).

Related

How to get the returned value of AsyncTask in android studio

Helloo, I know there is a lot of posts abnout this but ITS SO confusing i'v read alot of them but i can't manage to solve a simple probleme. All i want is to get a Class from my main activity.kt when i do
val QuizzList = Network().execute(); (in main activity.kt)
I want QuizzList to be my class, not a Async task blabla.
What do i need to do in here to make this task returns a QuizCollection (its a custom class)?
package com.example.myapplication;
import android.os.AsyncTask;
import android.os.Build;
import androidx.annotation.RequiresApi;
import com.google.gson.Gson;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
public class Network extends AsyncTask<String, Integer, Object> {
static InputStream is = null;
static JSONObject jObj = null;
static String json = "";
// constructor
public Network() {
}
#RequiresApi(api = Build.VERSION_CODES.KITKAT)
#Override
protected QuizCollection doInBackground(String... params) {
try {
// On doit utiliser cet adresse URL, le 127.0.0.1 ne marche pas a cause du serveur qui
// Roule deja sur l'adresse.
//Get the content from the server
URL url = new URL("http://10.0.2.2:8080/api/quizz");
HttpURLConnection con = (HttpURLConnection) url.openConnection();
con.setRequestProperty("Content-Type", "application/json");
con.setRequestMethod("GET");
BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream()));
String inputLine;
StringBuffer content = new StringBuffer();
while ((inputLine = in.readLine()) != null) {
content.append(inputLine);
}
Gson gson = new Gson();
JSONArray jsonArray = new JSONArray(content.toString());
System.out.println("Le content : "+content.toString());
QuizCollection quizz = new QuizCollection();
for (int i=0; i<jsonArray.length();i++){
System.out.println(jsonArray.get(0).toString());
Quiz quiz = gson.fromJson(jsonArray.getJSONObject(i).toString(), Quiz.class);
System.out.println("Titre "+quiz.Title);
quizz.addQuiz(quiz);
}
System.out.println("ca fonctionne?"+quizz.QuizArray.get(0).Title);
in.close();
return quizz;
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (JSONException e) {
e.printStackTrace();
}
return null;
}
protected void onPostExecute(Object page)
{
//onPostExecute
}
}
You should use callback
public interface OnTaskCompleted{
void onTaskCompleted(QuizCollection collection);
}
In your Activity:
//do whatever you want with collection which is the object returned from AsyncTask
Network(OnTaskCompleted { collection -> collection.toString() }).execute()
And your AsyncTask:
public class YourTask extends AsyncTask<Object,Object,QuizCollection >{
private OnTaskCompleted listener;
public YourTask(OnTaskCompleted listener){
this.listener=listener;
}
// required methods
protected QuizCollection doInBackground(String... params) {
return new QuizCollection();
}
protected void onPostExecute(QuizCollection collection){
// your stuff
listener.onTaskCompleted(collection);
}
}
I had to do this
protected void onPostExecute(QuizCollection result)
{
//onPostExecute
super.onPostExecute(result);
}
And do a .get() after calling execute

How to send song to API?

I have an assignment where I am supposed to send a youtube song in the format to a url. (Further Explanation):
{"title":"Roar", "artist":"Katy Perry", "rating":5, "youtubeID":"CevxZvSJLk8", "key":"rf3498phfwqvwlie457fghwlriq347fl"}
The song is supposed to show up in a database:
http://fury.cse.buffalo.edu/musicRatings/getAllSongs
This is what I have so far which I feel is completed, also no errors:
import java.io.IOException;
import org.apache.http.client.fluent.Request;
import org.apache.http.entity.ContentType;
import com.eclipsesource.json.JsonObject;
public class Lab10 {
public static void main(String[] args) {
}
public static String postRequest(String url, String params){
String response = "";
try{
response = Request.Post(url)
.bodyString(params, ContentType.DEFAULT_TEXT)
.execute().returnContent().asString();
}catch(IOException ex){
ex.printStackTrace();
}
return response;
}
public static String lab() {
JsonObject song = new JsonObject();
song.add("title", "Sweater Weather");
song.add("artist","TheNeighbourhood");
song.add("rating",4);
song.add("youtubeID","GCdwKhTtNNw");
song.add("key","v5eysvylja457gnu0p62szurzrqcf6n8");
String ans = song.toString();
return postRequest("http://fury.cse.buffalo.edu/musicRatings/addSong", ans);
}
}`
It still does not show in the database when searching with ctrl+F. Is the way I'm returning it wrong?

Why does Gson library show null value when debugging?

I am parsing the Json and display on list view using gson library. When I insert my input stream I am getting null values. Can you please tell where I am wrong I will give you steps
I downloaded 2.3 Gson library. Then I make getter and setter
------------------
package com.firstgroup.webservice;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Reader;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.StatusLine;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import com.firstgroup.dto.Holder;
import com.firstgroup.webservicecallback.WebserviceCallBack;
import com.google.gson.Gson;
import android.app.ProgressDialog;
import android.content.Context;
import android.os.AsyncTask;
public class RequestTask extends AsyncTask<String, String, String>{
private WebserviceCallBack callBack;
private ProgressDialog progressDialog;
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
progressDialog= new ProgressDialog((Context) callBack);
super.onPreExecute();
progressDialog.setTitle("Please Wait...");
progressDialog.setMessage("Webservice Call...");
progressDialog.setCancelable(true);
progressDialog.show();
}
#Override
protected String doInBackground(String... uri) {
HttpClient httpclient = new DefaultHttpClient();
HttpResponse response;
String responseString = null;
try {
response = httpclient.execute(new HttpGet(uri[0]));
StatusLine statusLine = response.getStatusLine();
if(statusLine.getStatusCode() == HttpStatus.SC_OK){
// I am getting correct result here ...
Reader reader = new InputStreamReader(response.getEntity().getContent());
Gson gson = new Gson();
Holder response1 = gson.fromJson(reader, Holder.class);
ByteArrayOutputStream out = new ByteArrayOutputStream();
response.getEntity().writeTo(out);
out.close();
responseString = out.toString();
} else{
//Closes the connection.
response.getEntity().getContent().close();
throw new IOException(statusLine.getReasonPhrase());
}
} catch (ClientProtocolException e) {
//TODO Handle problems..\
progressDialog.hide();
} catch (IOException e) {
//TODO Handle problems..
progressDialog.hide();
}
return responseString;
}
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
//Do anything with response..
if(callBack!=null){
callBack.getWebserviceResponse(result);
}
progressDialog.hide();
}
public void setObserver(WebserviceCallBack callback){
callBack=callback;
}
}
callback on main activity:
#Override
public void getWebserviceResponse(String response) {
// TODO Auto-generated method stub
Log.d("response", response);
//can I used this code ?
// I want to used gson in main activity?
Reader reader = new InputStreamReader(response.getEntity().getContent());
Gson gson = new Gson();
Holder response1 = gson.fromJson(reader, Holder.class);
}
}
Add a class:
public class Holder {
List<deparaturedaseboarddto> data;
}
And change your below code:
deparaturedaseboarddto response1 = gson.fromJson(reader, deparaturedaseboarddto.class);
to:
Holder response1 = gson.fromJson(reader, Holder.class);
Reason: Your json text value has a root object named as data and it has a list of deparaturedaseboarddto. You are trying to deserialize this json value to a deparaturedaseboarddto instance but it is an object which has a list of deparaturedaseboarddto.
Also (not relevant to your error);
1) Class names starts with capital letters, and field names are camel case at Java.
2) You don't have to use #SerializedName if the java class's field name
is same with the json value's field name.
3) Below mapping is probably prevent an error because there are no fields at json value named as Result. #SerializedName("Result") may be removed or replaced with #SerializedName("alertsId")
#SerializedName("Result")
int alertsId;
4) Also may want to replace below code:
ByteArrayOutputStream out = new ByteArrayOutputStream();
response.getEntity().writeTo(out);
out.close();
responseString = out.toString();
with:
responseString = gson.toJson(response1);
Edit for the second question at the comment:
If you want to use retrieve Holder instance from AsyncTask, make below edits.
Change this:
public class RequestTask extends AsyncTask<String, String, String>
with this:
public class RequestTask extends AsyncTask<String, String, Holder>
and:
protected String doInBackground(String... uri)
with this:
protected Holder doInBackground(String... uri)
and this:
protected void onPostExecute(String result)
with this:
protected void onPostExecute(Holder result)

android post and receive json Asyc

I am working on an android application that posts a JSON object to a server and gets one back in response. I am stuck in how to get the JSON that the server responds with back to the main thread. Below is the code that I have so far. Even after I run my background process, when I call getResponse it returns null.
import java.io.UnsupportedEncodingException;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.DefaultHttpClient;
import org.json.JSONObject;
import android.os.AsyncTask;
public class AsyncHttpPost extends AsyncTask<String, String, HttpResponse> {
private JSONObject mData = null;// post data
private HttpResponse response = null;
/**
* constructor
*/
public AsyncHttpPost(JSONObject json) {
mData = json;
}
public HttpResponse getResponse() {
return response;
}
/**
* background
*/
#Override
protected HttpResponse doInBackground(String... params) {
HttpClient client = new DefaultHttpClient();
HttpPost post = new HttpPost(params[0]);
try {
post.setEntity(new StringEntity(mData.toString()));
response = client.execute(post);
}catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
catch (Exception e) {
}
return response;
}
}
U need to get data first , have u create a an adapter for it ?
when u want to get something using json, for an example title
this is how it loooks like.. you would also need to write in your main activity(depending what java use to display) to display the data.
I help this will help you. C:
//Declare variables
String title;
// call out the variables
public (ClasName) (String title) {
this.title = title;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}

On Android simple-xml serial.read() throws StackOverflowError

I'm trying to learn to use xml in Java (Android platform, using Eclipse and simple-xml-2.5.2).
I keep getting a weird java.lang.StackOverflowError in the "serial.read" line in "Training.java".
Can you help fixing the problem? Is it an xml definition error?
I include the source below:
File beacons.java:
package com.marcos.training;
import java.util.List;
import org.simpleframework.xml.Element;
import org.simpleframework.xml.ElementList;
#Element
public class Beacons {
#ElementList(inline=true)
private List<Beacon> list;
#Element
private String id;
public String getId() {
return id;
}
public Integer getSize() {
return list.size();
}
public List<Beacon> getList() {
return list;
}
}
File Beacon.java:
package com.marcos.training;
import org.simpleframework.xml.Attribute;
import org.simpleframework.xml.Element;
import org.simpleframework.xml.Root;
#Root
public class Beacon {
#Attribute
protected String ssid;
#Element
protected String bssid;
public String getSsid() {
return ssid;
}
public String getBssid() {
return bssid;
}
}
File Training.java:
package com.marcos.training;
import org.simpleframework.xml.Serializer;
import org.simpleframework.xml.core.Persister;
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.widget.TextView;
import android.content.res.Resources.NotFoundException;
public class Training extends Activity {
private final static String TAG = Training.class.getCanonicalName();
TextView textStatus;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
textStatus = (TextView) findViewById(R.id.textStatus);
Serializer serial = new Persister();
try {
Beacons myBeacons;
try {
myBeacons = serial.read(Beacons.class, getResources().openRawResource(R.xml.beacons));
Log.i(TAG, "Number of Beacons: " + myBeacons.getSize());
} catch (NotFoundException e) {
Log.d(TAG, "Uncaught exception", e);
return;
} catch (Exception e) {
Log.d(TAG, "Uncaught exception", e);
return;
}
int len = myBeacons.getSize();
for (int i = 0; i < len; i++) {
Beacon b = myBeacons.getList().get(i);
textStatus.append("Beacon " + (i+1) + "\n");
textStatus.append(" SSID : " + b.getSsid() + "\n");
textStatus.append(" BSSID : " + b.getBssid() + "\n");
textStatus.append("\n");;
}
} catch (Exception e) {
Log.d(TAG, "Uncaught exception", e);
}
}
}
File beacons.xml:
<?xml version="1.0" encoding="utf-8"?>
<beacons id="1">
<beacon ssid="north">
<bssid>01:02:03:04:05:06</bssid>
</beacon>
<beacon ssid="east">
<bssid>02:03:04:05:06:07</bssid>
</beacon>
<beacon ssid="south">
<bssid>03:04:05:06:07:08</bssid>
</beacon>
<beacon ssid="west">
<bssid>04:05:06:07:08:09</bssid>
</beacon>
</beacons>
By putting your XML file into the XML directory of the resources, the Android build system is assuming you want that compiled down into a binary format and it obliges you. Therefore, when you access that input stream and then try to treat it as a textual XML representation it just doesn't work. You have 2 choices.
Move your XML file into the res\raw directory.
Leave it where it is and use the getResources().getXml(R.xml.beacons) API and create a pull parser for your particular XML.
See this link for more details.

Categories