The Webview Endpoint: Reading an Internal API From Webview HTML
The challenge
This screen inside a mobile app is really a web page loaded in a webview. The app calls an internal API from it, but never shows that address on screen. Open View source, find the hidden link to the internal endpoint, and submit it.
What you'll learn
- Understand that many mobile app screens are web pages inside a webview
- Read the HTML source of a webview-rendered screen
- Find a hidden link that points at an internal back-end host
- Extract a full internal API endpoint URL from the source
- Explain why internal endpoints should not ship in client-rendered markup
Skills tested
Prerequisites
- Basic idea of what a mobile app webview is
- Familiarity with URLs and hostnames
How it works
A surprising amount of a mobile app's screens are not native at all - they are web pages loaded inside a webview, a browser component embedded in the app. To the user it looks like part of the app, but under the hood it is HTML, CSS, and JavaScript, and that HTML can be inspected exactly like any website's.
To make these screens work, developers often embed references to the back-end the screen talks to. In this challenge the wallet screen prefetches configuration from an internal host when it loads, and the address is stored as a link set to stay invisible: https://api.acme.example/v1/internal/config. A comment in the source even notes "webview prefetches config from the internal host on load; do not surface to user." The user never sees it on screen, but it is in the page text.
This matters because internal endpoints, especially ones with names like /internal/config, are a strong target for an attacker mapping an app's back-end. Discovering them tells you where the real logic lives. Because a webview is just a browser, anything embedded in its markup is as exposed as it would be on a public website - the native wrapper provides no secrecy.
Common mistakes
- Assuming app screens are opaque. Treating a mobile screen as a native black box when it is really inspectable HTML.
- Reading only the visible links. Noting the add-money and history links but missing the invisible internal one.
- Submitting a partial URL. Dropping the scheme or host and typing only
/internal/configinstead of the full endpoint asked for. - Ignoring the comment. Skipping the source comment that confirms the internal prefetch.
How to defend against it
Treat webview HTML as fully public and keep internal addresses out of it. The screen should talk to the back-end through a layer that does not reveal internal hostnames or routes to the client.
- Do not embed internal API URLs in webview HTML or client JavaScript; resolve them server-side.
- Put internal-only endpoints behind authentication and network controls so a leaked address is not enough to reach them.
- Strip developer comments and unused links from shipped webview pages.
- Front client traffic through a public gateway and keep internal hosts unreachable from the device.