download multiple files keeps stopping android - java

Trying to download about 38 video files from a server with the code below and for some reason it keeps stopping at different points during the download, I'm mostly getting a
java.net.SocketException: Connection timed out
I'd like to know how I can perform this with less errors
My code below
private class DownloadFile extends AsyncTask<String, Integer, String> {
#Override
protected void onPreExecute() {
super.onPreExecute();
mProgressDialog.show();
}
#Override
protected void onProgressUpdate(Integer... progress) {
super.onProgressUpdate(progress);
mProgressDialog.setProgress(progress[0]);
mProgressDialog.setMessage("Downloading "+(i+1)+" of "+downloadURL.length);
}
#Override
protected String doInBackground(String... sUrl) {
try {
for(int i = 0; i < sUrl.length; i++){
URL url = new URL("http://myvideo.info/videos/"+sUrl[i]);
URLConnection connection = null;
try {
connection = url.openConnection();
connection.setConnectTimeout(15000);
connection.setReadTimeout(15000);
} catch (java.net.SocketTimeoutException e) {
e.printStackTrace();
}catch (Exception e) {
e.printStackTrace();
}
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("/sdcard/"+file_rename[i]);
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();
}
} catch (Exception e) {
Log.e("PP", "PP", e);
}
return null;
}
protected void onPostExecute(String jsonResult) {
mProgressDialog.dismiss();
}
}

Are you sure the server is responding in less then 15 sec?(that is the timeout I've seen that you have set). If the files are big you should be downloading them separately, take a look at Downloader manager, you can use it to download big files easy.

What download manager are you using?
And I'd suggest changing your timeout to the maximum. Personally your code seems fine. I think it would be your download manager and timeout. Hope this helps.

Related

Instead of JSON data link is returning .txt file how to get JSON data in android

I am using a link when I open that link in the browser it generates a json.txt file and downloads it. I want to fetch this txt file in an android application and want to get JSON data from this txt file.
new DownloadFileFromURL().execute("your_file_downloadable_url");
class DownloadFileFromURL extends AsyncTask<String, String, String> {
/**
* Before starting background thread
* */
#Override
protected void onPreExecute() {
super.onPreExecute();
System.out.println("Starting download");
}
/**
* Downloading file in background thread
* */
#Override
protected String doInBackground(String... f_url) {
int count;
try {
String root = Environment.getExternalStorageDirectory().toString();
System.out.println("Downloading");
URL url = new URL(f_url[0]);
URLConnection conection = url.openConnection();
conection.connect();
// getting file length
int lenghtOfFile = conection.getContentLength();
// input stream to read file - with 8k buffer
InputStream input = new BufferedInputStream(url.openStream(), 8192);
// Output stream to write file
OutputStream output = new FileOutputStream(root+"/downloadedfile.txt");
byte data[] = new byte[1024];
long total = 0;
while ((count = input.read(data)) != -1) {
total += count;
// writing data to file
output.write(data, 0, count);
}
// flushing output
output.flush();
// closing streams
output.close();
input.close();
} catch (Exception e) {
Log.e("Error: ", e.getMessage());
}
return null;
}
/**
* After completing background task
* **/
#Override
protected void onPostExecute(String file_url) {
System.out.println("Downloaded");
pDialog.dismiss();
}
}

Can't detect the socket is disconnected [duplicate]

This question already has answers here:
JAVA : Handling socket disconnection
(4 answers)
Closed 5 years ago.
Hi this is my code for sending data through a socket to another device connected to the network
try {
PrintWriter printWriter = new PrintWriter(new BufferedWriter(new OutputStreamWriter(socket.getOutputStream())), true);
printWriter.print(data);
Log.d("error", printWriter.checkError() + "");
printWriter.flush();
} catch (IOException e) {
Log.d("socket","is disconnected");
e.printStackTrace();
}
the problem is printWriter.checkError() is always returning false and the IOException never happens. for disconnecting socket I'm turning device off and trying to send data again. even reading from InputStream doesn't help
private class SocketHandler extends AsyncTask<Void, byte[], Void> {
InputStream in;
#Override
protected void onPreExecute() {
try {
in = socket.getInputStream();
} catch (IOException e) {
e.printStackTrace();
}
super.onPreExecute();
}
#Override
protected Void doInBackground(Void... voids) {
byte[] content = new byte[2048];
if (in != null) {
while (true) {
try {
if (in.available() > 0) {
int n = in.read(content);
if (n == -1) {
break;
}
publishProgress(new byte[][]{Arrays.copyOfRange(content, 0, n)});
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
return null;
}
#Override
protected void onProgressUpdate(byte[]... values) {
String data = new String(values[0]);
super.onProgressUpdate(values);
}
#Override
protected void onPostExecute(Void aVoid) {
Log.d("socket", "is disconnected");
}
}
read never returns -1 so I can detect the socket is disconnected. What can I do?
edit: It's not duplicate of JAVA : Handling socket disconnection because I did everything mentioned there
I had the same problem. I used a timer to send connection check command every second in both side and in that timer I checked the last time that I received this connection check command and if it's over for example 10 seconds, then I decided that the socket is disconnected
tOut = new Timer();
tOut.schedule(new TimerTask() {
#Override
public void run() {
long dif = System.currentTimeMillis() - lastCCReceivedTime;
if (dif > 1000 * 10) {
// socket is disconnected
return;
}
try {
out.println("Connection check");
} catch (Exception e) {
if (out != null)
out.close();
// socket is disconnected
}
}
}, 1000, 1000);
Save the last time that the command was received
while ((msg = in.readLine()) != null) {
lastCCReceivedTime = System.currentTimeMillis();
//Message received
}
if (in.available() > 0) {
You never call read() unless there is data available to be read without blocking.
int n = in.read(content);
if (n == -1) {
break;
Unreachable.
}
And here if available() was zero you do nothing except spin mindlessly smoking the CPU.
Cure: remove the available() test. It isn't doing anything useful, and it is preventing you from detecting end of stream.

URLConnection time out issue

I am working in an android application and I am downloading a file from an url. Every thing works fine, but when the internet connection goes in between(After opening a connection) the downloading time out never occurs and the connection never ends.
Suggest me a solution to solve this issue
**URL url = new URL("fileURL");
URLConnection connection = url.openConnection();
connection.setConnectTimeout(5000);
File file = new File(context.getFilesDir(), "" + filename);
// getting file length
int lenghtOfFile = connection.getContentLength();
// input stream to read file - with 8k buffer
InputStream input = new BufferedInputStream(url.openStream(), 8192);
// Output stream to write file
OutputStream output = new FileOutputStream(file);
byte data[] = new byte[1024];
long total = 0;
while ((count = input.read(data)) != -1) {
total += count;
int status = (int) ((total * 100) / lenghtOfFile);
publishProgress("" + status);
// writing data to file
output.write(data, 0, count);
}
// flushing output
output.flush();
// closing streams
output.close();
input.close()**
You can use Retrofit Library to download files from server,
Retrofit uses OkHttp internally
Please refer below URL,
https://futurestud.io/tutorials/retrofit-2-how-to-download-files-from-server
final FileDownloadService downloadService =
ServiceGenerator.createService(FileDownloadService.class);
Call<ResponseBody> call =
downloadService.downloadFileWithDynamicUrlSync(fileUrl);
call.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, final Response<ResponseBody>
response) {
if (response.isSuccessful()) {
Log.d(TAG, "server contacted and has file");
new AsyncTask<Void, Void, Void>() {
#Override
protected Void doInBackground(Void... voids) {
boolean writtenToDisk = writeResponseBodyToDisk(FileDownloadActivity.this, response.body(), null);
Log.d(TAG, "file download was a success? " + writtenToDisk);
return null;
}
}.execute();
} else {
Log.d(TAG, "server contact failed");
}
}
And you can also use #Streaming annotation for large files. Retrofit will handle the large file download also

How to write html to a file in android

I know this has been asked a few times here, but I'm not sure which way I should go. This code downloads the html file okay, but I get an IOException when trying to write the html to a file. I've tried many suggestions on sof, but none seem to work for me and I'm at a loss as it seems it should be working.
class Downloader extends AsyncTask<URL, Void, Void> {
String site = getResources().getString(R.string.sched_hd_url);
File sdCard = Environment.getExternalStorageDirectory();
File dir = new File(sdCard.getAbsolutePath() + "/directory/");
File file = new File(dir, "file.html");
#Override
protected Void doInBackground(URL... urls) {
try {
URL url = new URL(site);
URLConnection yc = url.openConnection();
BufferedInputStream in = new BufferedInputStream(new URL(site).openStream());
OutputStream out = new FileOutputStream(file);
int total = 0;
int count;
byte data1[] = new byte[1024];
while ((count = in.read(data1)) != -1) {
out.write(data1);
total += count;
}
in.close();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
protected void onPostExecute(Void result) {
progress.setVisibility(View.INVISIBLE);
finish();
}
}
I run this code and no file appears in the directory that I specified. The directory already exists, and I do have the permissions in my manifest. Any suggestions would be greatly appreciated.
So my problem was a couple of things. First, I want to thank those that commented. In my question, I did neglect to put in the out.close(); method. When that didn't work, I was looking at the string which held the URL I wanted to use. That had errors in it. This fixed the download problem, but I wanted to download from a place where the .html file was not in the URL (example: http://www.example.com/ instead of http://www.example.com/index.html). It worked for the latter but not the former. So instead of using URLConnection I used HttpURLConnection. Here is my working code:
class Downloader extends AsyncTask<URL, Void, Void> {
String site = getResources().getString(R.string.sched_hd_url);
File sdCard = Environment.getExternalStorageDirectory();
File dir = new File(sdCard.getAbsolutePath() + "/directory/");
File file = new File(dir, "file.html");
#Override
protected Void doInBackground(URL... uri) {
FileOutputStream out = null;
if (file.exists()) {
try {
file.delete();
file.createNewFile();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
try {
URL url = new URL(site);
HttpURLConnection yc = (HttpURLConnection) url.openConnection();
BufferedInputStream in = new BufferedInputStream(
new URL(site).openStream());
out = new FileOutputStream(file);
int total = 0;
int count;
byte data1[] = new byte[1024];
while ((count = in.read(data1)) != -1) {
out.write(data1);
total += count;
}
in.close();
out.close();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
protected void onPostExecute(Void result) {
progress.setVisibility(View.INVISIBLE);
finish();
}
}
Also another error in my question was in regards to no implementation checking to see if the file had already existed. Thanks again for the help.

How to creat a event Trigger when download is finished

am writing a downloadManager and i need a hint. there i could create an event an fire it when ever i wanted. but i cant seem to find how to do that in java. what i want to do is i want to create an event for my class and then fire it inside one of the classes' member methods. now when ever this Class is called and sees that the download is finish(i.e. some variable has reached 100 for example) it fires an event indicating the situation. how can i create that in java?
public class DownloadManager
{
static Queue<AvailableGame> downloadQueue;
static Integer currenProgress;
static String currentDownload;
static Boolean isRunning;
/**
* Start download
*/
public void startDownloading()
{
AsyncTask task = new AsyncTask()
{
#Override
protected Object doInBackground(Object[] objects)
{
downloadNextFile();
return null;
private static String downloadFile(String downloadUrl)
{
String toDownload = downloadUrl;
String fileName = getFileNameFromUrl(toDownload);
// take CPU lock to prevent CPU from going off if the user
// presses the power button during download
PowerManager pm = (PowerManager)
MainActivity.getContext().getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
"DownloadManager");
wl.acquire();
try
{
InputStream input = null;
OutputStream output = null;
HttpURLConnection connection = null;
try
{
URL url = new URL(toDownload);
connection = (HttpURLConnection) url.openConnection();
connection.connect();
// expect HTTP 200 OK, so we don't mistakenly save error report
// instead of the file
if (connection.getResponseCode() != HttpURLConnection.HTTP_OK)
{
return "Server returned HTTP " + connection.getResponseCode() + " "
+ connection.getResponseMessage();
}
int fileLength = connection.getContentLength();
// download the file
input = connection.getInputStream();
output = new FileOutputStream("/sdcard/" + fileName);
byte data[] = new byte[4096];
long total = 0;
int count;
while ((count = input.read(data)) != -1)
{
total += count;
// publishing the progress....
if (fileLength > 0)
{
currenProgress = ((int) (total * 100 / fileLength));
currentDownload = "Downloading " + fileName;
}
output.write(data, 0, count);
}
}
catch (Exception e)
{
return e.toString();
}
finally
{
try
{
if (output != null)
{
output.close();
}
if (input != null)
{
input.close();
}
}
catch (IOException ignored)
{
}
if (connection != null)
{
connection.disconnect();
}
}
}
finally
{
wl.release();
}
return null;
}
}
How can i save information when my download is finish,the second probleem is how to a
First I think you should be using Android's DownloadManager for this. If you are, you can register a BroadcastReceiver that detects when a download is finished.
There is a full example you can download and run on your phone with full source code for you to see how this can be done: https://github.com/commonsguy/cw-omnibus/tree/master/EmPubLite/T16-Update
Check specifically the files DownloadCheckService.java and DownloadCompleteReceiver.java.
Hope it helps.

Categories

Resources