I cannot download the file using HTTPS(https://) transfer protocol.The file gets download while using Http(http://)
val request = DownloadManager.Request(
Uri.parse(url))
val dm = getSystemService(Context.DOWNLOAD_SERVICE) as DownloadManager
val fileName = URLUtil.guessFileName(url, contentDisposition, mimetype)
val destinationFile = File(
Environment.getExternalStorageDirectory().absolutePath + "/FileName",
fileName)
request.allowScanningByMediaScanner()
request.setAllowedNetworkTypes(DownloadManager.Request.NETWORK_WIFI or DownloadManager.Request.NETWORK_MOBILE)
request.addRequestHeader("User-Agent", userAgent)
request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED)
request.setDestinationUri(Uri.fromFile(destinationFile))
dm.enqueue(request)
Related
I am using Download Manager to Download PDFs and Images. Downloaded files are not getting saved in Download Folder. Here is my code.
`
val fileName = "MG Uploaded Documents"
val request = DownloadManager.Request(Uri.parse(downloadUrl))
.setTitle("Download")
.setDescription("Downloading")
request.setDestinationUri(
Uri.fromFile(File(this.getExternalFilesDir(Environment.DIRECTORY_DOWNLOADS)
.toString() , fileName)))
.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED)
.setAllowedOverMetered(true)
val dm = this.getSystemService(Context.DOWNLOAD_SERVICE) as DownloadManager
dm.enqueue(request)
this.T("File is Downloading. Please wait!")
`
This code is in Home Activity. Any help.
I was not saving the file name with .pdf extension.
Below is the working code.
private fun downloadPDF(url: String) {
val fileName = "YourPdfName.pdf"
val request = DownloadManager.Request(Uri.parse(url))
.setTitle("PDF Download")
.setDescription("Downloading")
.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, fileName)
.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED)
.setAllowedOverMetered(true)
// val dm = getSystemService(DOWNLOAD_SERVICE) as DownloadManager
val dm = requireContext().getSystemService(Context.DOWNLOAD_SERVICE) as DownloadManager
dm.enqueue(request)
}
I am using DownloadManager to download a file from FirebaseStorage.
First, I will get the downloadUrl from FirebaseStorage and proceed with DownloadManager
As you can see codes below, this is where after I got the downloadUrl as url.
downloadManager = getSystemService(DOWNLOAD_SERVICE) as DownloadManager
val uri = Uri.parse(url)
val request = DownloadManager.Request(uri)
val folderName = File.separator + "MBITION" + File.separator + fileName + fileExtension
name = folderName
Log.i("???", "url: $url")
Log.i("???", "folderName: $folderName")
request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED)
request.setDestinationInExternalPublicDir(
Environment.DIRECTORY_DOWNLOADS,
folderName
)
enq = downloadManager!!.enqueue(request)
Logcat below shows the url and folderName value.
I/???: url: https://firebasestorage.googleapis.com/v0/b/mbition-2022.appspot.com/o/note%2F-N2_fRAhJXVshDjQMcrz?alt=media&token=936e1014-6c7a-4f46-89fd-5746eb6a9dbf
I/???: folderName: /MBITION/ICT600 - Chapter 3.pdf
As you can see codes below, where onReceive from BroadcastReceiver is handled.
if (DownloadManager.ACTION_DOWNLOAD_COMPLETE == action) {
val downloadId = it.getLongExtra(DownloadManager.EXTRA_DOWNLOAD_ID, 0)
val query = DownloadManager.Query()
query.setFilterById(downloadId)
val c: Cursor = downloadManager!!.query(query)
if (c.moveToFirst()) {
val columnIndex: Int = c.getColumnIndex(DownloadManager.COLUMN_STATUS)
if (DownloadManager.STATUS_SUCCESSFUL == c.getInt(columnIndex)) {
val uriString: String = c.getString(c.getColumnIndex(DownloadManager.COLUMN_LOCAL_URI))
val file = File(uriString)
val target = Intent(Intent.ACTION_VIEW)
Log.i("???", "uriString:: $uriString")
Log.i("???", "file:: $file")
val uri = FileProvider.getUriForFile(
this#NoteActivity,
"$packageName.provider",
file
)
target.setDataAndType(uri, "application/pdf")
target.flags = Intent.FLAG_GRANT_READ_URI_PERMISSION
val intentChooser = Intent.createChooser(target, "Open File")
try {
startActivity(intentChooser)
} catch (e: ActivityNotFoundException) {
Tools.showToast(
this#NoteActivity,
"You need to download PDF reader"
)
}
}
}
}
Below shows the Logcat.
I/???: uriString:: file:///storage/emulated/0/Download/MBITION/ICT600%20-%20Chapter%203-5.pdf
I/???: file:: file:/storage/emulated/0/Download/MBITION/ICT600%20-%20Chapter%203-5.pdf
This is my provider_paths.xml
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path
name="external_files"
path="." />
</paths>
I tried to open the file through the DownloadManager's Notification. It is working fine.
Image below shows where the file is located inside the MBITION folder.
Below is the error I got from Logcat.
2022-05-28 11:36:44.534 4999-4999/com.aaa.mbition E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.aaa.mbition, PID: 4999
java.lang.IllegalArgumentException: Failed to find configured root that contains /file:/storage/emulated/0/Download/MBITION/ICT600%20-%20Chapter%203.pdf
at androidx.core.content.FileProvider$SimplePathStrategy.getUriForFile(FileProvider.java:800)
at androidx.core.content.FileProvider.getUriForFile(FileProvider.java:442)
at com.aaa.mbition.ui.NoteActivity$onCompleteDownloadFile$1$onReceive$1.invoke(NoteActivity.kt:79)
Updated:
Refer to #blackapps 's suggestion. I tried to remove file:// by using replace like below:
val uriString: String = c.getString(c.getColumnIndex(DownloadManager.COLUMN_LOCAL_URI))
val urlFixer = uriString.replace("file://","")
val file = File(urlFixer)
val target = Intent(Intent.ACTION_VIEW)
Log.i("???", "uriString:: $uriString")
Log.i("???", "file:: $file")
Log.i("???", "urlFixer:: $urlFixer")
val uri = FileProvider.getUriForFile(
this#NoteActivity,
"$packageName.provider",
file
)
Below is the Logcat
I/???: uriString:: file:///storage/emulated/0/Download/MBITION/ICT600%20-%20Chapter%203-9.pdf
I/???: file:: /storage/emulated/0/Download/MBITION/ICT600%20-%20Chapter%203-9.pdf
I/???: urlFixer:: /storage/emulated/0/Download/MBITION/ICT600%20-%20Chapter%203-9.pdf
When I pressed OK button, it proceed to PDF Reader, a few milisecond, it kick me back to the apps.
According to #blackapps answer is working. I fixed them by using replace.
val uriString: String = c.getString(c.getColumnIndex(DownloadManager.COLUMN_LOCAL_URI))
val urlFixer = uriString.replace("file://", "").replace("%20", " ")
val file = File(urlFixer)
val target = Intent(Intent.ACTION_VIEW)
I am receveving a pdf as an encoded base64 String. I would like to show the PDF with ACTION_VIEW intent. How can I do that?
What I have so far is this
val byteArray = Base64.decode(base64String, Base64.DEFAULT)
val file = FileUtils.createFile(requireContext(), "application/pdf")
val fos = FileOutputStream(file)
fos.write(byteArray)
fos.close()
val uri = FileProvider.getUriForFile(requireContext(), requireActivity().getString(R.string.file_provider), file)
val intent = Intent(Intent.ACTION_VIEW)
intent.setDataAndType(uri, "application/pdf")
intent.setFlags(Intent.FLAG_ACTIVITY_NO_HISTORY)
startActivity(intent)
createFile function looks like
fun createFile(context: Context, mimeType: String): File {
val timeStamp = SimpleDateFormat("yyyyMMdd_HHmmss", Locale.getDefault()).format(Date())
val fileName = "TMP_" + timeStamp + "_"
val suffix = "." + MimeTypeMap.getSingleton().getExtensionFromMimeType(mimeType) //.pdf
return context.getExternalFilesDir("Documents")?.let {
if (!it.exists()) {
it.mkdir()
}
File.createTempFile(fileName, suffix, it)
} ?: File.createTempFile(fileName, suffix, Environment.getExternalStorageDirectory())
}
The intent starts properly but when I try to open it with a pdf viewer it says the file is corrupted.
I simple changed this
intent.setFlags(Intent.FLAG_ACTIVITY_NO_HISTORY)
to
intent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
works fine now!
I am trying to download a pdf file from the server (I have the url), and I am trying this solution
fun downloadPDF(url: String?, fileName: String): ResponseStatus {
val uri = Uri.parse(url)
val downloadManager = context.getSystemService(Context.DOWNLOAD_SERVICE) as DownloadManager?
val request = DownloadManager.Request(uri)
request.setAllowedNetworkTypes(
DownloadManager.Request.NETWORK_WIFI or DownloadManager.Request.NETWORK_MOBILE
)
request.setTitle(fileName)
request.setDescription("Android Data download using DownloadManager.")
request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED)
request.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, fileName)
request.setMimeType("*/*")
if (downloadManager == null) {
return ResponseStatus.Error( context.getString(R.string.download_error) )
}
downloadManager.enqueue(request)
return ResponseStatus.OK(uri)
}
this works for API 30 but not for API 27 and I don't know why.
Can someone help me please?
UPDATE:
I think that this can be a permissions problem because I tried again in API 27 and see this in the log java.lang.SecurityException: No permission to write to /storage/emulated/0/Download/file name12-34: Neither user 10080 nor current process has android.permission.WRITE_EXTERNAL_STORAGE.
I was able to solve the problem, I changed this line
request.setDestinationInExternalPublicDir (Environment.DIRECTORY_DOWNLOADS, fileName) for a uri that I parse with the address of the download folder and the file name, and I set it with request.setDestinationUri (destinationUri)
val destination = context.getExternalFilesDir(Environment.DIRECTORY_DOWNLOADS).toString() +
"/" + fileName
val destinationUri = Uri.parse("$FILE_BASE_PATH$destination")
The following code works perfectly to download mp3 file in external storage, but doens't work to download file in internal storage. A lot of smartphone doesn't have external storage. What can i do? I don't know how to implement async task in kotlin, if it is needed.
mywebView.setDownloadListener(object : DownloadListener {
override fun onDownloadStart(url: String, userAgent: String,
contentDisposition: String, mimetype: String,
contentLength: Long) {
val request = DownloadManager.Request(Uri.parse(url))
request.allowScanningByMediaScanner()
request.setDescription("Download file...")
request.setTitle(URLUtil.guessFileName(url, contentDisposition, mimetype))
request.setAllowedNetworkTypes(DownloadManager.Request.NETWORK_WIFI or DownloadManager.Request.NETWORK_MOBILE)
request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED) //Notify client once download is completed!
request.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, mimetype )
val webview = getSystemService(DOWNLOAD_SERVICE) as DownloadManager
webview.enqueue(request)
Toast.makeText(getApplicationContext(), "Download avviato", Toast.LENGTH_LONG).show()
}
})
Cannot test the code at the moment, but it should be something like the follow:
mywebView.setDownloadListener(object : DownloadListener {
override fun onDownloadStart(url: String, userAgent: String,
contentDisposition: String, mimetype: String,
contentLength: Long) {
val request = DownloadManager.Request(Uri.parse(url))
request.allowScanningByMediaScanner()
request.setDescription("Download file...")
request.setTitle(URLUtil.guessFileName(url, contentDisposition, mimetype))
request.setAllowedNetworkTypes(DownloadManager.Request.NETWORK_WIFI or DownloadManager.Request.NETWORK_MOBILE)
request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED) //Notify client once download is completed!
request.setDestinationInExternalPublicDir(Environment.getExternalStorageDirectory(), mimetype )
val webview = getSystemService(DOWNLOAD_SERVICE) as DownloadManager
webview.enqueue(request)
Toast.makeText(getApplicationContext(), "Download avviato", Toast.LENGTH_LONG).show()
}
})