So I am trying to fetch JSON string from a website which looks like this
[{"name":"Painting"},{"name":"Painting or varnishing doors"},{"name":"Painting or varnishing frames"},{"name":"Varnishing floors"},{"name":"Picking old wallpaper"},{"name":"Painting the facade"},{"name":"professional athlete"}]
I just want to fetch the first JSONObject with the string "Painting".
Here's my MainActivity.java code
package mobiletest.pixelapp.com.mobiletest;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.widget.TextView;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import model.Cup;
public class MainActivity extends AppCompatActivity {
private TextView textView;
private String myString;
private String anotherString;
private String myVar;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
textView = (TextView)findViewById(R.id.textView);
Cup myCup = new Cup();
String newString = myCup.myMethod();
try {
JSONArray jsonArray = new JSONArray(newString);
JSONObject jsonObject = jsonArray.getJSONObject(0);
Log.v("Key",jsonObject.getString("name"));
textView.setText(jsonObject.getString("name"));
} catch (JSONException e) {
e.printStackTrace();
}
}
}
Here's my java class file cup.java
package model;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
/**
* Created by pruthvi on 12/2/2015.
*/
public class Cup {
public String myMethod()
{
String output = getUrlContents("http://xyz.co/tests/android-query.php");
return output;
}
private static String getUrlContents(String theUrl)
{
StringBuilder content = new StringBuilder();
// many of these calls can throw exceptions, so i've just
// wrapped them all in one try/catch statement.
try
{
// create a url object
URL url = new URL(theUrl);
// create a urlconnection object
URLConnection urlConnection = url.openConnection();
// wrap the urlconnection in a bufferedreader
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(urlConnection.getInputStream()));
String line;
// read from the urlconnection via the bufferedreader
while ((line = bufferedReader.readLine()) != null)
{
content.append(line + "\n");
}
bufferedReader.close();
}
catch(Exception e)
{
e.printStackTrace();
}
return content.toString();
}
}
Now the problem, when I run this code as java I am easily able to print painting from the JSONObject, but when I try to run it as an android view by setting the text for my TextView, I am getting some strange system.err
12-02 14:06:26.809 19250-19250/mobiletest.pixelapp.com.mobiletest D/libc: [NET] getaddrinfo hn 10, servname NULL, ai_family 0+
12-02 14:06:26.809 19250-19250/mobiletest.pixelapp.com.mobiletest W/System.err: at java.net.InetAddress.lookupHostByName(InetAddress.java:393)
12-02 14:06:26.809 19250-19250/mobiletest.pixelapp.com.mobiletest W/System.err: at java.net.InetAddress.getAllByNameImpl(InetAddress.java:244)
12-02 14:06:26.809 19250-19250/mobiletest.pixelapp.com.mobiletest W/System.err: at java.net.InetAddress.getAllByName(InetAddress.java:219)
I am new to java and android, and as of now I just want to get data from my remote server files and database.
Thanks in advance
look at this example it will give you an idea
AsyncTask<Void, Void, Void> asyncLoad = new AsyncTask<Void, Void, Void>()
{
#Override
protected Void doInBackground(Void... params)
{
URL url = new URL("http://www.omdbapi.com/?i=&t="
+ TITLE);
String URL2="http://www.omdbapi.com/?i=&t=saw";
Log.d("URL content", url.toString());
HttpURLConnection urlConnection = (HttpURLConnection) url
.openConnection();
Log.d("URL content", "register URL");
urlConnection.connect();
Log.d("URL connection", "establish connection");
return null;
}
#Override
protected void onPostExecute(Void result)
{
super.onPostExecute(result);
}
};
asyncLoad.execute();
Do like that in onCrate Method
try {
JSONArray jsonArray = new JSONArray(newString);
for (int i = 0; i < jsonArray.length(); i++) {
JSONObject jsonObject = jsonArray.getJSONObject(i);
String name = jsonObject.getString("name")
textView.setText(name));}
} catch (JSONException e) {
e.printStackTrace();
}
It will set name to textView.
Happy to Help and Happy Coding
You can't do network task in UI Thread.
So
String newString = myCup.myMethod();
not properly working.
Main Reason of those errors are related with thread context.
If you want to do network task with android, use async task or other network library (personally I recommend retrofit).
try
{
JSONArray jsonArray = new JSONArray(newString);
if(jarray.length()>0){
String name = jarray.getJSONObject(0).getString("name");
displayName(name); //new method
}catch(Exception e){
}
Define the method displayName(String) like this outside onCreate()
public void displayName(final String name){
runOnUiThread(new Runnable() {
#Override
public void run() {
textView.setText(jsonObject.getString("name"));
}
});
}
Related
This question already has answers here:
What arguments are passed into AsyncTask<arg1, arg2, arg3>?
(5 answers)
Closed 3 years ago.
I am working on an Android app in which I am making a weather app. The application opens api data from a JSON and displays this information. More specifically it takes the user input of a city or zip code and adds this info to the URL for the API and then executes the URL.
MainActivity.java
package com.shanehampcsci3660.weather;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
//import static com.shanehampcsci3660.weather.GetJsonData.*;
public class MainActivity extends AppCompatActivity
{
public static TextView tempTV, jsonTV;
public EditText cityORZipET;
private Button getWeather;
public String zip, cityOrZip;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tempTV = (TextView) findViewById(R.id.tempTV);
jsonTV = (TextView) findViewById(R.id.jsonFeedTV);
cityORZipET = (EditText) findViewById(R.id.cityORZipET);
getWeather = (Button) findViewById(R.id.getWeatherButton);
//cityOrZip = cityORZipET.getText().toString();
getWeather.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick(View view)
{
GetJsonData getJsonData = new GetJsonData();
//getJsonData.execute();
cityOrZip = cityORZipET.getText().toString();
getJsonData.execute("https://api.openweathermap.org/data/2.5/weather?q=" + cityOrZip +"&appid=x");
jsonTV.setText(cityOrZip);
/*if(cityOrZip.equals(""))
{
getJsonData.execute("https://api.openweathermap.org/data/2.5/weather?q=" + cityOrZip +"&appid=x");
}
else
{
zip = "30528";
getJsonData.execute("https://api.openweathermap.org/data/2.5/weather?q=" + zip + "&appid=x");
}*/
}
});
}
}
GetJsonData.java
package com.shanehampcsci3660.weather;
import android.os.AsyncTask;
import android.util.Log;
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 GetJsonData extends AsyncTask<Void, Void, Void>
{
public String data= "", line = "", name = "";
double temp, minTemp, maxTemp;
#Override
protected Void doInBackground(Void... voids)
{
try
{
URL url = new URL("https://api.openweathermap.org/data/2.5/weather?q=30528&appid=id");
HttpURLConnection httpURLConnection = (HttpURLConnection) url.openConnection();
InputStream inputStream = httpURLConnection.getInputStream();
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
while(line != null)
{
line = bufferedReader.readLine();
data = data + line;
}
JSONObject jsonObject = new JSONObject(data);
JSONObject main = jsonObject.getJSONObject("main");
name = jsonObject.getString("name");
temp = main.getDouble("temp");
minTemp = main.getDouble("min_temp");
maxTemp = main.getDouble("max_temp");
/*JSONObject jsonObject = new JSONObject(result);
JSONObject jsonData = new JSONObject(jsonObject.getString("main"));
String weatherInfo = jsonObject.getString("weather");
JSONArray jsonArray = new JSONArray(weatherInfo);
String description, icon, iconURI;
for(int i = 0; i < jsonArray.length(); i++)
{
JSONObject jsonData1 = jsonArray.getJSONObject(i);
description = jsonData1.getString("description");
MainActivityController.description.setText(description);
icon = jsonData1.getString("icon");
iconURI = "http://openweathermap.org/img/w/" + icon + ".png";
Picasso.get().load(iconURI).into(MainActivityController.conditionImageView);
}*/
}
catch(MalformedURLException e)
{
e.printStackTrace();
}
catch(IOException e)
{
e.printStackTrace();
}
catch (JSONException e)
{
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void aVoid)
{
super.onPostExecute(aVoid);
//MainActivity.jsonTV.setText(data);
MainActivity.tempTV.setText("City:\t" + name + "\tTemp:\t" + temp);
Log.d("Json Feed", name + "Temp: " + temp);
}
public static void execute(String s) {
}
}
My issue is that no matter where I put...
if(cityOrZip.equals(""))
{
getJsonData.execute("https://api.openweathermap.org/data/2.5/weather?q=" + cityOrZip +"&appid=id");
}
else
{
zip = "30528";
getJsonData.execute("https://api.openweathermap.org/data/2.5/weather?q=" + zip + "&appid=id");
}
...It will only show the data of the default Url opened in GetJsonData.java. My question is what am I doing wrong and what should I correct in order to make my app work with the user input like it should.
you are calling an GetJsonData.execute with the url that contains the client data, but it has no code in it. Looking at your current code the zip that the client inputs does not get stored into the worker class.
This is because you always use the same URL in GetJsonData class. According to question What arguments are passed into AsyncTask? your class declaration should look like:
public class GetJsonData extends AsyncTask<String, Void, YourPojo> {
#Override
protected YourPojo doInBackground(String... urls)
{
try
{
URL url = new URL(urls[0]);
...
} catch (Exception e) {
handle(e);
}
}
}
where YourPojo is a class you need to create to store all properties you need to read from JSON payload:
class YourPojo {
private String data;
private String line;
private String name;
private double temp;
private double minTemp
private double maxTemp;
// getters, setters
}
I want to get data from php remote website.I have a php file through which i want to import data in android application.
I am unable to get data...exception error occurred(only exception part is running).I am new with the android so Please help me to solve this problem.I shall be thankful to you.Impatiently waiting for help.Thanks in advance.Stay blessed....
Here is my code.
package com.example.androiddevelopers.my;
import android.os.AsyncTask;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.webkit.WebView;
import android.widget.Toast;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
public class MainActivity extends AppCompatActivity {
public class Downloadweb extends AsyncTask<String,Void,String> {
#Override
protected String doInBackground(String... params) {
String data = "";
URL url ;
HttpURLConnection urlConnection = null;
try{
String postdata = URLEncoder.encode("Player Name","UTF-8")+"=" + URLEncoder.encode(params[1],"UTF-8");
postdata += URLEncoder.encode("Player Role","UTF-8")+"=" + URLEncoder.encode(params[2],"UTF-8");
//url =new URL("http://localhost/ODI-Team/ODI.php");
url = new URL(params[0]);
urlConnection = (HttpURLConnection)url.openConnection();
urlConnection.setDoOutput(true);
OutputStreamWriter wr = new OutputStreamWriter(urlConnection.getOutputStream());
wr.write(postdata);
wr.flush();
InputStream in = urlConnection.getInputStream();
InputStreamReader reader = new InputStreamReader(in);
int ch = reader.read();
while(ch != -1){
char current=(char)ch;
data += current;
ch=reader.read();
}
return data;
}
catch (Exception e){
//Toast.makeText(MainActivity.this, "error occured"+e.getMessage(), Toast.LENGTH_SHORT).show();
return "Error ocured"+e.getMessage();
}
}
#Override
protected void onPostExecute(String s){
try{
webView.loadData(s,"text/html","UTF-8");
}
catch (Exception e){
Toast.makeText(MainActivity.this, ""+e.getMessage(), Toast.LENGTH_SHORT).show();
}
}
}
WebView webView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
webView=(WebView)findViewById(R.id.webView);
try{
Downloadweb downloadweb=new Downloadweb();
//replace with your own laptop ip address
downloadweb.execute(new String[]{"http://192.168.0.109/ODI.php"});
}
catch (Exception e){
//Toast.makeText(this, ""+e.getMessage(), Toast.LENGTH_SHORT).show();
webView.loadData("<html><body>Error Occured.</body></html>","text/html","UTF-8");
}
}
}
Man, protected String doInBackground(String... params) - this method perform operations on a background thread. String... params - it's a string array with parameters, which you'll passing to the this thread. .execute() - here you are executing asynctask with parameters passed to the background thread, but there is only one argument "http://192.168.0.109/ODI.php", but in your doInBackground() method you are trying to get "Player Name" and Player Role from argument, which doesn't exist. Here you have what I mean.
protected String doInBackground(String... params) { // <--- in yor case params contains only 1 element with index 0
...
String postdata = URLEncoder.encode("Player Name", "UTF-8") + "=" + URLEncoder.encode(params[1], "UTF-8"); // here's your second execute params, it's error
postdata += URLEncoder.encode("Player Role", "UTF-8") + "=" + URLEncoder.encode(params[2], "UTF-8"); // here's your third execute params, it's error
url = new URL(params[0]); // here's your first execute params
}
And in activty
Downloadweb downloadweb = new Downloadweb();
//replace with your own laptop ip address
downloadweb.execute(new String[] {
"http://192.168.0.109/ODI.php", // <--- its params[0]
"", // <--- here's your missing params[1]
"" // <--- here's your missing params[2]
});
That's all, why you are getting an error.
Here's you have some docs, how using asynctask with examples.
#Edit
I'm using BufferedReader for fetching string from remote server
BufferedReader rd = new BufferedReader(new InputStreamReader(is));
String line;
StringBuilder response = new StringBuilder();
while ((line = rd.readLine()) != null) {
response.append(line + '\n');
}
rd.close();
return response.toString();
I am an android newbie who is trying to populate spinner using JSON but I keep getting Null Pointer Exception -
java.lang.NullPointerException: Attempt to invoke interface method
java.lang.Object[] java.util.Collection.toArray()' on a null object
reference
I understand that this is a frequently asked question, and have looked through the other answers and solutions. I have tried initializing the List but still, am unable to fix the error.I think I am having trouble understanding where the initialization is exactly needed.
My Complete log:
07-19 09:34:54.356 11199-11337/com.genx.meghna.makdver4 D/Result is: [{"car_number":"DL 2345"},{"car_number":"DL 53546"},{"car_number":"1472"},{"car_number":"m7894"},{"car_number":"nxjvjsv"}]
07-19 09:34:54.356 11199-11337/com.genx.meghna.makdver4 D/res =: [{"car_number":"DL 2345"},{"car_number":"DL 53546"},{"car_number":"1472"},{"car_number":"m7894"},{"car_number":"nxjvjsv"}]
07-19 09:34:54.357 11199-11337/com.genx.meghna.makdver4 E/AndroidRuntime: FATAL EXCEPTION: AsyncTask #3
Process: com.genx.meghna.makdver4, PID: 11199
java.lang.RuntimeException: An error occured while executing doInBackground()
at android.os.AsyncTask$3.done(AsyncTask.java:300)
at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:355)
at java.util.concurrent.FutureTask.setException(FutureTask.java:222)
at java.util.concurrent.FutureTask.run(FutureTask.java:242)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
at java.lang.Thread.run(Thread.java:818)
Caused by: java.lang.NullPointerException: Attempt to invoke interface method 'java.lang.Object[] java.util.Collection.toArray()' on a null object reference
at java.util.ArrayList.addAll(ArrayList.java:188)
at com.genx.meghna.makdver4.Fragments.SendCarFragment$GetData.doInBackground(SendCarFragment.java:173)
at com.genx.meghna.makdver4.Fragments.SendCarFragment$GetData.doInBackground(SendCarFragment.java:117)
at android.os.AsyncTask$2.call(AsyncTask.java:288)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
at java.lang.Thread.run(Thread.java:818)
My code :
package com.genx.meghna.makdver4.Fragments;
import android.content.Context;
import android.content.SharedPreferences;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.RadioButton;
import android.widget.RadioGroup;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;
import com.genx.meghna.makdver4.R;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import static com.genx.meghna.makdver4.Fragments.LoginFragment.un;
public class SendCarFragment extends Fragment {
TextView tv1, tv2, tv3;
Spinner sp;
RadioGroup rg;
RadioButton rb1, rb2;
Button btn;
FragmentManager fm;
ArrayList<String> carList;
ArrayAdapter<String> adapter;
String res;
SharedPreferences spp;
public SendCarFragment() {
// Required empty public constructor
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View rootView = inflater.inflate(R.layout.fragment_send_car, container, false);
btn = rootView.findViewById(R.id.nextPage1);
rg = rootView.findViewById(R.id.radioGroup1);
rb1 = rootView.findViewById(R.id.rb1);
rb2 = rootView.findViewById(R.id.rb2);
sp = rootView.findViewById(R.id.spinnerSelectCar);
spp=getContext().getSharedPreferences("MyPrefs", Context.MODE_PRIVATE);
btn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
if (rg.getCheckedRadioButtonId() == -1) {
Toast.makeText(getContext(), "Select One Option", Toast.LENGTH_SHORT).show();
} else {
if (rb1.isChecked()) {
fm = getFragmentManager();
fm.beginTransaction().replace(R.id.container, new ServiceCenterListFragment(), "Service center").commit();
} else {
fm = getFragmentManager();
fm.beginTransaction().replace(R.id.container, new SelectionFragment(), "Select Address").commit();
}
}
}
});
return rootView;
}
public void onStart(){
super.onStart();
String username1 = spp.getString(un, "userKey");
GetData get = new GetData();
get.execute(username1);
}
class GetData extends AsyncTask<String, Void, String> {
List<String> list;
protected void onPreExecute(){
super.onPreExecute();
list=new ArrayList<>();
}
#Override
protected String doInBackground(String... params) {
{
try {
String username1 = params[0];
String link = "http://10.0.3.2//Traccar/getCars.php";
String myurl = "username=" + username1;
URL url = new URL(link);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.setRequestMethod("POST");
connection.getOutputStream().write(myurl.getBytes());
int response = connection.getResponseCode();
Log.d("Response code", "" + response);
if (response == HttpURLConnection.HTTP_OK) {
String line;
InputStreamReader isr = new InputStreamReader(connection.getInputStream());
BufferedReader br = new BufferedReader(isr);
StringBuilder buffer = new StringBuilder();
while ((line = br.readLine()) != null) {
buffer.append(line);
//res+=line;
}
Log.d("Result is", buffer.toString());
res = buffer.toString();
Log.d("res = ", res);
}
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
try{
JSONArray jrr = new JSONArray(res);
for (int i=0; i<jrr.length(); i++) {
JSONObject obj = jrr.getJSONObject(i);
String name = obj.getString("car_number");
list.add(name);
}
} catch (JSONException e1) {
e1.printStackTrace();
}
return res;
}
protected void onPostExecute(String res) {
list.addAll(carList);
adapter = new ArrayAdapter<>(getContext(),android.R.layout.simple_list_item_1, carList);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
sp.setAdapter(adapter);
}
}
}
One Alternative method I tried was placing my JSON parse code in the onPostExecute() function but I kept having trouble trying to pass my array from doInBackground() to onPostExecute() which led to my onPostExecute() never being used.
Any help would be much appreciated. Thank you!
You have a carList and a list. You don't initialize or add items to carList but try to pass it to list.addAll(carList); which naturally cannot work.
Since the data is already in list you should be able to do this
class GetData extends AsyncTask<String, Void, List<String>> {
List<String> list;
protected void onPreExecute(){
super.onPreExecute();
list=new ArrayList<>();
}
#Override
protected String doInBackground(String... params) {
{
try {
String username1 = params[0];
String link = "http://10.0.3.2//Traccar/getCars.php";
String myurl = "username=" + username1;
URL url = new URL(link);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.setRequestMethod("POST");
connection.getOutputStream().write(myurl.getBytes());
int response = connection.getResponseCode();
Log.d("Response code", "" + response);
if (response == HttpURLConnection.HTTP_OK) {
String line;
InputStreamReader isr = new InputStreamReader(connection.getInputStream());
BufferedReader br = new BufferedReader(isr);
StringBuilder buffer = new StringBuilder();
while ((line = br.readLine()) != null) {
buffer.append(line);
//res+=line;
}
Log.d("Result is", buffer.toString());
res = buffer.toString();
Log.d("res = ", res);
}
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
try{
JSONArray jrr = new JSONArray(res);
for (int i=0; i<jrr.length(); i++) {
JSONObject obj = jrr.getJSONObject(i);
String name = obj.getString("car_number");
list.add(name);
}
} catch (JSONException e1) {
e1.printStackTrace();
}
return list;
}
protected void onPostExecute(List<String> res) {
adapter = new ArrayAdapter<>(getContext(),android.R.layout.simple_list_item_1, res);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
sp.setAdapter(adapter);
}
}
Note that I changed AsyncTask to AsyncTask<String, Void, List<String>> and carList is not needed.
I am currently populating a RrecyclerView from a remote database but wish to only query the database for dates based on a users ID. I have the userID assigned as a global variable on the LoginActivty of the app but I'm not sure where to pass that information to the php page from my DateActivity.
My Code for the DateActivity is as follows:
import android.app.ProgressDialog;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.widget.Toast;
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;
import java.util.ArrayList;
import java.util.List;
public class DateActivity extends AppCompatActivity {
public static String globex_num;
// CONNECTION_TIMEOUT and READ_TIMEOUT are in milliseconds
public static final int CONNECTION_TIMEOUT = 10000;
public static final int READ_TIMEOUT = 15000;
private RecyclerView mRVDateList;
private AdapterDate mAdapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_date);
//Make call to AsyncTask
new AsyncFetch().execute();
}
private class AsyncFetch extends AsyncTask<String, String, String> {
ProgressDialog pdLoading = new ProgressDialog(DateActivity.this);
HttpURLConnection conn;
URL url = null;
#Override
protected void onPreExecute() {
super.onPreExecute();
//this method will be running on UI thread
pdLoading.setMessage("\tLoading...");
pdLoading.setCancelable(false);
pdLoading.show();
}
#Override
protected String doInBackground(String... params) {
try {
url = new URL("thephpfile.com");
} catch (MalformedURLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
return e.toString();
}
try {
// Setup HttpURLConnection class to send and receive data from php and mysql
conn = (HttpURLConnection) url.openConnection();
conn.setReadTimeout(READ_TIMEOUT);
conn.setConnectTimeout(CONNECTION_TIMEOUT);
conn.setRequestMethod("GET");
// setDoOutput to true as we recieve data from json file
conn.setDoOutput(true);
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
return e1.toString();
}
try {
int response_code = conn.getResponseCode();
// Check if successful connection made
if (response_code == HttpURLConnection.HTTP_OK) {
// Read data sent from server
InputStream input = conn.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(input));
StringBuilder result = new StringBuilder();
String line;
while ((line = reader.readLine()) != null) {
result.append(line);
}
// Pass data to onPostExecute method
return (result.toString());
} else {
return ("unsuccessful");
}
} catch (IOException e) {
e.printStackTrace();
return e.toString();
} finally {
conn.disconnect();
}
}
#Override
protected void onPostExecute(String result) {
//this method will be running on UI thread
pdLoading.dismiss();
List<DataDate> data=new ArrayList<>();
pdLoading.dismiss();
try {
JSONArray jsonArray = new JSONArray(result);
// Extract data from json and store into ArrayList as class objects
for(int i=0;i<jsonArray.length();i++){
JSONObject json_data = jsonArray.getJSONObject(i);
DataDate dateData = new DataDate();
dateData.date= json_data.getString("date");
data.add(dateData);
}
// Setup and Handover data to recyclerview
mRVDateList = (RecyclerView)findViewById(R.id.dateList);
mAdapter = new AdapterDate(DateActivity.this, data);
mRVDateList.setAdapter(mAdapter);
mRVDateList.setLayoutManager(new LinearLayoutManager(DateActivity.this));
} catch (JSONException e) {
Toast.makeText(DateActivity.this, e.toString(), Toast.LENGTH_LONG).show();
}
}
}
}
I solved the problem by passing it though the link.
url = new URL(www.thephpfile.php?userID=" + LoginActivity.userID);
At the start of the php file I did the following:
$userID = $_GET['userID'];
The list is working fine but the problem is i can't download the file from the web server file system. When i tried clicking one of the list item, the dialog will show up but after a few seconds the app will crash. I am using GenyMotion emulator
The filename is correct and also the url, i guess it's in the saving part
Memo.java
package com.example.androidtablayout;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import org.apache.http.NameValuePair;
import org.apache.http.message.BasicNameValuePair;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import android.app.ListActivity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Environment;
import android.util.Log;
import android.view.View;
import android.view.Window;
import android.view.WindowManager;
import android.widget.AdapterView;
import android.widget.Button;
import android.widget.ListAdapter;
import android.widget.ListView;
import android.widget.SimpleAdapter;
import android.widget.TextView;
public class Memo extends ListActivity {
// Declare Variables
JSONObject jsonobject;
JSONArray jsonarray;
ListView listview;
ArrayList<HashMap<String, String>> arraylist;
ProgressDialog mProgressDialog, dialog;
JSONParser jsonParser = new JSONParser();
String email;
SessionManager session;
String[] services;
private String url = "http://10.0.3.2/sunshine-ems/memo.php";
// single product url
// ALL JSON node names
private static final String MEMO_ID = "memo_id";
private static final String MEMO_SENDER = "sender";
private static final String MEMO_FILENAME = "file_name";
Button btnLogout;
String username;
String download_path = "";
String dest_file_path = "";
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
setContentView(R.layout.announc);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
session = new SessionManager(getApplicationContext());
username = session.getUsername();
btnLogout = (Button) findViewById(R.id.btnLogout);
btnLogout.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
// Launching All products Activity
session.logoutUser();
Intent i = new Intent(getApplicationContext(), Login.class);
startActivity(i);
}
});
new DownloadJSON().execute();
ListView lv = getListView();
lv.setOnItemClickListener(new android.widget.AdapterView.OnItemClickListener() {
public void onItemClick(AdapterView<?> arg0, View view, int arg2, long arg3) {
String memo_filename = ((TextView) view.findViewById(R.id.txt_service)).getText().toString();
download_path = "http://www.sunshine-ems.balay-indang.com/attachments/memo/"+memo_filename+".docx";
String sd_path = Environment.getExternalStorageDirectory().getPath();
dest_file_path = sd_path+"/"+memo_filename+".docx";
dialog = ProgressDialog.show(Memo.this, "", "Downloading file...", true);
new Thread(new Runnable() {
public void run() {
//Log.d("Download Path", dest_file_path+" "+download_path);
downloadFile(download_path, dest_file_path);
}
}).start();
}
});
}
//download
public void downloadFile(String download_path, String dest_file_path) {
try {
File dest_file = new File(dest_file_path);
URL u = new URL(download_path);
URLConnection conn = u.openConnection();
int contentLength = conn.getContentLength();
DataInputStream stream = new DataInputStream(u.openStream());
byte[] buffer = new byte[contentLength];
stream.readFully(buffer);
stream.close();
DataOutputStream fos = new DataOutputStream(new FileOutputStream(dest_file));
fos.write(buffer);
fos.flush();
fos.close();
hideProgressIndicator();
} catch(FileNotFoundException e) {
hideProgressIndicator();
return;
} catch (IOException e) {
hideProgressIndicator();
return;
}
}
void hideProgressIndicator(){
runOnUiThread(new Runnable() {
public void run() {
dialog.dismiss();
}
});
}
// DownloadJSON AsyncTask
private class DownloadJSON extends AsyncTask<String, String, String> {
#Override
protected void onPreExecute() {
super.onPreExecute();
mProgressDialog = new ProgressDialog(Memo.this);
mProgressDialog.setTitle("Loading Services");
mProgressDialog.setMessage("Loading...");
mProgressDialog.setIndeterminate(false);
mProgressDialog.show();
}
#Override
protected String doInBackground(String... params) {
username = session.getUsername();
List<NameValuePair> params1 = new ArrayList<NameValuePair>();
params1.add(new BasicNameValuePair("username", username));
JSONObject json = jsonParser.makeHttpRequest(url, "POST", params1);
// Check your log cat for JSON reponse
Log.d("Check JSON ", json.toString());
// Create the array
arraylist = new ArrayList<HashMap<String, String>>();
try {
int success = json.getInt("success");
if (success == 1) {
// Locate the array name
jsonarray = json.getJSONArray("memos");
for (int i = 0; i < jsonarray.length(); i++) {
json = jsonarray.getJSONObject(i);
String m_id = json.optString(MEMO_ID);
String m_subject = json.getString(MEMO_FILENAME);
String m_sender = json.getString(MEMO_SENDER);
// Retrive JSON Objects
HashMap<String, String> map = new HashMap<String, String>();
map.put(MEMO_ID, m_id);
map.put(MEMO_FILENAME, m_subject);
map.put(MEMO_SENDER, m_sender);
// Set the JSON Objects into the array
arraylist.add(map);
}
}
} catch (JSONException e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(String file_url) {
mProgressDialog.dismiss();
// updating UI from Background Thread
runOnUiThread(new Runnable() {
public void run() {
/**
* Updating parsed JSON data into ListView
* */
ListAdapter adapter = new SimpleAdapter(
Memo.this,
arraylist,
R.layout.listview_services,
new String[] { MEMO_ID, MEMO_FILENAME, MEMO_SENDER },
new int[] { R.id.transac_id, R.id.txt_service,
R.id.txt_date });
// updating listview
setListAdapter(adapter);
}
});
}
}
}
I think the downloading was fine, maybe the problem is in the saving/writing part. Maybe the destination path or something close to that
And also where can i see the downloaded file after the download?
I'm using GenyMotion emulator
I'm sorry for the noob questions
Thank you so much
The problem seems to be this line (because it is the only array):
byte[] buffer = new byte[contentLength];
Looking at the declaration of contentLenght it seems conn.getContentLength() is returning a negative number.
Returns the content length in bytes specified by the response header field
content-length or -1 if this field is not set or cannot be represented as an int.
I copied your code and checked with a debugger: contentLenght is always -1.
I just rewrote your downloadFile function to use HttpURLConnection instead of URLConnection. Additionally, it uses a small buffer multiple times instead of creating one large buffer.
//download
public void downloadFile(String download_path, String dest_file_path) {
try {
URL u = new URL(download_path);
HttpURLConnection conn = (HttpURLConnection) u.openConnection();
InputStream stream = conn.getInputStream();
File f = new File(dest_file_path);
FileOutputStream fos = new FileOutputStream(f);
int bytesRead = 0;
byte[] buffer = new byte[4096];
while ((bytesRead = stream.read(buffer)) != -1) {
fos.write(buffer, 0, bytesRead);
}
fos.close();
stream.close();
hideProgressIndicator();
} catch(FileNotFoundException e) {
hideProgressIndicator();
return;
} catch (IOException e) {
hideProgressIndicator();
return;
}
}
You can view the file afterwards by using ADB. Android device monitor contains a file explorer and is located at "path-to\AndroidSDK\tools\monitor.bat" (using Windows)