Tauri 2 Linux 上 asset://localhost 访问返回 403 避坑指南

很多人在 Tauri v2(尤其是 Linux 系统)中使用 convertFileSrc()asset://localhost 协议加载本地图片、视频、音频等资源时,经常遇到 403 Forbidden 错误。Windows/macOS 可能正常,Linux 却直接翻车。

本文把整个坑的来龙去脉、根本原因、glob 匹配规则彻底讲清楚,并给出最稳的配置方案,帮助大家一次性避坑。

一、问题现象

  • 使用 convertFileSrc(fullPath) 生成的 URL 在 <img><video><audio> 等标签中加载失败

  • 浏览器控制台报 403

  • 终端(Rust 侧)日志提示类似:

    javascript 复制代码
    asset protocol not configured to allow the path: /home/user/.local/share/xxx/xxx.png
  • 尤其容易出现在 隐藏目录 (以 . 开头的目录)下:.local/share.cache.config

二、根本原因:Tauri 的 Glob Scope + Linux 隐藏目录规则

Tauri v2 的 assetProtocol.scope 使用的是 Rust globset 库实现的 glob 模式来做安全校验。只有路径匹配 scope 里的 glob,才允许浏览器通过 asset 协议访问。

最坑的一点在于,Linux(Unix-like 系统)下:

通配符 *?**默认不会匹配以 . 开头的路径 (dotfiles / dotdirs),除非你在 glob 模式里字面写出 .

所以即使你写了最宽松的 "**/*",它也进不了 .local.cache 等隐藏目录,导致 403。

这不是 bug,而是 Tauri 为了安全故意设计的(和 Linux shell 的 ls * 默认不显示隐藏文件一样)。

三、Glob 模式最容易搞混的两个写法:**/ vs **/*

glob 写法 含义 能匹配什么 在 assetProtocol.scope 里的实际效果 推荐程度
**/* 递归匹配所有文件 文件(如 a.pngsub/b.mp4 ✅ 强烈推荐 ★★★★★
**/ 递归匹配所有目录 纯目录路径(如 images/sub/ ❌ 几乎没用(scope 要的是文件路径) ★☆☆☆☆

一句话总结

  • **/* = "递归所有文件"(你 99% 的情况都需要这个)
  • **/ = "递归所有目录"(基本不要单独写在 scope 里)

正确写法是 你的路径/**/* 或直接 **/*

四、正确配置(一步到位)

1. 主配置(推荐同时加 Linux 专属配置)

src-tauri/tauri.conf.json(全局):

json 复制代码
{
  "app": {
    "security": {
      "csp": "default-src 'self' ipc: http://ipc.localhost; img-src 'self' asset: http://asset.localhost; video-src 'self' asset: http://asset.localhost; audio-src 'self' asset: http://asset.localhost; style-src 'self' 'unsafe-inline';",
      "assetProtocol": {
        "enable": true,
        "scope": [
          "**/*",
          "**/.local/share/**/*",
          "**/.cache/**/*",
          "$CACHE/**",
          "$CONFIG/**",
          "$HOME/**"
        ]
      }
    }
  }
}

src-tauri/tauri.linux.conf.json(Linux 专属,强烈建议):

json 复制代码
{
  "app": {
    "security": {
      "assetProtocol": {
        "enable": true,
        "scope": [
          "**/*",
          "**/.local/share/**/*",
          "**/.cache/**/*",
          "$CACHE/**",
          "$CONFIG/**"
        ]
      }
    }
  }
}

这样 Windows/macOS 不会被多余的 scope 影响。

2. 代码侧使用(不变)

ts 复制代码
import { convertFileSrc } from '@tauri-apps/api/core';

const assetUrl = convertFileSrc(absoluteFilePath);

五、操作流程

  1. 按上面修改配置文件
  2. (推荐)cargo clean
  3. pnpm tauri dev(或 npm run tauri dev)测试
  4. 还是 403?看终端日志,把报错里提示的路径对应的 glob 补进去

六、额外避坑小贴士

  • 用 Tauri 内置变量 $CACHE$CONFIG 最香,自动处理平台差异
  • 如果是用户通过 dialog.open() 选择的路径,Tauri 会自动扩展 scope,但持久化路径仍需写进配置
  • 打包进 bundle 的资源不需要 assetProtocol,走 frontendDist 即可
  • Rust 版本建议 ≥ 1.77,Tauri CLI 保持最新

总结

Tauri 2 的 asset 403 坑,99% 是因为 Linux 下 glob 默认不匹配 . 开头的隐藏目录 。只要把 **/* + **/.local/share/**/* + $CACHE/** 写全,问题基本秒解。

把这篇配置直接复制到你的项目里,基本不会再踩这个坑了。

希望这篇文章能帮到更多 Tauri 开发者少走弯路!

如果你还有其他 Tauri v2 的奇葩问题,欢迎继续留言~

相关推荐
卷无止境30 分钟前
C++20 的概念与约束:让模板编程终于"说人话"
后端
Ai拆代码的曹操31 分钟前
一次排查三种连接泄漏模式,再也不怕 HikariCP 连接池爆满了
后端
咪库咪库咪38 分钟前
Cypher入门
后端
纯爱掌门人1 小时前
干了这么多年前端,聊聊 2026 年我们到底还值不值钱
前端·程序员
houhou1 小时前
Monaco Editor 集成指南:从配置到优化
前端
hunterandroid1 小时前
[Android 从零到一] Custom View 自定义绘制:从 onDraw 到完整交互
前端
李明卫杭州1 小时前
Vue3 v-memo 指令详解:让你的列表渲染性能翻倍 🚀
前端
雪隐1 小时前
个人电脑玩AI-08让5060 Ti给你打工——我拿 Unlimited-OCR扫了 600 页书,然后悟了
人工智能·后端
梨子同志1 小时前
Monorepo
前端