Downloaded .apk file in Android corrupted - android

I need to download by program an .apk file then launching its activity.
The code I am using is the following
private String downloadFile(String sourceURL, String destinationPath)
{
try {
URL url = new URL(sourceURL);
URLConnection connection = url.openConnection();
connection.connect();
// download the file
InputStream input = new BufferedInputStream(url.openStream());
OutputStream output = new FileOutputStream(destinationPath);
byte data[] = new byte[1024];
int count;
while ((count = input.read(data)) > 0) {
output.write(data, 0, count);
}
output.flush();
output.close();
input.close();
// EDITED here: Make the file rw, otherwise the apk file will not be installed
Runtime.getRuntime().exec("chmod 666 " + destinationPath);
message = "OK";
}
catch (MalformedURLException e) {
message = "Malformed URL error: " + e.getMessage();
}
catch (ProtocolException e) {
message = "Protocol exception error: " + e.getMessage();
}
catch (FileNotFoundException e) {
message = "File not found error: " + e.getMessage();
}
catch (IOException e) {
e.printStackTrace();
message = "Failed to download the file : " + e.getMessage();
}
return message;
}
I mention that I call the method first for a text file, then for an apk file. Each time I process the files locally, therefore, somehow I know what's going wrong or not. In this way I know that the text file is downloaded correctly. But the .apk file is corrupted. Because I develop locally, with access to DDMS and localhost (the IP: 10.0.2.2) I can firmly state that the culprit is the code above. When I artificially replace the 'downloaded' file, through DDMS, with the original .apk file, all processing that follows is Ok. In addition, I have byes difference when I compare the original and the downloaded .apk files.
What am I doing wrong?
Thanks
PS: Searching, I realized that, while is a popular issue, there is no consistent answer to it. In my case I identified it as purely a download method issue.

Please see above the answer under the EDITED line. Implemented, works fine, that may help others

Related

Cannot add a eng.traineddata to my Tesseract project Android 5.0

I am currently trying to implement Tesseract OCR into my project but have came to a crossing road. I followed all of the directions from https://github.com/rmtheis/tess-two and got stuck at the actual implementation portion of this project. The current code I have running is:
TessBaseAPI baseApi = new TessBaseAPI();
baseApi.init(TESS_DATA_FILE_PATH, "eng");
baseApi.setImage(icon);
String recognizedText = baseApi.getUTF8Text();
baseApi.end();
Now the TESS_DATA_FILE_PATH is the current issue. I have been trying to add the eng.traineddata file to my project, but I simply do not know where or how to do it.
Things I have tried:
In the assets folder I added the file eng.traineddata but that is read only and I cannot change it at run time. So this wont work
I tried to add in other ways of running the project, and running the adb push command to add it directly to the device, but that wont work since I will be pushing this application to the masses.
So what I am looking for is an answer of, How do I add the eng.traineddata to my project. And what do I place in the TESS_DATA_FILE_PATH part of the init call.
Side Notes:
I did receive the BUILD SUCCESSFUL call at the end of all the steps at the link provided above.
I have successfully added the language pack to my project, and ran tess two on my android project.
Here is the code for how I did it:
This is what sets up the files path, and adds the traineddata folder
public void setupOCR(){
File folder = new File(Environment.getExternalStorageDirectory() + "/classlinkp/tessdata");
if (!folder.exists()) {
folder.mkdirs();
}
File saving = new File(folder, "eng.traineddata");
try {
saving.createNewFile();
} catch (IOException e) {
e.printStackTrace();
}
InputStream stream = null;
try {
stream = mContext.getAssets().open("eng.traineddata", AssetManager.ACCESS_STREAMING);
} catch (IOException e) {
e.printStackTrace();
}
if (stream != null){
copyInputStreamToFile(stream, saving);
}
}
Here is how I saved out the eng.traineddata file:
private void copyInputStreamToFile( InputStream in, File file ) {
try {
OutputStream out = new FileOutputStream(file);
byte[] buf = new byte[1024];
int len;
while((len=in.read(buf))>0){
out.write(buf,0,len);
}
out.close();
in.close();
} catch (Exception e) {
e.printStackTrace();
}
}
The saving method was gathered from: https://stackoverflow.com/a/28131358/3781164

How to send PNG file from android and receive it in python

I'm trying to send PNG file from my android server to my python client.
The PNG image I try to send is a screenshot, around 4mb tops, usually under 2mb.
android code (sending):
File myFile = new File(imagePath);
FileInputStream fis = null;
try {
fis = new FileInputStream(myFile);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
BufferedInputStream bis = new BufferedInputStream(fis);
Log.i("service", "sending file len");
try {
out.write("" +myFile.length());
out.flush();
} catch (Exception e) {
e.printStackTrace();
}
Log.i("service:", "waiteing for ok");
try {
msg = in.readLine();
} catch (Exception e) {
e.printStackTrace();
}
Log.i("service", "sending file");
byte[] outBuffer = new byte[(int) myFile.length()];
try {
bis.read(outBuffer, 0, outBuffer.length);
os = client.getOutputStream();
os.write(outBuffer, 0, outBuffer.length);
} catch (IOException e) {
e.printStackTrace();
}
python code (receiving):
print "waiting for responce's length"
MSGLEN = int(sock.recv(bufferLen))
print MSGLEN
sock.sendall("ok" +"\n")
chunks = []
bytes_recd = 0
while bytes_recd < MSGLEN:
chunk = sock.recv(min(MSGLEN - bytes_recd, bufferLen))
chunks.append(chunk)
bytes_recd = bytes_recd + len(chunk)
dataRecived = ''.join(chunks)
print 'data receieved'
print 'writing data to file'
fileout = open("D:\shots.png", 'w')
fileout.write(dataRecived)
fileout.close()
The file transfers from the android to my PC, but the file is corrupted.
When I compare it with the original image, almost everything is identical
except some empty lines here and there (not missing information, just empty line like someone added \n) and 1 or 2 big chunks of lines (15 lines or so) are missing.
Here you can see comparison between the tho files (left-original, right-file after sending).
I don't know why the file transfers corrupted, please help me.
Try coding it as Base64 and sending a simple string. Those missing lines are also part of image data - remember that those are binary.
Base64 or Bytestream is what u need

InputStream Exception while downloading a file

I am trying to download a PPT file from a server.
it's in Bytes.
but while debugging I noticed that the input stream throws an exception of FileNotFound while running.. the file does exist on the server, here's my code, any help would be greatly appreciated.
public class DownloadFileAsync extends AsyncTask<String, String, String> {
#Override
protected String doInBackground(String... aurl) {
int count;
try {
URL url = new URL(aurl[0]);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.addRequestProperty("Authorization", "Basic " + SharedPref.getAuthPrefValue());
connection.addRequestProperty("Device", BaseApplication.getCurrentDevice().getDevice().toString());
connection.addRequestProperty("DeviceId", BaseApplication.getCurrentDevice().getDeviceId());
connection.connect();
int lengthOfFile = connection.getContentLength();
Log.d("ANDRO_ASYNC", "Length of file: " + lengthOfFile);
InputStream input = new BufferedInputStream(url.openStream());
File sdcardDest = new File(Environment.getExternalStorageDirectory(), "Availo");
String finalDest = sdcardDest + File.separator + "Check1" + "." + "PPT";
OutputStream output = new FileOutputStream(finalDest);
byte data[] = new byte[1024];
long total = 0;
while ((count = input.read(data)) != -1) {
total += count;
publishProgress(""+(int)((total*100)/lengthOfFile));
output.write(data, 0, count);
}
output.flush();
output.close();
input.close();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
I am using Charles on Mac (which is similar to fiddler on windows.) to see what I send and receive from the server,
The server doesn't return any error, though it shows download steps for 6-7 sec, downloading around 400 bytes and then it stops.
The Exception is thrown from the input stream line.
Thanks!
I suggest you take a look at the DownloadManager system service. it's designed specifically for what you are trying to do:
(from the documentation)
The download manager is a system service that handles long-running
HTTP downloads. Clients may request that a URI be downloaded to a
particular destination file. The download manager will conduct the
download in the background, taking care of HTTP interactions and
retrying downloads after failures or across connectivity changes and
system reboots
While I do agree with Muzikant regarding the download manager,
FileNotFoundException is usually thrown when... the file is not found on the local device...
You need to do the following to make sure it doesnt happen
File dest = new File(finalDest);
try{
File parentDest = dest.getParentFile();
if(!parentDest.exists()){
parentDest.mkdirs(); //make all the directory structures needed
}
if(!dest.exists()){
dest.createNewFile();
}
OutputStream output = new FileOutputStream(dest);
//now you can use your file dest
//write data to it...
}catch (Exception e){
}

How do I store data to the device?

I'm trying to figure how to store my application's data for the long term. Basically I get a list of data from from a web service, and I don't want to go back to the web service the next time the app runs. I'd prefer to just store it locally. How do I do this?
I don't mind serialising the data to any particular format. I don't see this on the Xamarin site for Android. There's a tutorial for iOS, but I'm not interested in that.
I personally copy the data from webservice in raw format in a text file on the memory.
So, I have just to open the inputStream from the file the same I did from the webservice and my code remains clean.
But I guess there are indeed thousands of ways to copy this data.
I just wanted to share the one I found more convenient.
The code just for information:
InputStream source = getStreamFromWebservice();// <= YOUR CODE HERE
File dir = context.getDir("CACHE", Context.MODE_PRIVATE);
dir.mkdirs();
File file = new File(dir, fileName);
// Write to Memory
try {
FileOutputStream f = new FileOutputStream(file);
byte[] buffer = new byte[32768];
int read;
try {
while ((read = source.read(buffer, 0, buffer.length)) > 0) {
f.write(buffer, 0, read);
}
} catch (IOException e) {
e.printStackTrace();
}
f.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
}

Android:Virtual machine cannot download file from website

I have written an app to download a .PDF file from the given url path.
But when I run it in the vm,I found my app cannot download the file.
So I tryed the DownloadManager in the vm,still it cannot download the file .
And the DownloadManage stopped with just and always showing "OnGoing".
Can anyone tell me the reason and how to solve this problem?
Thanks in advance!
PS:I write this
public File writeFileToSDCard(String path,String fileName,InputStream in){
File file = null;
OutputStream out = null;
try{
if(!createDir(path)){
Log.e("FileUtils.java", "writeFileToSDCard().createDir() failed!");
}else{
Log.e("FileUtils.java", "writeFileToSDCard().createDir() Successed!");
}
file = createFile(path+fileName);
out = new FileOutputStream(file);
byte buffer[] = new byte[128];
//write the file
do{
int length = in.read(buffer);
if(length != -1){
Log.e("FileUtils.java", "Writing to card!");
out.write(buffer, 0, length);
}else{
break;
}
}while(true);
}catch(Exception e){
Log.e("FileUtils.java", "writeFileToSDCard() failed!");
}finally {
try{
out.close();
}catch (Exception e) {
Log.e("FileUtils.java", "writeFileToSDCard() finally failed!");
}
}
return file;
}
*PSS:*I dont think my code goes wrong,but Is it the problem of the android emulator?
Most probably it is because you don't have permission to download the file from the server.
I had a similar problem few days back, I solved it by creating a .htacces file in the server directory. Create a file named .htacess containing this :
satisfy any
and save it in the directory where your pdf file is. I am not familiar with how this works, but I guess it has something to do with the permissions. Note that if you do this anyone can access the contents of that directory. And I believe this will only wirk for Apache servers.
Don't know if it will work, but its worth a shot.

Categories

Resources