Usar AsyncTask con pasar un valor

He estado trabajando en esto y he llegado a un punto en el que no sé qué hacer. Lo que bash hacer es usar una clase para descargar y analizar un archivo en una cadena y luego enviar esa cadena a otra clase para analizar las cosas de JSON. Todas las piezas funcionan bien por sí mismas y he probado todo por separado. Simplemente no sé cómo enviar el valor a los análisis Json para comenzar el análisis sintáctico.

Así que esta es mi clase filedownloader.

public class JsonFileDownloader extends AsyncTask { //used to access the website String username = "admin"; String password = "admin"; public String ret = ""; @Override protected String doInBackground(String... params) { Log.d("Params ", params[0].toString()); readFromFile(params[0]); return ret; } private String readFromFile(String myWebpage) { HttpURLConnection urlConnection = null; try { //Get the url connection URL url = new URL(myWebpage); Authenticator.setDefault(new Authenticator() { @Override protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication(username, password.toCharArray()); } }); urlConnection = (HttpURLConnection) url.openConnection(); InputStream inputStream = urlConnection.getInputStream(); if (inputStream != null) { ret = streamToString(inputStream); inputStream.close(); Log.d("Final String", ret); } } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } finally { if (urlConnection != null) { urlConnection.disconnect(); } return ret; } } public static String streamToString(InputStream is) throws IOException { StringBuilder sb = new StringBuilder(); BufferedReader rd = new BufferedReader(new InputStreamReader(is)); String line; while ((line = rd.readLine()) != null) { sb.append(line); } return sb.toString(); } public String getJsonData() { return ret; } 

}

Esto funciona bien lo he probado una y otra vez sin errores. El siguiente es el analizador Json que es así.

 public class JSONParser { JSONObject jsonResponse; String jsonData; //Consturctor public JSONParser() { //this.jsonData = jsonData; // this.OutputData = outPutData; } public void parsesData(String promo, ArrayList pictureHTTP, ArrayList pathHTTP, ArrayList labelText) throws IOException { //Build the Json String JsonFileDownloader jfd = new JsonFileDownloader(); // jsonData = String.valueOf(jfd.execute(promo)); jfd.execute(promo); //jfd.getResuts(jsonData); //jsonData = jfd.ret; Log.d("JsonData String = " , jsonData); //Try to parse the data try { Log.d("Jsondata " , jsonData); //Creaate a new JSONObject ith the name/value mapping from the JSON string jsonResponse = new JSONObject(jsonData); //Returns the value mapped by the name if it exists and is a JSONArry JSONArray jsonMainNode = jsonResponse.optJSONArray(""); //Proccess the JSON node int lenghtJsonArrar = jsonMainNode.length(); for (int i = 0; i<lenghtJsonArrar; i++) { //Get object for each json node JSONObject jsonChildNode = jsonMainNode.getJSONObject(i); //Get the node values //int song_id = Integer.parseInt(jsonChildNode.optString("song_id").toString()); String picture = jsonChildNode.optString("picture").toString(); String pathName = jsonChildNode.optString("path").toString(); String lableName = jsonChildNode.optString("label".toString()); //Debug Testing code pictureHTTP.add(picture); pathHTTP.add(pathName); labelText.add(lableName); } } catch (JSONException e) { e.printStackTrace(); } } 

Ahora sé dónde está ocurriendo el problema. Cuando bash asignar un valor a jsonData, nunca se asigna, por lo que es nulo y el sistema falla. He intentado algunas cosas después de jfd.exicute () pero simplemente no sé cómo obtener el valor de la salida de cadena final en jsonData. Gracias por cualquier ayuda con esto.

Muy bien, aquí hay un patrón bastante flexible para el uso general del uso de AsyncTask para descargar contenido web y obtener los resultados de nuevo en el hilo de la interfaz de usuario.

Paso 1 Defina una interfaz que actuará como un bus de mensajes entre AsyncTask y donde desee los datos.

 public interface AsyncResponse { void onResponse(T response); } 

Paso 2 Crea una extensión AsyncTask genérica que tomará cualquier URL y devolverá los resultados. Básicamente ya tenías esto, pero hice algunos retoques. Lo más importante, permite la configuración de la interfaz de callback AsyncResponse.

 public class WebDownloadTask extends AsyncTask { private AsyncResponse callback; // Optional parameters private String username; private String password; // Make a constuctor to store the parameters public WebDownloadTask(String username, String password) { this.username = username; this.password = password; } // Don't forget to call this public void setCallback(AsyncResponse callback) { this.callback = callback; } @Override protected String doInBackground(String... params) { String url = params[0]; return readFromFile(url); } @Override protected void onPostExecute(String s) { super.onPostExecute(s); if (callback != null) { callback.onResponse(s); } else { Log.w(WebDownloadTask.class.getSimpleName(), "The response was ignored"); } } /******* private helper methods *******/ private String streamToString(InputStream is) throws IOException { StringBuilder sb = new StringBuilder(); BufferedReader rd = new BufferedReader(new InputStreamReader(is)); String line; while ((line = rd.readLine()) != null) { sb.append(line); } return sb.toString(); } private String readFromFile(String myWebpage) { String response = null; HttpURLConnection urlConnection = null; try { //Get the url connection URL url = new URL(myWebpage); // Unnecessary for general AsyncTask usage /* Authenticator.setDefault(new Authenticator() { @Override protected PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication(username, password.toCharArray()); } }); */ urlConnection = (HttpURLConnection) url.openConnection(); InputStream inputStream = urlConnection.getInputStream(); if (inputStream != null) { response = streamToString(inputStream); inputStream.close(); Log.d("Final String", response); } } catch (IOException e) { e.printStackTrace(); } finally { if (urlConnection != null) { urlConnection.disconnect(); } } return response; } } 

Paso 3 Avance y use esa AsyncTask donde lo desee. Aquí hay un ejemplo. Tenga en cuenta que si no usa setCallback , no podrá obtener los datos que provienen de AsyncTask.

 public class MainActivity extends Activity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); WebDownloadTask task = new WebDownloadTask("username", "password"); task.setCallback(new AsyncResponse() { @Override public void onResponse(String response) { // Handle response here. Eg parse into a JSON object // Then put objects into some list, then place into an adapter... Toast.makeText(getApplicationContext(), response, Toast.LENGTH_SHORT).show(); } }); // Use any URL, this one returns a list of 10 users in JSON task.execute("http://jsonplaceholder.typicode.com/users"); } }