To show a website, you need to fetch html + multiple js/css files.
Does android open connection for each file (URI)?
I'm about to do it (opening connection for each file) and want to know if this is absurdly stupid.
What I want to eventually do is to cache js/css files myself (I'm considering inside shouldInterceptRequest(WebView view, WebResourceRequest request) )
I tried to see how android itself does it by breaking at the shouldInterceptRequest function, but I couldn't find much more info from there.
Does android open connection for each file (URI)?
If you are referring to inside WebView, that will be dictated by the version of WebView that you are using. Keep-alive support (and SPDY/HTTP2) should be supported today; I don't know how far back the SPDY/HTTP2 support would go.
I'm about to do it (opening connection for each file) and want to know if this is absurdly stupid
If you mean that you are going to make HTTP requests yourself outside of WebView, choose an HTTP client API that supports keep-alive and SPDY/HTTP2. Note that keep-alive itself only works on non-SSL connections, and you are using SSL (right? right?!?), so SPDY/HTTP2 support is more critical. OkHttp offers this, to the point where HttpUrlConnection on Android 4.4+ is actually using OkHttp under the covers. Other HTTP client libraries may offer it as well.
Related
I'm developing an Android application, it is like a browser, has a web-view and sends http(s) requests. For debugging purpose, I want to be able to see the requests sent and received by the application (in particular the headers), but I'm unable to do so.
What i tried
I mainly debug the app with Chrome on PC, and use the Network Inspector in Chrome. The problem is that my app uses the ShouldInterceptRequest to intercept the requests an then manually sends a request with cronet. Chrome, in this case, shows some "provisional headers" that are from the original request, an not the headers of the actual request i sent manually.
I tried to use Fiddler and HTTP Toolkit, but the server I'm communicating with, doesn't like the certificate they use, so they can monitor correctly, but, if active, i cannot reach the page i need to monitor.
I also tried the Android Studio network inspector, but seems it work only for HttpURLConnection and Okhttp(1)
Thanks for your time.
If you're using a WebView, set a custom WebViewClient and override shouldInterceptRequest. That will pass in a WebResourceRequest object that will include all headers.
I'm working on a multilayer Android app where I have to intercept HTTP requests, modify one of the headers, execute and return responses. I can't change a way of creating requests, but I can change the API base URL used for requests. The approach I chose was writing a proxy listening on a specific port and doing a man-in-the-middle job:
taking requests,
applying required changes to HTTP requests,
executing it and
returning response.
I applied SparkJava as an HTTP server and OkHttpClient as an HTTP client. It worked like a charm until I found it works only on Android 8 and newer. There is a problem with missing ThreadLocal<S> ThreadLocal.withInitial (Supplier<? extends S> supplier) in API prior to 26 that SparkJava's backend - Jetty, uses).
I guess I will try to look for other HTTP server framework working fine in older API and reimplement my proxy.
In the meantime, does this approach seem to be ok? Or maybe there is another way of proxying HTTP requests in Android app that would allow modifying headers having only an option of changing base API URL?
All ideas much appreciated.
PS. I know that in a typical app this kind of proxying would make a security issue, but this is not a concern in this case.
I did not found an acceptable solution for rewriting all urls referenced in an WebView of an Android-App.
I mean all urls!
Not just those from HTTP-GET Methods. I also need to rewrite urls with HTTP-POST, PUT, DELETE, HEAD methods and urls inside Javascript(with all http methods).
Why I want to do this? I want to make an app, accessing intranet content from outside. Let's say intranet is located on https://myintranet.com
Let's say I have web resources https://myintranet.com/resources/whatever.html. If I am logged in my desktop-machine in the firm I can access the resource directly.
Now we want to go mobile. Therefore we do have a proxy, which supports https and basic authentication. We now accessing a resource with https://myproxy.com/myInternalMapperToIntranet/resources/whatever.html
What did I try:
I tried to set the Web view a WebViewClientoverriding
public WebResourceResponse shouldInterceptRequest (WebView view, String url)
look here Unfortunately this only works for HTTP-GET requests but not for HTTP POST requests.
And a WebViewClient overriding
public boolean shouldOverrideUrlLoading (WebView view, String url)
same thing here, HTTP Posts mapped to a send Button or JavaScript do not provoking a call to one of those methods.
In my case the most easiest way would be, to get the HttpClient of the WebView, and intercepting all requests this urls wants to make and rewriting the url to the one with the Proxy-content.
I simply could define a regex and replace the Url. But it seems, this is not possible in Android. A Collegue did this on a iOS-App, but on Android it seems currently not possible. I found a possible solution #API 21 with:
public WebResourceResponse shouldInterceptRequest (WebView view, WebResourceRequest request)
the WebResourceRequests encapsulates the Http Method, so it smells for the possibility to intercept all httpMethods. Unfortunately I have to support API 17, and may not use this API.
I cant believe that this technical requirement cant be realized with standard android components. Please prove me the opposite!
Does anybody knows alternatives?
Doing the whole rewriting in the back-end for many simultaneous users is currently no alternative. It has to be done client-side on the App due performance issues.
TIA Luke
We have discovered a strange bug in on of our Android apps in that the app cannot connect to the internet over cellular on certain Android Models/Mobile Networks (connecting via WiFi works perfectly). The URL which the app is trying is to reach is however accessible using the device's normal browser, which rules out the URL being blocked upstream. Any ideas what could be causing this would be appreciated please.
which rules out the URL being blocked upstream
Not necessarily. As one of the commenters pointed out, you do not indicate how you are using this URL in your app. If this is an HTTP request, and it works in a browser but not your app, try changing the User-Agent HTTP header of your request to match the one from the browser.
You have provided no error log, but from experience I have run into a few inconsistencies when connecting to a server.
Using HttpsUrlConnection a SNI header is set on HoneyComb and above but not on previous versions, which can alter how the server responds. To add to this there are some general SSL handling inconsistencies between API levels, such as handling of wildcard domains in a certificate is buggy in some api levels.
Second some phones/api levels add a header to HttpUrlConnection requests that specifies time the request was sent like so:
X-Android-Sent-Millis=1353085024868
Some servers seem to use these headers to detect mobile traffic and alter the response.
I had problems when using a dual-simcard. Do you have more devices connected? Try to shut them down.
I have an application with WebView
I tried to load external data via Ajax (Get) but it failed with no errors, tried JSONP and failed with no errors too.
Now here are more info:
When my External Source is an IP-Based like http: //192.168.0......../path/data Things work fine for both JSON and JSONP
but when the external source is a Domain http:// subdomain.mydomain.com Things doesn't work (it never completes loading)
I even tried to specify the JSONP source as
<script src="http://subdomain.mydomain.com/path/?callback=callbackFunc"></script>
but still this script never completes loading
Please notice that the external URL works normally in web-browser and even on my PC (using the JSONP method).
I believe it's either Cross-Domain policy problem which I don't know how to fix.
or a DNS problem (Which I don't know how to fix too).
or there might be a better way for loading external data inside WebView in android
Ok I found the answer to the problem,
The UserAgent of my Android was being blocked on my server for the specified path,
The IP I was using was a network IP, while the domain was another server . .
now it's fixed..