The app works — until the phone goes offline
Your ZIP ships inside the APK, so your own files are always there. Files your pages load from other servers are not: the Bootstrap stylesheet from jsDelivr, jQuery from cdnjs, the Inter font from Google Fonts. On Wi-Fi nobody notices. On a train, in airplane mode or on a first launch with no signal, the page appears without its styling, the buttons do nothing because the script never arrived, and text falls back to the phone's default font.
The fix is to make those files part of the ZIP. That is tedious by hand — especially for Google Fonts, where the stylesheet you link to is generated per browser and itself points at a dozen font files on another host. This tool does the whole chain.
What it does
- Reads every HTML file and finds
<script src="https://…">and<link rel="stylesheet" href="https://…">tags (protocol-relative//cdn…links too). - Downloads each file into
vendor/<host>/<path>, mirroring the CDN's structure. - For stylesheets, also downloads everything they reference with
url()— icon fonts, web fonts, background images — and follows@import. Google Fonts CSS is saved asvendor/fonts.googleapis.com/<family>.csswith its WOFF2 files beside it. - Rewrites each tag to a relative path, removes the
integrityandcrossoriginattributes (they describe the remote request and are meaningless for a local file), and drops now-uselesspreconnecthints to the font hosts.
What it cannot do automatically
- Hosts that block cross-origin downloads. A browser page can only fetch a file from another site if that site allows it (CORS). cdnjs, jsDelivr, unpkg and Google Fonts all do; some self-hosted CDNs and older font services do not. Those are listed so you can download them manually.
- ES modules from CDNs (
<script type="module" src="https://esm.sh/…">). A module imports more modules by URL at runtime, so a single download is not the whole program. Install the package and let your bundler include it. - Scripts that load other scripts. Analytics tags, chat widgets and ad scripts fetch further code dynamically — and need a connection to be useful anyway. Leave them as they are.
Why not just leave CDN links in?
It is allowed: bundled apps can load https:// resources whenever the phone is online. But an app is judged by how it behaves at its worst moment, and "blank when offline" is the most common one-star review a converted website gets. Localizing costs a few hundred kilobytes; it buys an app that opens instantly, everywhere.