Support Windows Builds (#54)

This adds support for windows builds. With it, the app can successfully
run on windows and unix systems. Note that the terminal still only works
on unix systems at this time.
This commit is contained in:
Sylvie Crowe 2024-06-15 14:59:14 -07:00 committed by GitHub
parent 014c6fb2ec
commit d0c4f5c46f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
8 changed files with 58 additions and 32 deletions

View File

@ -32,12 +32,12 @@ tasks:
build:server: build:server:
cmds: cmds:
- go build -o dist/bin/wavesrv cmd/server/main-server.go - go build -o dist/bin/wavesrv{{exeExt}} cmd/server/main-server.go
sources: sources:
- "cmd/server/*.go" - "cmd/server/*.go"
- "pkg/**/*.go" - "pkg/**/*.go"
generates: generates:
- dist/bin/wavesrv - dist/bin/wavesrv{{exeExt}}
deps: deps:
- go:mod:tidy - go:mod:tidy

View File

@ -9,6 +9,7 @@ import (
"log" "log"
"os" "os"
"os/signal" "os/signal"
"runtime" "runtime"
"strconv" "strconv"
"sync" "sync"
@ -80,6 +81,12 @@ func main() {
log.Printf("error acquiring wave lock (another instance of Wave is likely running): %v\n", err) log.Printf("error acquiring wave lock (another instance of Wave is likely running): %v\n", err)
return return
} }
defer func() {
err = waveLock.Unlock()
if err != nil {
log.Printf("error releasing wave lock: %v\n", err)
}
}()
log.Printf("wave home dir: %s\n", wavebase.GetWaveHomeDir()) log.Printf("wave home dir: %s\n", wavebase.GetWaveHomeDir())
err = filestore.InitFilestore() err = filestore.InitFilestore()
@ -105,9 +112,9 @@ func main() {
time.Sleep(30 * time.Millisecond) time.Sleep(30 * time.Millisecond)
pidStr := os.Getenv(ReadySignalPidVarName) pidStr := os.Getenv(ReadySignalPidVarName)
if pidStr != "" { if pidStr != "" {
pid, err := strconv.Atoi(pidStr) _, err := strconv.Atoi(pidStr)
if err == nil { if err == nil {
syscall.Kill(pid, syscall.SIGUSR1) log.Printf("WAVESRV-ESTART\n")
} }
} }
}() }()

View File

@ -7,6 +7,8 @@ import * as path from "path";
import * as readline from "readline"; import * as readline from "readline";
import { debounce } from "throttle-debounce"; import { debounce } from "throttle-debounce";
import * as services from "../frontend/app/store/services"; import * as services from "../frontend/app/store/services";
import os from "os";
import fs from "fs";
const electronApp = electron.app; const electronApp = electron.app;
const isDev = process.env.WAVETERM_DEV; const isDev = process.env.WAVETERM_DEV;
@ -23,6 +25,7 @@ let waveSrvReadyResolve = (value: boolean) => {};
let waveSrvReady: Promise<boolean> = new Promise((resolve, _) => { let waveSrvReady: Promise<boolean> = new Promise((resolve, _) => {
waveSrvReadyResolve = resolve; waveSrvReadyResolve = resolve;
}); });
let waveSrvProc: child_process.ChildProcessWithoutNullStreams | null = null; let waveSrvProc: child_process.ChildProcessWithoutNullStreams | null = null;
electronApp.setName(isDev ? "NextWave (Dev)" : "NextWave"); electronApp.setName(isDev ? "NextWave (Dev)" : "NextWave");
const unamePlatform = process.platform; const unamePlatform = process.platform;
@ -40,7 +43,7 @@ function getBaseHostPort(): string {
// must match golang // must match golang
function getWaveHomeDir() { function getWaveHomeDir() {
return path.join(process.env.HOME, ".w2"); return path.join(os.homedir(), ".w2");
} }
function getElectronAppBasePath(): string { function getElectronAppBasePath(): string {
@ -60,6 +63,11 @@ function getWaveSrvPath(): string {
return path.join(getGoAppBasePath(), "bin", "wavesrv"); return path.join(getGoAppBasePath(), "bin", "wavesrv");
} }
function getWaveSrvPathWin(): string {
const appPath = path.join(getGoAppBasePath(), "bin", "wavesrv.exe");
return `& "${appPath}"`
}
function getWaveSrvCwd(): string { function getWaveSrvCwd(): string {
return getWaveHomeDir(); return getWaveHomeDir();
} }
@ -77,7 +85,12 @@ function runWaveSrv(): Promise<boolean> {
envCopy[WaveDevVarName] = "1"; envCopy[WaveDevVarName] = "1";
} }
envCopy[WaveSrvReadySignalPidVarName] = process.pid.toString(); envCopy[WaveSrvReadySignalPidVarName] = process.pid.toString();
const waveSrvCmd = getWaveSrvPath(); let waveSrvCmd: string;
if (process.platform === "win32") {
waveSrvCmd = getWaveSrvPathWin();
} else {
waveSrvCmd = getWaveSrvPath();
}
console.log("trying to run local server", waveSrvCmd); console.log("trying to run local server", waveSrvCmd);
const proc = child_process.spawn(getWaveSrvPath(), { const proc = child_process.spawn(getWaveSrvPath(), {
cwd: getWaveSrvCwd(), cwd: getWaveSrvCwd(),
@ -108,6 +121,10 @@ function runWaveSrv(): Promise<boolean> {
terminal: false, terminal: false,
}); });
rlStderr.on("line", (line) => { rlStderr.on("line", (line) => {
if (line.includes("WAVESRV-ESTART")) {
waveSrvReadyResolve(true);
return;
}
console.log(line); console.log(line);
}); });
return rtnPromise; return rtnPromise;
@ -232,11 +249,6 @@ electron.ipcMain.on("isDevServer", () => {
return isDevServer; return isDevServer;
}); });
process.on("SIGUSR1", function () {
``;
waveSrvReadyResolve(true);
});
(async () => { (async () => {
const startTs = Date.now(); const startTs = Date.now();
const instanceLock = electronApp.requestSingleInstanceLock(); const instanceLock = electronApp.requestSingleInstanceLock();
@ -245,16 +257,21 @@ process.on("SIGUSR1", function () {
electronApp.quit(); electronApp.quit();
return; return;
} }
const waveHomeDir = getWaveHomeDir();
if (!fs.existsSync(waveHomeDir)) {
fs.mkdirSync(waveHomeDir);
}
try { try {
await runWaveSrv(); await runWaveSrv();
} catch (e) { } catch (e) {
console.log(e.toString()); console.log(e.toString());
} }
console.log("waiting for wavesrv ready signal (SIGUSR1)");
const ready = await waveSrvReady; const ready = await waveSrvReady;
console.log("wavesrv ready signal received", ready, Date.now() - startTs, "ms"); console.log("wavesrv ready signal received", ready, Date.now() - startTs, "ms");
let clientData = await services.ClientService.GetClientData(); console.log("get client data");
let clientData = await services.ClientService.GetClientData().catch(e => console.log(e)) as Client;
console.log("client data ready");
let windowData: WaveWindow = (await services.ObjectService.GetObject( let windowData: WaveWindow = (await services.ObjectService.GetObject(
"window:" + clientData.mainwindowid "window:" + clientData.mainwindowid
)) as WaveWindow; )) as WaveWindow;

3
go.mod
View File

@ -5,6 +5,7 @@ go 1.22
toolchain go1.22.1 toolchain go1.22.1
require ( require (
github.com/alexflint/go-filemutex v1.3.0
github.com/creack/pty v1.1.18 github.com/creack/pty v1.1.18
github.com/golang-migrate/migrate/v4 v4.17.1 github.com/golang-migrate/migrate/v4 v4.17.1
github.com/google/uuid v1.4.0 github.com/google/uuid v1.4.0
@ -17,7 +18,6 @@ require (
github.com/sawka/txwrap v0.2.0 github.com/sawka/txwrap v0.2.0
github.com/spf13/cobra v1.8.0 github.com/spf13/cobra v1.8.0
github.com/wavetermdev/waveterm/wavesrv v0.0.0-20240508181017-d07068c09d94 github.com/wavetermdev/waveterm/wavesrv v0.0.0-20240508181017-d07068c09d94
golang.org/x/sys v0.20.0
golang.org/x/term v0.17.0 golang.org/x/term v0.17.0
) )
@ -29,4 +29,5 @@ require (
github.com/spf13/pflag v1.0.5 // indirect github.com/spf13/pflag v1.0.5 // indirect
github.com/stretchr/testify v1.8.4 // indirect github.com/stretchr/testify v1.8.4 // indirect
go.uber.org/atomic v1.7.0 // indirect go.uber.org/atomic v1.7.0 // indirect
golang.org/x/sys v0.20.0 // indirect
) )

5
go.sum
View File

@ -1,5 +1,7 @@
filippo.io/edwards25519 v1.1.0 h1:FNf4tywRC1HmFuKW5xopWpigGjJKiJSV0Cqo0cJWDaA= filippo.io/edwards25519 v1.1.0 h1:FNf4tywRC1HmFuKW5xopWpigGjJKiJSV0Cqo0cJWDaA=
filippo.io/edwards25519 v1.1.0/go.mod h1:BxyFTGdWcka3PhytdK4V28tE5sGfRvvvRV7EaN4VDT4= filippo.io/edwards25519 v1.1.0/go.mod h1:BxyFTGdWcka3PhytdK4V28tE5sGfRvvvRV7EaN4VDT4=
github.com/alexflint/go-filemutex v1.3.0 h1:LgE+nTUWnQCyRKbpoceKZsPQbs84LivvgwUymZXdOcM=
github.com/alexflint/go-filemutex v1.3.0/go.mod h1:U0+VA/i30mGBlLCrFPGtTe9y6wGQfNAWPBTekHQ+c8A=
github.com/cpuguy83/go-md2man/v2 v2.0.3/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= github.com/cpuguy83/go-md2man/v2 v2.0.3/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o=
github.com/creack/pty v1.1.18 h1:n56/Zwd5o6whRC5PMGretI4IdRLlmBXYNjScPaBgsbY= github.com/creack/pty v1.1.18 h1:n56/Zwd5o6whRC5PMGretI4IdRLlmBXYNjScPaBgsbY=
github.com/creack/pty v1.1.18/go.mod h1:MOBLtS5ELjhRRrroQr9kyvTxUAFNvYEK993ew/Vr4O4= github.com/creack/pty v1.1.18/go.mod h1:MOBLtS5ELjhRRrroQr9kyvTxUAFNvYEK993ew/Vr4O4=
@ -46,16 +48,19 @@ github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA=
github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
github.com/stretchr/testify v1.8.4 h1:CcVxjf3Q8PM0mHUKJCdn+eZZtm5yQwehR5yeSVQQcUk= github.com/stretchr/testify v1.8.4 h1:CcVxjf3Q8PM0mHUKJCdn+eZZtm5yQwehR5yeSVQQcUk=
github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
github.com/wavetermdev/waveterm/wavesrv v0.0.0-20240508181017-d07068c09d94 h1:/SPCxd4KHlS4eRTreYEXWFRr8WfRFBcChlV5cgkaO58= github.com/wavetermdev/waveterm/wavesrv v0.0.0-20240508181017-d07068c09d94 h1:/SPCxd4KHlS4eRTreYEXWFRr8WfRFBcChlV5cgkaO58=
github.com/wavetermdev/waveterm/wavesrv v0.0.0-20240508181017-d07068c09d94/go.mod h1:ywoo7DXdYueQ0tTPhVoB+wzRTgERSE19EA3mR6KGRaI= github.com/wavetermdev/waveterm/wavesrv v0.0.0-20240508181017-d07068c09d94/go.mod h1:ywoo7DXdYueQ0tTPhVoB+wzRTgERSE19EA3mR6KGRaI=
go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw= go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw=
go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
golang.org/x/sys v0.16.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/sys v0.20.0 h1:Od9JTbYCk261bKm4M/mw7AklTlFYIa0bIp9BgSm1S8Y= golang.org/x/sys v0.20.0 h1:Od9JTbYCk261bKm4M/mw7AklTlFYIa0bIp9BgSm1S8Y=
golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/term v0.17.0 h1:mkTF7LCd6WGJNL3K1Ad7kwxNfYAW6a8a8QqtMblp/4U= golang.org/x/term v0.17.0 h1:mkTF7LCd6WGJNL3K1Ad7kwxNfYAW6a8a8QqtMblp/4U=
golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk= golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=

View File

@ -10,7 +10,7 @@ import (
"context" "context"
"fmt" "fmt"
"log" "log"
"path" "path/filepath"
"time" "time"
"github.com/wavetermdev/thenextwave/pkg/util/migrateutil" "github.com/wavetermdev/thenextwave/pkg/util/migrateutil"
@ -51,7 +51,7 @@ func InitFilestore() error {
func GetDBName() string { func GetDBName() string {
waveHome := wavebase.GetWaveHomeDir() waveHome := wavebase.GetWaveHomeDir()
return path.Join(waveHome, FilestoreDBName) return filepath.Join(waveHome, FilestoreDBName)
} }
func MakeDB(ctx context.Context) (*sqlx.DB, error) { func MakeDB(ctx context.Context) (*sqlx.DB, error) {

View File

@ -11,21 +11,19 @@ import (
"log" "log"
"os" "os"
"os/exec" "os/exec"
"path"
"path/filepath" "path/filepath"
"runtime" "runtime"
"strings" "strings"
"sync" "sync"
"time" "time"
"golang.org/x/sys/unix" "github.com/alexflint/go-filemutex"
) )
const WaveVersion = "v0.1.0" const WaveVersion = "v0.1.0"
const DefaultWaveHome = "~/.w2" const DefaultWaveHome = "~/.w2"
const WaveHomeVarName = "WAVETERM_HOME" const WaveHomeVarName = "WAVETERM_HOME"
const WaveDevVarName = "WAVETERM_DEV" const WaveDevVarName = "WAVETERM_DEV"
const HomeVarName = "HOME"
const WaveLockFile = "waveterm.lock" const WaveLockFile = "waveterm.lock"
var baseLock = &sync.Mutex{} var baseLock = &sync.Mutex{}
@ -37,8 +35,8 @@ func IsDevMode() bool {
} }
func GetHomeDir() string { func GetHomeDir() string {
homeVar := os.Getenv(HomeVarName) homeVar, err := os.UserHomeDir()
if homeVar == "" { if err != nil {
return "/" return "/"
} }
return homeVar return homeVar
@ -52,7 +50,7 @@ func ExpandHomeDir(pathStr string) string {
if pathStr == "~" { if pathStr == "~" {
return homeDir return homeDir
} }
return path.Join(homeDir, pathStr[2:]) return filepath.Join(homeDir, pathStr[2:])
} }
func ReplaceHomeDir(pathStr string) string { func ReplaceHomeDir(pathStr string) string {
@ -142,18 +140,16 @@ func DetermineLang() string {
return osLang return osLang
} }
func AcquireWaveLock() (*os.File, error) { func AcquireWaveLock() (*filemutex.FileMutex, error) {
homeDir := GetWaveHomeDir() homeDir := GetWaveHomeDir()
lockFileName := filepath.Join(homeDir, WaveLockFile) lockFileName := filepath.Join(homeDir, WaveLockFile)
log.Printf("[base] acquiring lock on %s\n", lockFileName) log.Printf("[base] acquiring lock on %s\n", lockFileName)
fd, err := os.OpenFile(lockFileName, os.O_RDWR|os.O_CREATE, 0600) m, err := filemutex.New(lockFileName)
if err != nil { if err != nil {
return nil, err return nil, err
} }
err = unix.Flock(int(fd.Fd()), unix.LOCK_EX|unix.LOCK_NB)
if err != nil { err = m.TryLock()
fd.Close() return m, err
return nil, err
}
return fd, nil
} }

View File

@ -7,7 +7,7 @@ import (
"context" "context"
"fmt" "fmt"
"log" "log"
"path" "path/filepath"
"time" "time"
"github.com/jmoiron/sqlx" "github.com/jmoiron/sqlx"
@ -42,7 +42,7 @@ func InitWStore() error {
func GetDBName() string { func GetDBName() string {
waveHome := wavebase.GetWaveHomeDir() waveHome := wavebase.GetWaveHomeDir()
return path.Join(waveHome, WStoreDBName) return filepath.Join(waveHome, WStoreDBName)
} }
func MakeDB(ctx context.Context) (*sqlx.DB, error) { func MakeDB(ctx context.Context) (*sqlx.DB, error) {