0

I'm trying to download a file from inside of my android app. When the code reaches the line

connection.connect();

Logcat shows this exception:

  09-23 21:41:21.853: W/System.err(6084): android.os.NetworkOnMainThreadException
09-23 21:41:21.863: W/System.err(6084):     at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1133)
09-23 21:41:21.863: W/System.err(6084):     at libcore.io.BlockGuardOs.connect(BlockGuardOs.java:84)
09-23 21:41:21.863: W/System.err(6084):     at libcore.io.IoBridge.connectErrno(IoBridge.java:127)
09-23 21:41:21.863: W/System.err(6084):     at libcore.io.IoBridge.connect(IoBridge.java:112)
09-23 21:41:21.863: W/System.err(6084):     at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:192)
09-23 21:41:21.863: W/System.err(6084):     at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:459)
09-23 21:41:21.863: W/System.err(6084):     at java.net.Socket.connect(Socket.java:842)
09-23 21:41:21.863: W/System.err(6084):     at libcore.net.http.HttpConnection.<init>(HttpConnection.java:76)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpConnection.<init>(HttpConnection.java:50)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpConnection$Address.connect(HttpConnection.java:340)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpConnectionPool.get(HttpConnectionPool.java:87)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpConnection.connect(HttpConnection.java:128)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpEngine.openSocketConnection(HttpEngine.java:316)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpEngine.connect(HttpEngine.java:311)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpEngine.sendSocketRequest(HttpEngine.java:290)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpEngine.sendRequest(HttpEngine.java:240)
09-23 21:41:21.873: W/System.err(6084):     at libcore.net.http.HttpURLConnectionImpl.connect(HttpURLConnectionImpl.java:81)
09-23 21:41:21.873: W/System.err(6084):     at com.asde.ipac.AsyncUpdater$1.onClick(AsyncUpdater.java:107)
09-23 21:41:21.883: W/System.err(6084):     at com.android.internal.app.AlertController$ButtonHandler.handleMessage(AlertController.java:166)
09-23 21:41:21.883: W/System.err(6084):     at android.os.Handler.dispatchMessage(Handler.java:99)
09-23 21:41:21.883: W/System.err(6084):     at android.os.Looper.loop(Looper.java:137)
09-23 21:41:21.883: W/System.err(6084):     at android.app.ActivityThread.main(ActivityThread.java:5103)
09-23 21:41:21.883: W/System.err(6084):     at java.lang.reflect.Method.invokeNative(Native Method)
09-23 21:41:21.883: W/System.err(6084):     at java.lang.reflect.Method.invoke(Method.java:525)
09-23 21:41:21.893: W/System.err(6084):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:737)
09-23 21:41:21.893: W/System.err(6084):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
09-23 21:41:21.893: W/System.err(6084):     at dalvik.system.NativeStart.main(Native Method)

This line of logcat is connection.connect();

09-23 21:41:21.873: W/System.err(6084):     at com.asde.ipac.AsyncUpdater$1.onClick(AsyncUpdater.java:107)

This is the url of the file:

private String urlDownload = "http://192.168.0.107/ipac/ipac.apk/";

And this is the code of the method:

protected void onPostExecute(String lastVer) {

        PackageInfo packageInfo;
        try {
            packageInfo = ((Activity) ctx).getPackageManager().getPackageInfo(ctx.getPackageName(), 0);
            String currentVer = packageInfo.versionName;

            System.out.println("Server: "+ lastVer);
            System.out.println("Installed: "+ currentVer);
            if(!lastVer.equals(currentVer))
            {
                new AlertDialog.Builder(ctx)
                .setTitle("UPDATE AVAILABLE")
                .setMessage("New Test available")
                .setCancelable(false)
                .setPositiveButton("DOWNLOAD", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int id) {

                         try {
                             System.out.println("0!!!!");
                                URL url = new URL(urlDownload);
                                System.out.println("0.2!!!!");
                                URLConnection connection = url.openConnection();
                                System.out.println("0.3!!!!" + url.toString());
                                connection.connect();
                                System.out.println("1!!!!");
//                              int fileLength = connection.getContentLength();

                                // download the file
                                InputStream input = new BufferedInputStream(url.openStream());
                                OutputStream output = new FileOutputStream(path);
                                System.out.println("2!!!!");
                                byte data[] = new byte[1024];
//                              long total = 0;
                                int count;
                                while ((count = input.read(data)) != -1) {
//                                  total += count;
//                                  publishProgress((int) (total * 100 / fileLength));
                                    output.write(data, 0, count);
                                }
                                System.out.println("3!!!!");
                                output.flush();
                                output.close();
                                input.close();


                                //INSTALL
                            } catch (Exception e) {


                                 e.printStackTrace();
                            }



                    }
                })
                .setNegativeButton("LATER", null)
                .show();    

            }
        } catch (NameNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }



    }

What can be happening?

Hanzo
  • 1,839
  • 4
  • 30
  • 51
  • why do you do n/w operation in `onPostexecute` which is invoked on the ui thread? – Raghunandan Sep 26 '13 at 10:09
  • you do your Network things in the onPostExecute, thats the worng way, please do all network stuff in the doInBackground or own Thread not in the UI thread. http://stackoverflow.com/questions/6343166/android-os-networkonmainthreadexception And please provide us this Line of code com.asde.ipac.AsyncUpdater$1.onClick(AsyncUpdater.java:132) – A.S. Sep 26 '13 at 10:10
  • @Raghunandan : that's not in `onPostExecute`, that's in `onClick` (the point still stands, though) – njzk2 Sep 26 '13 at 10:17
  • @njzk2 button click is inside `onPostExecute` so i din't mention in detail – Raghunandan Sep 26 '13 at 10:18
  • yes, but no. the execution of the onClick occurs after the onPostExecute finishes, and the fact that it is executed on the ui thread is only related to the nature of the onClick, not to the fact that it is declared in onPostExecute. – njzk2 Sep 26 '13 at 10:20
  • @njzk2 yes it is executed on click of the button and i am not denying that just that i din't mention everything in detail – Raghunandan Sep 26 '13 at 10:22
  • my point is that the n/w operation does occur on the ui thread, but not in the onPostExecute – njzk2 Sep 26 '13 at 10:22
  • Hi I edit the original code of my question. The line 132 of the original logcat shows was a little error, The new Logcat shows different error. The AsyncTask checks if the installed version of my app is older than the version of the server. If the installed version is older shows a alert prompt to update, onclick "DOWNLOAD" then starts the problem – Hanzo Sep 26 '13 at 10:31

1 Answers1

0

You have to use AsyncTasks or threads on the Main thread, or Android will crash like your crash.

Put that outside onCreate (global variable):

ProgressDialog mProgressDialog;

Then put that inside of your activity (outside oncreate):

    mProgressDialog = new ProgressDialog(About.this);
        mProgressDialog.setMessage("Downloading file....");
        mProgressDialog.setIndeterminate(false);
        mProgressDialog.setMax(100);
        mProgressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);


Then make that class:
private class DownloadFile extends AsyncTask<String, Integer, String> {
        @Override
        protected String doInBackground(String... sUrl) {

            File folders = new File(Environment.getExternalStorageDirectory()
                    + "/pathofthefile/");
            folders.mkdirs();

            File file;
            file = new File(Environment.getExternalStorageDirectory()
                    + "/pathofthefile/nameofthefile.extensionofthefile");


            if (!file.exists()) {
                try {
                    file.createNewFile();
                } catch (IOException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            } else {
                file.delete();
                try {
                    file.createNewFile();
                } catch (IOException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }

            try {
                URL url = new URL(sUrl[0]);
                URLConnection connection = url.openConnection();
                connection.connect();
                // this will be useful so that you can show a typical 0-100%
                // progress bar
                int fileLength = connection.getContentLength();

                // download the file
                InputStream input = new BufferedInputStream(url.openStream());
                OutputStream output = new FileOutputStream(file);

                byte data[] = new byte[1024];
                long total = 0;
                int count;
                while ((count = input.read(data)) != -1) {
                    total += count;
                    // publishing the progress....
                    publishProgress((int) (total * 100 / fileLength));
                    output.write(data, 0, count);
                }

                output.flush();
                output.close();
                input.close();
                return "Downloaded";
            } catch (Exception e) {
                return null;
            }

        }

        @Override
        protected void onPreExecute() {
            super.onPreExecute();
            mProgressDialog.show();
        }

        @Override
        protected void onProgressUpdate(Integer... progress) {
            super.onProgressUpdate(progress);
            mProgressDialog.setProgress(progress[0]);
        }

        @Override
        protected void onPostExecute(String result) {
            mProgressDialog.dismiss();
            if (result.equals("Downloaded")) {
                //do something here with the downloaded file
            }
        }
    }

Finally put that in onCreate (or when you want to call the download) to call the AsyncTask class sending the URL of the file to download:

DownloadFile downloadFile = new DownloadFile();
                    downloadFile.execute("http://www.page.com/file.mp3");

Hope it helps!

Ezrou
  • 438
  • 6
  • 14