Skip to main content

Start with doctor

mb-local doctor checks every step of the path from your machine and names the one that is broken. Run it before anything else.
Read the first FAIL and ignore the rest. Everything below it usually fails as a consequence. The output contains no keys, tokens, or traffic, so it is safe to paste into a support ticket. Add --json for machine-readable output.

Getting to MobileBoost

The control plane is unreachable

Your machine has no route out to MobileBoost. Ask for outbound TCP 443 to api.mobileboost.io and relay-eu.mobileboost.io, or configure your corporate proxy with --proxy-host.

A corporate proxy is in the way

mb-local reads HTTPS_PROXY and NO_PROXY, and on macOS it reads system settings too. The egress path line tells you what it found. If it found nothing and you know there is a proxy:
If it found one and you need to bypass it:

The proxy asks for a password

Pass credentials:
Kerberos and NTLM proxy authentication are not supported yet. If your proxy requires either, ask for these hosts to be allowed without authentication, or run the tunnel on a host that does not sit behind that proxy.

Your machine uses a PAC file

PAC files are detected but not yet evaluated. Open the PAC file, find the proxy it selects for mobileboost.io, and pass it directly:

TLS inspection is rewriting certificates

Your company decrypts and re-signs outbound TLS. This is not automatically a problem, and a warning alone does not mean the tunnel is broken. It becomes a problem when the inspection also blocks the tunnel’s connection, which shows up as the next failure. If the certificate does not validate at all, install your corporate root CA in the system trust store, or point at it directly:
mb-local also recognises local antivirus products that inspect TLS the same way. If the named product is running on your laptop rather than at the network edge, the fix is local: exclude MobileBoost from its HTTPS scanning.

The connection is refused even though the host is reachable

This pair is the clearest signal there is. Ordinary HTTPS to that exact host works, so the host, the route, the proxy, and TLS are all fine. Something on the path is specifically refusing the tunnel’s connection. This needs a change on your network, and mb-local writes the request for you:
It prints a document that names the appliance it detected, the exact policy feature to change in that product, what MobileBoost does not need, and the evidence from your machine. Send it to whoever manages your network.
The usual resolution is a TLS inspection exception for the MobileBoost hosts. Every major gateway supports one, and it is a routine request: Zscaler calls it Do Not Inspect, Netskope SSL Do Not Decrypt, Palo Alto No Decrypt. The generated document uses the right term for the product it found.
If an exception is not possible, run the tunnel somewhere that is not behind that gateway. A small VM in a DMZ or a container next to your staging environment works, and one shared tunnel there serves everyone. See Run a shared tunnel.

The clock is wrong

Credentials and TLS both fail in confusing ways when a clock drifts. Enable network time sync. Laptops that have been suspended for a long time and CI images with no NTP are the usual causes.

Reaching your own services

Requests are denied

Your status output shows a growing denied count, and your test fails to reach a host you expected to work.
The host is not covered by your rules. Check them:
Remember that *.acme.internal does not match acme.internal itself. Use .acme.internal to cover both. Rules with only IP ranges are another common cause. If you pass --only-hosts '10.0.0.0/8' and your app requests api.internal by name, the name matches no rule, so the request leaves the device normally instead of using the tunnel. Add the hostname alongside the range:

The target is not reachable from your machine either

The tunnel is healthy and the problem is between your machine and your service. A split-tunnel VPN that excludes that subnet is the usual cause. If you cannot curl the service from the machine running mb-local, the tunnel cannot either.

The app ignores the proxy

Some HTTP clients do not use the device’s proxy settings. Flutter’s dart:io HttpClient and Cronet-based stacks are the common ones. Requests from those clients leave the device directly and never enter the tunnel, so they fail to reach internal hosts while the rest of the app works. For Flutter, point the client at the proxy explicitly in test builds:
If you cannot change the app, contact support. Android emulators can be booted with the proxy applied below the app layer, which catches every client.

The key is rejected

Exit code 10 means the key is not recognised. Exit code 15 means the key is valid but was issued without the tunnel:connect scope, so it cannot open tunnels. The second one is fixed by an administrator, not by changing the secret.

localhost does not work

On a device, localhost is the device itself. Point the app at mb-local.net instead, which resolves to 127.0.0.1 and is mapped back to loopback on the machine running the tunnel. If requests then return 400 Bad Request or a host header error, your framework is rejecting the Host: mb-local.net header. Add mb-local.net to its allowed hosts: ALLOWED_HOSTS in Django, config.hosts in Rails.

Some requests work and others do not

If the failing requests are all to the same service, check whether it uses HTTP/3 over QUIC. QUIC does not travel through the tunnel. Most mobile clients fall back to TCP automatically. If yours does not, disable HTTP/3 in test builds.

Tunnel lifecycle

”A tunnel with this name is already connected”

Exit code 13. Another process holds that name, usually a parallel CI job or a tunnel left over from an earlier run.
  • In CI, give every job a unique name. See Give every job a unique tunnel name.
  • Locally, stop the other one with mb-local --daemon stop --tunnel-name NAME, or replace it with --force.
MobileBoost refuses the second connection rather than taking over the first, so a running test is never disconnected by a colleague starting a tunnel.

The tunnel keeps reconnecting

A growing reconnects count in status means the connection is unstable. mb-local reconnects automatically and new requests keep working, but requests already in flight fail when a reconnect happens. Common causes are laptop sleep, Wi-Fi switching, and a VPN that drops. For anything long-running, use a shared tunnel on a stable host.

A run fails immediately with a tunnel error

If the named tunnel is not connected when a run starts, the run fails right away instead of starting and timing out on every request. Check that the tunnel is up with mb-local status, and that the name in your payload matches exactly.

Still stuck

Send support two things:
Neither contains credentials or any of your traffic.