Documentation
¶
Overview ¶
Package backend 负责 brave 桌面壳与后端服务之间的连接。
当前阶段(阶段 1)的策略是「连接已运行的后端」:窗口启动时探测 http://127.0.0.1:<port>,外壳只把前端请求反向代理过去,不负责拉起进程。
后续在同一个包内增加 Start/Stop(sidecar 子进程或库内嵌方式), 对上层(cmd/desktop)与前端暴露的接口保持不变。
Index ¶
Constants ¶
const ( // DefaultPort 是 gobrave 的默认监听端口(见 gobrave/config.yml 的 server 段)。 DefaultPort = 8084 // DefaultHost 是 gobrave 的默认监听地址。 DefaultHost = "127.0.0.1" )
Variables ¶
var ProxyPrefixes = []string{
"/api",
"/health",
"/swagger",
"/docs",
"/audio",
"/images",
"/images-data",
"/brave-api",
"/container",
"/apps",
"/onlyoffice",
"/go-onlyoffice",
"/data-analysis",
"/data-project",
"/c/analysis/apps",
}
ProxyPrefixes 是需要转发到后端(或由后端处理的)路径前缀。
该清单与 gobrave 的 internal/router/router.go 中 mountFrontendStatic 的白名单保持一致:凡是后端负责的路径,桌面外壳都不应该在本地前端资源里找文件。
Functions ¶
func NewHandler ¶
func NewHandler(opts HandlerOptions) http.Handler
NewHandler 返回一个 http.Handler:
- `/wails/*` 交给 Wails 运行时中间件(runtime.js / 绑定调用);
- 命中 ProxyPrefixes 的请求反向代理到后端;
- 其余请求从 Assets 里取静态文件;
- 找不到且看起来像路由(无扩展名)时回退到 index.html,支持 SPA 路由。
Types ¶
type Config ¶
type Config struct {
// Scheme 为 http 或 https。
Scheme string
// Host 为后端主机名或 IP。
Host string
// Port 为后端端口。
Port int
}
Config 描述后端连接参数。
type DevProxy ¶ added in v0.2.1
type DevProxy struct {
// contains filtered or unexported fields
}
DevProxy 是「开发模式」下的小型前置代理。
背景:`-dev-url http://localhost:5174/` 时 WebView 直接加载 Vite dev server, 页面 origin 就是 Vite,而不是我们自己的 http.Server。此时前端发出的 请求会打到 Vite 上,导致两类问题:
- `POST /wails/runtime` → Vite 不认这个路径,404,原生窗口打不开;
- `/api/...`、`/c/analysis/apps/<id>/` 等后端路径 → 要么 404,要么被 Vite 代理到**另一个**后端(vite.config.ts 里写死的 localhost:8084), 而不是本进程内嵌的那个后端。
解决方式:在 Vite 前面再加一层本地代理(本文件),由它按路径分流:
WebView → DevProxy(127.0.0.1:随机端口)
├── /wails/* → Wails transport 中间件
├── /api、/c/analysis/apps/… → 内嵌后端(appHandler)
└── 其余(页面、静态资源、HMR)→ Vite
这样开发模式与生产模式(本地 http.Server)行为一致:后端相关请求始终打到 **本进程内嵌后端**,前端资源与热更新始终来自 Vite。
func StartDevProxy ¶ added in v0.2.1
func StartDevProxy( target string, wailsHandler func(next http.Handler) http.Handler, appHandler http.Handler, ) (*DevProxy, error)
StartDevProxy 启动开发模式代理。
- target 是 Vite 的地址(如 http://localhost:5174/);
- wailsHandler 是 Wails transport 中间件(处理 /wails/*);
- appHandler 是后端 handler,负责静态资源/反代后端/SPA 回退, 与生产模式的本地 http.Server 完全相同,用于服务**后端路径**, 同时在 Vite 不可用时兼作兜底(避免白屏)。
返回的 URL 应当作为 WebView 的加载地址。
func (*DevProxy) URL ¶ added in v0.2.1
URL 返回代理根地址,例如 http://127.0.0.1:41234。
type HandlerOptions ¶
type HandlerOptions struct {
// Assets 是以 index.html 所在目录为根的前端文件系统。
Assets fs.FS
// BackendBaseURL 是反向代理的目标地址,例如 http://127.0.0.1:8084。
BackendBaseURL string
// WailsHandler 是 Wails 运行时的中间件(由 HTTPTransport.Handler() 提供)。
//
// 为什么必须注入:
// Wails v3 的 HTTP transport 只提供「中间件」,它本该挂在 Wails 自己的
// AssetServer 上;而桌面端为了让 POST body / WebSocket 正常工作,WebView
// 加载的是我们自己的本地 http.Server,请求根本不经过 Wails 的 AssetServer。
// 如果不在本地 server 上显式挂载它,`/wails/runtime`、`/wails/runtime.js`
// 会一路穿透到 SPA 回退,前端拿到的是一段 index.html 而不是绑定结果,
// 表现为「调用没有报错但什么也没发生」。
WailsHandler func(next http.Handler) http.Handler
}
HandlerOptions 描述前端静态资源与后端地址。
type LocalServer ¶
type LocalServer struct {
// contains filtered or unexported fields
}
LocalServer 在 127.0.0.1 上启动一个真实 HTTP 服务,供 WebView 加载页面。
为什么不直接用 Wails 的 AssetServer(wails:// 自定义协议): WebKitGTK 的 URI-scheme handler 不会把 POST 请求体传给 handler (见 Wails internal/assetserver/assetserver_webview.go), 导致所有 POST 请求到达后端时 ContentLength=0, 服务端 ShouldBindJSON 读不到数据而返回 EOF。
改用真实 HTTP 端口后,POST/PUT body、SSE、WebSocket 全部走标准 HTTP, 前端也处于正常的 http:// origin 下,行为与浏览器一致。
func StartLocalServer ¶
func StartLocalServer(handler http.Handler) (*LocalServer, error)
StartLocalServer 启动本机 HTTP 服务,返回监听地址(如 http://127.0.0.1:39217)。
type Manager ¶
type Manager struct {
// contains filtered or unexported fields
}
Manager 负责探测后端可用性。
阶段 1 它只是「已运行后端的探针」;后续接入 sidecar 或库内嵌时, 在这里增加 Start/Stop 即可,调用方无需修改。
func (*Manager) SetBaseURL ¶
SetBaseURL 覆盖后端根地址。
桌面端以库方式启动后端时,实际监听端口可能与配置不同 (例如 --port=0 用随机空闲端口),启动后需要回填真实地址。