Repository: tauri
Issue: [bug] Can't serve image by asset protocol on Android (500 error)
Labels: type: bug,status: needs triage

### Describe the bug

I can't surface an image from the asset server in an Android application, despite it working on Windows just fine. It's possible I'm missing something as the documentation around this is sparse _at best_, so would appreciate pointers in the right direction as well as how to debug this in the Rust side - I'm not very familiar with Rust but could probably play around a bit.

I'm aware that I could just embed images in the binary as part of the frontend dist, but this is just a basic repro. My actual use case is serving other assets to the webview, including larger videos -- and even though I've seen issues posted in this repo about videos on Linux and such, I didn't find such disclaimers for images, so I expected this to work without issues.

### Reproduction

Should be pretty easy, in 5 mins or so depending on how fast your machine installs dependencies. I've run the repro on Windows, I'm not sure if any part of this is os-dependent though.

Create tauri app using the creator, pick all defaults.

```
npm create tauri-app@latest

> npx
> create-tauri-app

✔ Project name · tauri-app
✔ Identifier · com.tauri-app.app
✔ Choose which language to use for your frontend · TypeScript / JavaScript - (pnpm, yarn, npm, deno, bun)
✔ Choose your package manager · npm
✔ Choose your UI template · Vanilla
✔ Choose your UI flavor · TypeScript
```

Set it up
```
cd tauri-app
npm i
npm run tauri android init
```

Update tauri.conf.json, replace app > security with
```
    "security": {
      "csp": {
        "img-src": "'self' http://asset.localhost blob: data:"
      },
      "assetProtocol": {
        "enable": true,
        "scope": ["**/*"]
      }
    }
```
(intentionally broad scope, to ensure permissions are not a problem)

In bundle, add a new section "resources" like so: 
```
"bundle": {
   (...)
   "resources": {
      "../src/assets/typescript.svg": "ts.svg"
   }
}
```

Edit the `main.ts` file to look like so (removing the greeting code & injecting our ts.svg image from the asset server):
```ts
import { convertFileSrc } from "@tauri-apps/api/core";
import { resolveResource } from '@tauri-apps/api/path';

window.addEventListener("DOMContentLoaded", async () => {
  const img = document.createElement("img");
  img.setAttribute("src", convertFileSrc(await resolveResource('ts.svg')));
  img.setAttribute("width", "100px");
  document.querySelector("#greet-msg")!.appendChild(img);
});
```

Confirm all is good by running the app with `npm run tauri dev` (on Windows). There should be a big TS logo in the bottom of the screen :) - see [attachment](https://github.com/user-attachments/assets/ca688faf-52c6-4a8c-9d1f-a9eca7edf6ad)

Now for the problematic part. Without any changes, run `npm run android dev`, and get... no logo!

![image](https://github.com/user-attachments/assets/dacbc658-a394-4e82-b475-4150bc02647d)

If I hook in with developer tools, I see in the console
```
asset%3A%2F%2Flocalhost%2Fts.svg:1   
       Failed to load resource: the server responded with a status of 500 (Internal Server Error)
```
With response body `No such file or directory (os error 2)`

To be honest, `http://asset.localhost/asset%3A%2F%2Flocalhost%2Fts.svg` _does look_ like the wrong URL. It looks like the old asset:// protocol that I understand is not in use for Android anymore? Only Linux/macOS.

I've tried different variants though, and in all cases I get a 500 and no image
``` 
  img.setAttribute("src", convertFileSrc(await resolveResource('ts.svg')));
  img.setAttribute("src", convertFileSrc(await join(await resourceDir(), 'ts.svg')));
  img.setAttribute("src", convertFileSrc(await join(await appDataDir(), 'ts.svg')));
  img.setAttribute("src", convertFileSrc('ts.svg'));
  img.setAttribute("src", convertFileSrc(await resolveResource('ts.svg')));
  img.setAttribute("src", 'http://asset.localhost/ts.svg');
```

### Expected behavior

I should see the image in Android with the same code that works on Windows. Well, I don't even care about same code, I'd appreciate any pointer on how to make this work.

### Full `tauri info` output

```text
> tauri-app@0.1.0 tauri
> tauri info


[✔] Environment
    - OS: Windows 10.0.26100 x86_64 (X64)
    ✔ WebView2: 131.0.2903.112
    ✔ MSVC: Visual Studio Community 2022
    ✔ rustc: 1.84.0 (9fc6b4312 2025-01-07)
    ✔ cargo: 1.84.0 (66221abde 2024-11-19)
    ✔ rustup: 1.27.1 (54dd3d00f 2024-04-24)
    ✔ Rust toolchain: stable-x86_64-pc-windows-msvc (default)
    - node: 20.18.0
    - npm: 10.8.2

[-] Packages
    - tauri 🦀: 2.2.1
    - tauri-build 🦀: 2.0.5
    - wry 🦀: 0.48.0
    - tao 🦀: 0.31.1
    - @tauri-apps/api : 2.2.0
    - @tauri-apps/cli : 2.2.4

[-] Plugins
    - tauri-plugin-opener 🦀: 2.2.3
    - @tauri-apps/plugin-opener : 2.2.3

[-] App
    - build-type: bundle
    - CSP: img-src 'self' http://asset.localhost blob: data:
    - frontendDist: ../dist
    - devUrl: http://localhost:1420/
    - bundler: Vite
```