3

My Android application is used on customers internal networks, and part of the configuration involves them entering the URL to their web service.

Android from the start seems to be unable to see hostnames inside an internal network so until now I've been suggesting people use their server's IP address. An issue that's come up recently is that a customer has applied SSL to their server meaning the URL is only accessible over https, and the self-signed certificate of course matches the hostname and not the IP address. Requests to the URL via IP address no longer work, whether you specify http or https.

Googling for days suggest either rooting the device and modifying the hosts file, or supplying an internal DNS-over-TLS server, but both of these options are unavailable to me.

It surely cannot be this hard to resolve an internal hostname?

I'm not entirely sure this is a code issue as the problem is reproducible in Chrome, but here is my code:

protected JSONObject doInBackground(String... params) {
            try {
                URL url = new URL("http://officeserver/PTSWeb/PTSCommsServer.asmx");
                HttpURLConnection huc = (HttpURLConnection) url.openConnection();
                HttpURLConnection.setFollowRedirects(false);
                huc.setConnectTimeout(5 * 1000);
                huc.setRequestMethod("GET");
                huc.setRequestProperty("User-Agent", "Mozilla/5.0 (Windows; U; Windows NT 6.0; en-US; rv:1.9.1.2) Gecko/20090729 Firefox/3.5.2 (.NET CLR 3.5.30729)");
                huc.connect(); //FAILS HERE WITH UNABLE TO RESOLVE HOST
                BufferedReader in = new BufferedReader(new InputStreamReader(huc.getInputStream()));
                String result = "";
                StringBuilder total = new StringBuilder();
                for (String line; (line = in.readLine()) != null; ) {
                    total.append(line).append('\n');
                }
                in.close();
                result = total.toString();
                return new JSONObject(result);
            } catch (Exception e) {
                try {
                    JSONObject MyErrorJSON = new JSONObject();
                    MyErrorJSON.accumulate("WasError", "True");
                    MyErrorJSON.accumulate("ResponseText", e.toString());
                    return MyErrorJSON;
                } catch (Exception x) {
                    return null;
                }
            }
        }
Psiloc
  • 257
  • 3
  • 9
  • You should be able to configure the Android device with the details of the DNS service on your customer's network; e.g. https://www.androidpolice.com/2020/03/26/make-android-use-dns-server-choice/ – Stephen C May 21 '21 at 09:34
  • Unfortunately they don't have a DNS-over-TLS compatible server. Or so they tell me – Psiloc May 21 '21 at 09:38
  • Here are some other alternatives: https://android.stackexchange.com/questions/78320. 1) Edit the `/etc/hosts` file. 2) Install a local DNS server on the device itself ... – Stephen C May 21 '21 at 09:45
  • How about install cert on device? – tadev May 21 '21 at 10:36
  • "Android from the start seems to be unable to see hostnames inside an internal network" -- where is this hostname being defined? Is this a real DNS entry on a real DNS server, or is it some Windows-specific thing? "a customer has applied SSL to their server meaning the URL is only accessible over https, and the self-signed certificate of course matches the hostname and not the IP address" -- you will have additional problems then, as Android will reject that certificate, if it is self-signed. – CommonsWare May 21 '21 at 10:49
  • Real DNS entry on real DNS server. But I can recreate the issue in the office with a standard router. Hostname in this sense is just the defined name of the Windows PC, nothing fancy, and Android can't resolve it. – Psiloc May 21 '21 at 12:57
  • @tadev it's not specifically an SSL issue. It's the fact that Android cannot resolve the hostname - which happens to now be a necessity due to the use of SSL – Psiloc May 21 '21 at 13:29
  • Windows names should be resolvable via mDNS. You can find android client libraries that should resolve the name to an IP if you add `.local`. The system itself doesn't want to do that, https://issuetracker.google.com/issues/140786115 - But given an IP, you can still customize the ssl verifier to accept any invalid certificate or even one that matches the hostname you expect (https://stackoverflow.com/a/37046188/995891) – zapl Sep 27 '22 at 15:12

2 Answers2

1

This has received a number of views over the past 12 months so I thought I'd drop my "answer" here in case it's not just me facing this issue.

I've danced around this problem for well over six years now, with it becoming a major headache over the last two. I've concluded that Android is indeed incapable of resolving hostnames on any simple internal network without rooting the device. It can however find servers by IP address or via the fully qualified domain name.

Therefore you (or in my case, my customers) need to reconfigure the SSL certificate to handle requests being sent to the IP address or the FQDN in addition to the hostname. This is done by adding both as a SAN (Subject Alternative Name) to the certificate.

For example:

SAN 1: DNS Name=pts
SAN 2: DNS Name=pts.local
SAN 3: DNS Name=pts.domain.co.uk
SAN 4: IP Address=93.184.216.34
SAN 5: IP Address=2606:2800:220:1:248:1893:25c8:1946

Note the difference between the "DNS Name" and "IP Address" headers. It's conceivable that adding the IP address as a DNS Name may help too in certain edge cases?

Psiloc
  • 257
  • 3
  • 9
  • It's invalid to use a subject alternative name of type DNS with an IP. https://superuser.com/a/1499403 – zapl Sep 27 '22 at 15:18
  • That's definitely strictly true, but I also wouldn't hesitate to do it if I had to. – Psiloc Sep 29 '22 at 11:34
0

You may actually connect over simple http with the ip address, putting this in the manifest permitting the clear text traffic:

<application
        ...
        android:usesCleartextTraffic="true"
        ...>
        ...
    </application>
Phantom Lord
  • 572
  • 3
  • 13