What does `<link rel="manifest" href="/manifest.webmanifest">` add to a page beyond the favicon links, and why do sites still ship `<link rel="apple-touch-icon">` alongside it?
answer
- a tab picture versus an app identity
- one link, all the detail elsewhere
- the JSON that names, scopes and starts it
- Apple got there first
- opaque square, platform does the rounding
basics
~20 sThe manifest link points at a JSON file that gives the site an installable identity — name, short_name, icons, start_url, scope, display, background_color and theme_color — instead of just a tab picture. An apple-touch-icon link stays because Safari on iOS reads it for the home-screen icon.
solid answer
~50 sA favicon link answers one question: which picture stands for this page. `<link rel="manifest">` points at a separate JSON document that describes the site as an *application* — `name` and `short_name` for the launcher label, an `icons` array for home-screen and splash surfaces, `start_url` and `scope` for where a launched instance opens and how far it roams, `display` (`standalone`, `minimal-ui`, `browser`, `fullscreen`) for how much browser chrome to keep, and `background_color`/`theme_color` for the launch and chrome colours. It is served as `application/manifest+json` and is usually linked from every page so the browser sees it wherever the user decides to install. You still ship `<link rel="apple-touch-icon" href="/apple-touch-icon.png">` because Safari on iOS has historically taken the home-screen icon from that link rather than the manifest's `icons`; a 180×180 opaque PNG is the standard asset. Note the split: the manifest describes the app, the browser's install machinery and service workers are a separate concern.
code
json · 13 lines{
"name": "KataJob Interview Prep",
"short_name": "KataJob",
"start_url": "/",
"scope": "/",
"display": "standalone",
"background_color": "#0b0b0c",
"theme_color": "#0b0b0c",
"icons": [
{ "src": "/icon-192.png", "sizes": "192x192", "type": "image/png" },
{ "src": "/icon-512.png", "sizes": "512x512", "type": "image/png" }
]
}go deeper
Know the tag is <link rel="manifest" href="...">, that it points at a JSON file, and that the JSON holds the app's name, icons and start URL.
Be ready to name the core members — name, short_name, icons, start_url, scope, display, theme_color — and to explain why apple-touch-icon is still in the head next to the manifest link.
Expect a debugging scenario: a manifest that is fetched but ignored, or an installed app that opens at the wrong path. Reason about the MIME type, the link's presence on every page, and relative-path resolution against the manifest URL.
Own the identity decisions the manifest encodes — what start_url and scope mean for analytics, deep links and auth flows when the app is launched from a home screen rather than a tab.
## Two different jobs Icon links and the manifest link look alike — both are `<link>` elements in `<head>` — but they answer different questions. `<link rel="icon">` says: *here is a small picture for this document.* Its whole vocabulary is a URL, a format and a size. `<link rel="manifest">` says: *here is a description of this site as an installable application.* It carries no information itself beyond the URL; everything lives in the JSON file it points at. ```html <link rel="manifest" href="/manifest.webmanifest"> ``` The file is a plain JSON document served with the `application/manifest+json` MIME type. A server that serves it as `text/plain` or `application/octet-stream` is a common cause of "the browser ignores my manifest". ## What goes in the file ```json { "name": "KataJob Interview Prep", "short_name": "KataJob", "start_url": "/", "scope": "/", "display": "standalone", "background_color": "#0b0b0c", "theme_color": "#0b0b0c", "icons": [ { "src": "/icon-192.png", "sizes": "192x192", "type": "image/png" }, { "src": "/icon-512.png", "sizes": "512x512", "type": "image/png" } ] } ``` The members that matter most in an interview: - **`name` / `short_name`** — the full application name and the truncated one used where space is tight, such as under a home-screen icon. Ship both; a long `name` gets ellipsised badly. - **`icons`** — an array of `{ src, sizes, type }` objects (plus an optional `purpose`). These are the launcher, home-screen and splash-screen icons. 192 and 512 pixel PNGs are the usual minimum pair. - **`start_url`** — the URL a launched instance opens. It does not have to be the page that linked the manifest; a site often installs from a marketing page and starts at `/app`. - **`scope`** — the URL prefix considered "inside" the application. Navigations outside it typically leave the app's own window. - **`display`** — `browser` (a normal tab), `minimal-ui` (a slim chrome), `standalone` (looks like a native app), `fullscreen`. There is also `display_override`, an array letting you express an ordered preference. - **`background_color` / `theme_color`** — the colour painted before the app's own styles are ready, and the colour the OS or browser tints surrounding UI with. ## Where the manifest ends and other topics begin A manifest is a *description*. It does not by itself make a site installable, does not register anything, and does not cache anything — the install machinery and offline behaviour are a separate, runtime concern. Keep that line clean when answering: the markup question is "is the manifest linked, reachable, correctly typed, and does it describe the app accurately". Similarly, `theme_color` as a *manifest member* colours the installed app's chrome. The `<meta name="theme-color">` tag is a separate document-level mechanism with its own rules; do not conflate the two members just because they share a name. ## Why apple-touch-icon survives Safari on iOS established `<link rel="apple-touch-icon">` long before manifests existed, and it has historically taken the home-screen icon from that link rather than from the manifest's `icons` array. That is why every icon generator still emits one and why removing it is the change that makes an iOS home-screen shortcut fall back to a screenshot of the page. The asset conventions: - **180×180 PNG** is the usual size; one is enough. - **Opaque.** iOS composites the icon onto the home screen without preserving alpha the way you might hope, so transparent corners come out dark. Give it a solid background and let the platform apply its own rounding. - **No pre-rounded corners.** The platform masks the icon itself; baking in your own radius produces a double-rounded look. A `sizes` attribute is accepted on the link if you genuinely ship several, but a single 180 asset at a predictable path is the pragmatic default. Note that, like the implicit `/favicon.ico`, Safari has a root-path fallback convention for this asset — but declaring it explicitly is what lets you version the filename. ## Checking your work Three failure modes cover most real bugs: 1. **Wrong MIME type** on the manifest response — the file is fetched and discarded. 2. **Relative paths inside the manifest** resolving against the *manifest's* URL, not the page's. A manifest at `/static/manifest.webmanifest` with `"start_url": "./"` starts at `/static/`, which is almost never intended. Root-relative paths avoid the whole class. 3. **The manifest linked from only one page.** Link it from every page so the browser has the description wherever the user is when they decide to install.
- Why do relative URLs inside a manifest so often produce a wrong start_url?Because members like `start_url`, `scope` and `icons[].src` resolve against the *manifest file's* URL, not against the page that linked it. A manifest served from `/static/` with `"start_url": "./"` launches the app at `/static/`. Using root-relative paths such as `/` and `/icon-512.png` removes the ambiguity entirely.
- What is the difference between `name` and `short_name`, and what happens if you only provide one?`name` is the full application title used where there is room — install prompts, app listings. `short_name` is the compact label for tight surfaces such as under a home-screen icon. With only `name`, a long title gets truncated or ellipsised in those tight spots; with only `short_name`, the fuller surfaces show an abbreviation. Ship both.
- Should every page link the manifest, or is once enough?Link it from every page. The browser reads the manifest from whatever document the user happens to be on when installation is considered, so a manifest linked only from the home page is invisible to a user who landed deep in the site. It is one line in the shared head template and the file is fetched once and cached.
saying these in an interview costs you the question
- Says linking a manifest is what makes a site installable
- Thinks the manifest replaces the favicon links entirely
- Resolves manifest relative paths against the page instead of the manifest URL
- Claims apple-touch-icon is obsolete because manifest icons exist
- Ships a transparent, pre-rounded PNG as the apple-touch-icon