From eb52f8c69043da06cca3faac71af4f5687a9823d Mon Sep 17 00:00:00 2001 From: jim800121chen Date: Sun, 12 Apr 2026 03:45:17 +0800 Subject: [PATCH] =?UTF-8?q?fix(local-tool):=20locateServerBinary=20?= =?UTF-8?q?=E6=89=BE=20{app}\bin\=20=E5=AD=90=E7=9B=AE=E9=8C=84=EF=BC=88Wi?= =?UTF-8?q?ndows/Linux=20installer=20=E4=BD=88=E5=B1=80=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 根因:Windows installer 把 visiona-local-server.exe 裝到 {app}\bin\ (.iss 的 DestDir: "{app}\bin"),但 locateServerBinary 只搜 exeDir\visiona-local-server.exe 和 macOS bundle 專屬路徑, Windows/Linux 打包後的 bin/ 子目錄完全沒被搜尋,導致執行時 "server binary not found" 嚴重錯誤。 修法: - locateServerBinary 第一優先搜 exeDir\bin\visiona-local-server (Inno Setup installer / AppImage 的標準佈局) - 開發模式 fallback 新增 payload//bin/ 候選路徑 - 同時修正 locateBundleBinDir / locateBundledPythonAssets 的開發模式 fallback 寫死 "payload/darwin",改用 runtime.GOOS 動態選 payload 子目錄 Co-Authored-By: Claude Opus 4.6 (1M context) --- local-tool/visiona-local/app.go | 42 ++++++++++++++++++++------------- 1 file changed, 26 insertions(+), 16 deletions(-) diff --git a/local-tool/visiona-local/app.go b/local-tool/visiona-local/app.go index 57bde8b..b31f16e 100644 --- a/local-tool/visiona-local/app.go +++ b/local-tool/visiona-local/app.go @@ -698,12 +698,13 @@ func locateBundledPythonAssets() (tarball, wheelsDir string, err error) { } } - // 2. 開發模式 fallback + // 2. 開發模式 fallback(依 GOOS 挑對應 payload 子目錄) if cwd, e := os.Getwd(); e == nil { + osName := runtime.GOOS // darwin / windows / linux candidates := []struct{ t, w string }{ - {filepath.Join(cwd, "payload", "darwin", "python", "python.tar.gz"), filepath.Join(cwd, "payload", "darwin", "wheels")}, - {filepath.Join(cwd, "..", "payload", "darwin", "python", "python.tar.gz"), filepath.Join(cwd, "..", "payload", "darwin", "wheels")}, - {filepath.Join(cwd, "..", "..", "payload", "darwin", "python", "python.tar.gz"), filepath.Join(cwd, "..", "..", "payload", "darwin", "wheels")}, + {filepath.Join(cwd, "payload", osName, "python", "python.tar.gz"), filepath.Join(cwd, "payload", osName, "wheels")}, + {filepath.Join(cwd, "..", "payload", osName, "python", "python.tar.gz"), filepath.Join(cwd, "..", "payload", osName, "wheels")}, + {filepath.Join(cwd, "..", "..", "payload", osName, "python", "python.tar.gz"), filepath.Join(cwd, "..", "..", "payload", osName, "wheels")}, } for _, c := range candidates { if fileExists(c.t) && dirExists(c.w) { @@ -712,7 +713,7 @@ func locateBundledPythonAssets() (tarball, wheelsDir string, err error) { } } - return "", "", fmt.Errorf("bundled python assets not found (tried .app Resources + payload/darwin)") + return "", "", fmt.Errorf("bundled python assets not found (tried .app Resources + same-dir + payload/%s)", runtime.GOOS) } // locateBundleBinDir 找 bundle 內的 bin 目錄(含 ffmpeg / yt-dlp / visiona-local-server)。 @@ -743,12 +744,13 @@ func locateBundleBinDir() (string, error) { } } - // 開發模式 fallback + // 開發模式 fallback(依 GOOS 挑對應 payload 子目錄) if cwd, err := os.Getwd(); err == nil { + osName := runtime.GOOS // darwin / windows / linux candidates := []string{ - filepath.Join(cwd, "payload", "darwin", "bin"), - filepath.Join(cwd, "..", "payload", "darwin", "bin"), - filepath.Join(cwd, "..", "..", "payload", "darwin", "bin"), + filepath.Join(cwd, "payload", osName, "bin"), + filepath.Join(cwd, "..", "payload", osName, "bin"), + filepath.Join(cwd, "..", "..", "payload", osName, "bin"), } for _, c := range candidates { if dirExists(c) { @@ -1210,10 +1212,12 @@ func oldDataDirCandidates() []string { // locateServerBinary 找 visiona-local-server 執行檔。 // // 搜尋順序: -// 1. 與 Wails app 可執行檔同目錄(打包後的位置) -// 2. macOS app bundle 內:Contents/MacOS/ 或 Contents/Resources/ -// 3. 開發模式:/dist/visiona-local-server(相對 cwd) -// 4. 開發模式:/server/visiona-local-server +// 1. 與 Wails app 可執行檔同目錄下的 bin/(Windows/Linux installer 佈局,Inno Setup .iss 裝到 {app}\bin) +// 2. 與 Wails app 可執行檔同目錄(開發/舊佈局) +// 3. macOS app bundle 內:Contents/Resources/bin 或 Contents/Resources +// 4. 開發模式:/payload//bin/visiona-local-server +// 5. 開發模式:/dist/visiona-local-server +// 6. 開發模式:/server/visiona-local-server func locateServerBinary() (string, error) { binName := "visiona-local-server" if runtime.GOOS == "windows" { @@ -1222,12 +1226,15 @@ func locateServerBinary() (string, error) { candidates := []string{} - // 1. 與 Wails app 同目錄 + // 1-2. 打包後佈局(installer 生成的目錄結構) if exe, err := os.Executable(); err == nil { exeDir := filepath.Dir(exe) + // {app}\bin\visiona-local-server.exe — Windows / Linux installer 標準佈局 + candidates = append(candidates, filepath.Join(exeDir, "bin", binName)) + // {app}\visiona-local-server.exe — exe 跟 server 同目錄的扁平佈局 candidates = append(candidates, filepath.Join(exeDir, binName)) - // 2. macOS app bundle 常見位置 + // 3. macOS app bundle 佈局 if runtime.GOOS == "darwin" { candidates = append(candidates, filepath.Join(exeDir, "..", "Resources", "bin", binName), @@ -1237,9 +1244,12 @@ func locateServerBinary() (string, error) { } } - // 3-4. 開發模式 + // 4-6. 開發模式 if cwd, err := os.Getwd(); err == nil { + osName := runtime.GOOS // darwin / windows / linux candidates = append(candidates, + filepath.Join(cwd, "payload", osName, "bin", binName), + filepath.Join(cwd, "..", "payload", osName, "bin", binName), filepath.Join(cwd, "dist", binName), filepath.Join(cwd, "..", "dist", binName), filepath.Join(cwd, "server", binName),