Android Question ultimatewebview downloading error

boresh

Member
Respected Sir

Happy Evening

i am doing student internship,
i am converting web application to android webview application.
downloaded b4a
downloaded example file "B4AExample.zip" from "https://www.b4x.com/android/forum/threads/ultimatewebview-custom-view.135666/"
and in that "txtUrl.Text" control i entered "https://app.evergreenelectric.in" and the webview display good and beautiful.
with single line of code got entire project.

Only problem i am facing is downloading the files (Excel and pdf Files) from the site within webview. but the same is working file when accessing the website.

GETTING ERROR AS BELOW :

*** Service (starter) Create ***
** Service (starter) Start **
** Activity (main) Create, isFirst = true **
** Activity (main) Resume **
Download INITIALIZED
Error occurred on line: 81 (Main)
java.lang.reflect.InvocationTargetException
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4j.object.JavaObject.RunMethod(JavaObject.java:132)
at com.uwebview.ultimatewebview._startfiledownload(ultimatewebview.java:3708)
at com.test.net.main._ultimatewebview1_filedownloadinitialized(main.java:570)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.shell.Shell.runMethod(Shell.java:732)
at anywheresoftware.b4a.shell.Shell.raiseEventImpl(Shell.java:348)
at anywheresoftware.b4a.shell.Shell.raiseEvent(Shell.java:255)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.ShellBA.raiseEvent2(ShellBA.java:146)
at anywheresoftware.b4a.keywords.Common.CallSub4(Common.java:1085)
at anywheresoftware.b4a.keywords.Common.CallSubNew2(Common.java:1040)
at com.uwebview.ultimatewebview._ondownloadinitialized(ultimatewebview.java:1981)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.BA.raiseEvent2(BA.java:213)
at anywheresoftware.b4a.BA$1.run(BA.java:352)
at android.os.Handler.handleCallback(Handler.java:938)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loopOnce(Looper.java:226)
at android.os.Looper.loop(Looper.java:313)
at android.app.ActivityThread.main(ActivityThread.java:8663)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:567)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1135)
Caused by: java.lang.IllegalArgumentException: Can only download HTTP/HTTPS URIs: blob:https://app.evergreenelectric.in/3c18e813-abbd-408e-b56d-40625b6b896f
at android.app.DownloadManager$Request.<init>(DownloadManager.java:634)
at com.uwebview.ultimatewebview$MyDownloadListener.startDownload(ultimatewebview.java:4167)
... 24 more
** Activity (main) Pause, UserClosed = true **
** Service (starter) Destroy (ignored)**


Please help to solve the problem.
Thanks in advance
 

agraham

Expert
Licensed User
Longtime User
I found this on the web that seems to be the cause of your problem.
Tthe Android Download Manager only accepts http and https download uris.
So blob uris needs to be converted into a base64 string in JS and then that base64 string has to be written on the download path using Android Java APIs.
I have no idea for a solution as I don't do Webby things. Perhaps someone else can chip in.
 
Upvote 0

boresh

Member
sir thanks for reply,

As you mentioned, found a link at stackoverflow

Download Blob file from Website inside Android WebViewClient

sir but the link gives code to download the blob file, but the code in JAVA language, as i am not familiar with JAVA language.

i search this forums for some code to use java class,

found @ Calling Java Class in this forum found how to call java class, as mentioned by that link i called the java class, but getting error as below

Copying updated assets files (1)
*** Service (starter) Create ***
** Service (starter) Start **
** Activity (main) Create, isFirst = true **
Error occurred on line: 39 (Main)
java.lang.RuntimeException: Constructor not found.
at anywheresoftware.b4j.object.JavaObject.InitializeNewInstance(JavaObject.java:95)
at com.evergreenelectric.main._activity_create(main.java:424)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.shell.Shell.runMethod(Shell.java:732)
at anywheresoftware.b4a.shell.Shell.raiseEventImpl(Shell.java:351)
at anywheresoftware.b4a.shell.Shell.raiseEvent(Shell.java:255)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.ShellBA.raiseEvent2(ShellBA.java:146)
at com.evergreenelectric.main.afterFirstLayout(main.java:128)
at com.evergreenelectric.main.access$000(main.java:40)
at com.evergreenelectric.main$WaitForLayout.run(main.java:106)
at android.os.Handler.handleCallback(Handler.java:938)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loopOnce(Looper.java:226)
at android.os.Looper.loop(Looper.java:313)
at android.app.ActivityThread.main(ActivityThread.java:8663)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:567)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1135)
** Activity (main) Resume **


pleases kindly help to solve the issue
Attached the project for reference

thank in advance
 

Attachments

  • EvergreenElectric.zip
    14.7 KB · Views: 106
Upvote 0

drgottjr

Expert
Licensed User
Longtime User

Attachments

  • capture.png
    capture.png
    6.8 KB · Views: 87
  • tblpartymast.pdf
    13.8 KB · Views: 113
Upvote 0

boresh

Member
happy morning sir,

Yes sir, same (second attachment) to download within webview.

Sir, the project they developed using PHPMaker 2022 and it works fine in browser, Need to download the pdf and excel file using android webview.
sir When you open the web application "https://app.evergreenelectric.in", there are two menus, 1), party list 2) party master. you can find two buttons at top for exporting the list to pdf and excel on both the pages, on clicking the buttons at top, need to download the pdf or excel using webview

Sir app test url is : https://app.evergreenelectric.in
but i dont know in the error it shows : blob:https://app.evergreenelectric.in/3c18e813-abbd-408e-b56d-40625b6b896f

pleases kindly help to solve the issue

thank in advance
 
Upvote 0

boresh

Member
Happy evening sir,

@agraham sir you had already mentioned in the POST #2, that another way has to be found for downloading blob URIs.
For which i tried some JAVA code from google, sir please kindly review my POST #3.

My previous POST #5 is reply for @drgottjr sir, where @drgottjr sir has mentioned, there is an easy way to retrieve it POST #4

what you wanted? (second attachment). there is an easy way to retrieve it, but i'm not going to get into details if it's not what you're after
@drgottjr sir, what i wanted was the same (second attachment), downloading PDF and EXCEL from the site within webview. please kindly guide me with suggestions

Thanks you sir
 
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
i am required to do perform grandfather duties today. i will return with a solution (which i have tried several times to make sure it works) shortly.
 
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
forget this. while mostly germane, it did not show a fully working solution. see a couple posts down for one.

attached please find the project. if you run it and click on the pdf download button, you'll see what it does.
if you select a different page and tap the pdf download button, you'll see what it does, etc.

as was mentioned by @agraham, webview download manager does not support blob url's (or any kind of object url).
the chrome browser does support such downloads. if you have looked at google's documentation regarding webview,
you know that webview is not a browser substitute.

since the webview download manager does not handle blob url's, a workaround is needed. the java
solutions you refer to use such workarounds. it is quite possible they do not work either with webview (any android code
originally written 5 years ago cannot be counted upon to function in today's webview with today's security measures. in
other words, it is unclear under what conditions those workarounds were used.) my solution(s) use features offered by b4a.

i am sorry to say i misspoke when i claimed to have found an easy solution. in the project, you will find several
commented solutions. they were all easy to implement, they run and produce a result; so in that context they were easy
solutions. but there is something missing; it could be on the server side, it could involve a webview setting (there are many),
it could involve cookies, etc. and, of course, i may have coded something incorrectly. if that is the case, i made the same
error in several different programming languages; the code is there. uncomment each demarcated section and run them.
if the case of the blob url, i can download one. the first time, it's correct. the next times, the server provides a blob that is
different from the one it tells me to download.

there are 2 ways to approach the webview download manager problem: intercept the manager or intercept the url. i show
both using some inline java. you can't use both at the same time, because the manager appears to take precedence.
if you want to see how intercepting the url works, you have to comment the download manager code. both solutions result
in an event being raised in b4a. (note: intercepting a url is not the same as overriding a url.) although the event is the same
for either workaround, the action taken in the event is different. if you intercept the download manager, you need to
inject the javascript code which downloads a blob url. if you intercept the url, you download it with okhttp. they both
produce the same result: correct the first time, incorrect thereafter. in other words, even though the server tells you exactly
what to download, if you try to download it, you get a sort of default result (which happens to be correct the first time).

the server generates 2 url's for downloading (1 a blob url, the other, a regular url). you see them clearly in the log. if you
intercept the download manager, you see the blob url. if you intercept a url, you see the other. each requires a different
download method.

intercepting the download manager or intercepting a url involves customizing the webview. this will nullify not only our
webview's behavior but that of any webview library you might be using. this may be an important consideration. for example,
a webview can only have 1 so-called webviewclient (this object does most of webview's background processing). if
i add a webviewclient to intercept a url, it overrides what the library does, as my webviewclient is now the only webviewclient.
since mine only does 1 thing, all the features of the webview library you were using, are ignored.

most webview libraries will set up a webviewclient and will enable intercepting a url. you just need a way of integrating my
code into the library. if the library offers a way of intercepting the download manager, integrate my code. if it doesn't intercept
the manager, then you cannot use my download manager workaround and the library at the same time. one will override the
other (depending on which one you load second).

i can answer some questions. my early success in downloading the table made me believe there would be no issue in subsequent
attempts. i apologize.

note: the website offers a download of all 814 records at one time. it did not work. i tried both in desktop chrome browser and in webview.
there appeared to be some timeout involved. perhaps i am on a slow network...

the issue related to blob url's and why the website chose to employ them merits its own discussion. in any case, i think the real issue pertains to webview.
 

Attachments

  • webview4.zip
    9.5 KB · Views: 92
Last edited:
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
forget the previous. here is a working solution. as suspected, the issue was cookies. without them, you could only get the first page (the first 20 records only).
below find the project and some sample downloads using the various search/request option offered by the website.

note: the java workarounds shown in SO and referred to by you will not work because there are cookies involved. it is not possible to set cookies in the request header of an XMLHttpRequest() (which is what those workarounds use). in principle, the only way to access a blob url in webview is with javascript injection that makes an ajax call, but any attempt to set a cookie request header is immediately denied. if the server did not require cookies when processing attempts to access the blob url, the javascript code shown in my first project works. as a result, i believe the only solution is to download the requested resource before it is converted to a blob url. the attached solution does that. whether the administrators of the website eventually notice my many, many attempts to work around their measures, i can't say. as of today, my solution works.
 

Attachments

  • webview5.zip
    8.8 KB · Views: 138
  • 1pdf.pdf
    31.3 KB · Views: 130
  • 2pdf.pdf
    30.9 KB · Views: 152
  • 3pdf.pdf
    30.2 KB · Views: 100
  • 4pdf.pdf
    30.7 KB · Views: 97
  • 5pdf.pdf
    2.8 KB · Views: 101
Last edited:
Upvote 0
Top