1f487c3163
从 wails/v2 v2.12.0 迁到 v3 v3.0.0-alpha2.117,采用 v3 工程规范:
Go 侧:
- main.go:wails.Run(options.App) → application.New(Options{Services,Assets,Mac})
+ app.Window.NewWithOptions(WebviewWindowOptions) + app.Run();窗口选项照搬
(1440×900/min 1100×700/#0b0d12/Mac TitleBarHiddenInset)
- app.go:App 结构体绑定 → v3 Service(application.NewService);去 startup/ctx 注入;
SaveFileDialog 改 v3 链式 API(application.Get().Dialog.SaveFile().SetFilename().
AddFilter().PromptForSingleSelection());5 个原生方法保留
- go.mod wails/v2→v3、go 1.25
构建:
- wails.json → Taskfile.yml + build/(config.yml 填产品信息 + 各平台配置)
- 删移动端脚手架(ios/android),桌面端只留 darwin/windows/linux
- .gitignore 改为只忽略 build/bin(build/ 构建系统需提交)
前端:
- vite.config 接 @wailsio/runtime/plugins/vite 插件 + WAILS_VITE_PORT
- package.json 加 @wailsio/runtime;wails3 generate bindings → frontend/bindings/
- desktop.ts:window.go.main.App → import { App } from bindings;桌面态检测改
window._wails.environment(原生注入);isMacDesktop 用 System.IsMac()
- version.ts:runtime.BrowserOpenURL → @wailsio/runtime Browser.OpenURL;测试同步更新
- tsconfig 加 allowJs(消费 JSDoc 绑定)
验证进度:Go 编译过 + tsc 干净 + 48 前端测试绿 + 前端 vite build 通过。
**未完成:整体 wails3 build/dev 原生窗口实跑 + 原生能力(另存为/打开/外链)联调**——下次续。
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
99 lines
2.6 KiB
Go
99 lines
2.6 KiB
Go
package main
|
||
|
||
import (
|
||
"fmt"
|
||
"io"
|
||
"net/http"
|
||
"os"
|
||
"os/exec"
|
||
"path/filepath"
|
||
goruntime "runtime"
|
||
|
||
"github.com/wailsapp/wails/v3/pkg/application"
|
||
)
|
||
|
||
// App 经 Wails v3 的 Service 绑定暴露给前端,承载只有桌面端能做的原生能力:
|
||
// 文件读写、系统"另存为"框、用系统默认应用打开、原生通知。
|
||
// v3 中不再需要注入 ctx——对话框经 application.Get().Dialog 获取。
|
||
type App struct{}
|
||
|
||
// Ping 供前端探活 Go 桥是否就绪。
|
||
func (a *App) Ping() string { return "sundynix-desktop ok" }
|
||
|
||
// ReadLocalFile 读取本地文件内容(本地文件系统 I/O)。
|
||
func (a *App) ReadLocalFile(path string) (string, error) {
|
||
b, err := os.ReadFile(path)
|
||
if err != nil {
|
||
return "", err
|
||
}
|
||
return string(b), nil
|
||
}
|
||
|
||
// SaveReportAs 弹原生"另存为"对话框,把 url 指向的报告(.docx)下载到用户选定路径。
|
||
// 返回保存路径;用户取消则返回空串。
|
||
func (a *App) SaveReportAs(url, filename string) (string, error) {
|
||
if filename == "" {
|
||
filename = "report.docx"
|
||
}
|
||
path, err := application.Get().Dialog.SaveFile().
|
||
SetFilename(filename).
|
||
AddFilter("Word 文档 (*.docx)", "*.docx").
|
||
PromptForSingleSelection()
|
||
if err != nil || path == "" {
|
||
return "", err
|
||
}
|
||
if err := download(url, path); err != nil {
|
||
return "", err
|
||
}
|
||
return path, nil
|
||
}
|
||
|
||
// OpenReport 把报告下载到临时目录,并用系统默认应用(Word/Pages/WPS)打开。
|
||
func (a *App) OpenReport(url, filename string) error {
|
||
if filename == "" {
|
||
filename = "report.docx"
|
||
}
|
||
dst := filepath.Join(os.TempDir(), "sundynix-open-"+filename)
|
||
if err := download(url, dst); err != nil {
|
||
return err
|
||
}
|
||
return openInSystem(dst)
|
||
}
|
||
|
||
// Notify 弹一条系统通知(best-effort:macOS 用 osascript,其它平台暂静默)。
|
||
func (a *App) Notify(title, body string) {
|
||
if goruntime.GOOS == "darwin" {
|
||
script := fmt.Sprintf("display notification %q with title %q", body, title)
|
||
_ = exec.Command("osascript", "-e", script).Start()
|
||
}
|
||
}
|
||
|
||
func download(url, dst string) error {
|
||
resp, err := http.Get(url)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
defer resp.Body.Close()
|
||
if resp.StatusCode >= 400 {
|
||
return fmt.Errorf("下载失败 HTTP %d", resp.StatusCode)
|
||
}
|
||
f, err := os.Create(dst)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
defer f.Close()
|
||
_, err = io.Copy(f, resp.Body)
|
||
return err
|
||
}
|
||
|
||
func openInSystem(path string) error {
|
||
switch goruntime.GOOS {
|
||
case "darwin":
|
||
return exec.Command("open", path).Start()
|
||
case "windows":
|
||
return exec.Command("rundll32", "url.dll,FileProtocolHandler", path).Start()
|
||
default:
|
||
return exec.Command("xdg-open", path).Start()
|
||
}
|
||
}
|