From 7b1882f2889fc2fd3d86c0a99d15dcda05f7b724 Mon Sep 17 00:00:00 2001 From: wtf911 Date: Sun, 4 May 2025 21:34:27 -0400 Subject: [PATCH 1/2] Added the ability to build the server for Windows --- .gitignore | 4 ++++ .goreleaser.yml | 7 ++++--- Makefile | 16 +++++++++++++++- 3 files changed, 23 insertions(+), 4 deletions(-) diff --git a/.gitignore b/.gitignore index 7cbb52ac..987cd8a5 100644 --- a/.gitignore +++ b/.gitignore @@ -15,3 +15,7 @@ node_modules/ __pycache__ web/dev-dist/ venv/ +.cursorindexingignore +.specstory/ +# SpecStory explanation file +.specstory/.what-is-this.md diff --git a/.goreleaser.yml b/.goreleaser.yml index 062cce1f..22184c28 100644 --- a/.goreleaser.yml +++ b/.goreleaser.yml @@ -52,10 +52,11 @@ builds: id: ntfy_windows_amd64 binary: ntfy env: - - CGO_ENABLED=0 # explicitly disable, since we don't need go-sqlite3 - tags: [noserver] # don't include server files + - CGO_ENABLED=1 # required for go-sqlite3 + - CC=x86_64-w64-mingw32-gcc # apt install gcc-mingw-w64-x86-64 + tags: [sqlite_omit_load_extension,osusergo,netgo] ldflags: - - "-X main.version={{.Version}} -X main.commit={{.Commit}} -X main.date={{.Date}}" + - "-s -w -X main.version={{.Version}} -X main.commit={{.Commit}} -X main.date={{.Date}}" goos: [windows] goarch: [amd64] - diff --git a/Makefile b/Makefile index 4355423e..5d3293fe 100644 --- a/Makefile +++ b/Makefile @@ -31,6 +31,7 @@ help: @echo "Build server & client (without GoReleaser):" @echo " make cli-linux-server - Build client & server (no GoReleaser, current arch, Linux)" @echo " make cli-darwin-server - Build client & server (no GoReleaser, current arch, macOS)" + @echo " make cli-windows-server - Build client & server (no GoReleaser, amd64 only, Windows)" @echo " make cli-client - Build client only (no GoReleaser, current arch, Linux/macOS/Windows)" @echo @echo "Build dev Docker:" @@ -201,6 +202,16 @@ cli-darwin-server: cli-deps-static-sites -ldflags \ "-linkmode=external -s -w -X main.version=$(VERSION) -X main.commit=$(COMMIT) -X main.date=$(shell date +%s)" +cli-windows-server: cli-deps-static-sites + # This is a target to build the CLI (including the server) for Windows. + # Use this for Windows development, if you really don't want to install GoReleaser ... + mkdir -p dist/ntfy_windows_server server/docs + CC=x86_64-w64-mingw32-gcc GOOS=windows GOARCH=amd64 CGO_ENABLED=1 go build \ + -o dist/ntfy_windows_server/ntfy.exe \ + -tags sqlite_omit_load_extension,osusergo,netgo \ + -ldflags \ + "-s -w -X main.version=$(VERSION) -X main.commit=$(COMMIT) -X main.date=$(shell date +%s)" + cli-client: cli-deps-static-sites # This is a target to build the CLI (excluding the server) manually. This should work on Linux/macOS/Windows. # Use this for development, if you really don't want to install GoReleaser ... @@ -213,7 +224,7 @@ cli-client: cli-deps-static-sites cli-deps: cli-deps-static-sites cli-deps-all cli-deps-gcc -cli-deps-gcc: cli-deps-gcc-armv6-armv7 cli-deps-gcc-arm64 +cli-deps-gcc: cli-deps-gcc-armv6-armv7 cli-deps-gcc-arm64 cli-deps-gcc-windows cli-deps-static-sites: mkdir -p server/docs server/site @@ -228,6 +239,9 @@ cli-deps-gcc-armv6-armv7: cli-deps-gcc-arm64: which aarch64-linux-gnu-gcc || { echo "ERROR: ARM64 cross compiler not installed. On Ubuntu, run: apt install gcc-aarch64-linux-gnu"; exit 1; } +cli-deps-gcc-windows: + which x86_64-w64-mingw32-gcc || { echo "ERROR: Windows cross compiler not installed. On Ubuntu, run: apt install gcc-mingw-w64-x86-64"; exit 1; } + cli-deps-update: go get -u go install honnef.co/go/tools/cmd/staticcheck@latest From feb6647f23daad4334e8b08632bfa1462d81773c Mon Sep 17 00:00:00 2001 From: wtf911 Date: Wed, 7 May 2025 00:38:29 -0400 Subject: [PATCH 2/2] Adds the ability to run ntfy as a Windows service. Example service creation command: sc.exe create ntfy start= auto binPath= "YOURPATH\ntfy.exe serve" To use a server.yml file you would create the service like this: sc.exe create ntfy start= auto binPath= "YOURPATH\ntfy.exe serve --config YOURPATH\server.yml" --- cmd/serve_windows.go | 70 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 cmd/serve_windows.go diff --git a/cmd/serve_windows.go b/cmd/serve_windows.go new file mode 100644 index 00000000..201e5c25 --- /dev/null +++ b/cmd/serve_windows.go @@ -0,0 +1,70 @@ +// Copyright 2015 Daniel Theophanes. +// Use of this source code is governed by a zlib-style +// license that can be found at: https://github.com/kardianos/minwinsvc + +//go:build windows && !noserver + +package cmd + +import ( + "os" + "sync" + + "golang.org/x/sys/windows/svc" +) + +var ( + onExit func() + guard sync.Mutex +) + +func init() { + isService, err := svc.IsWindowsService() + if err != nil { + panic(err) + } + if !isService { + return + } + go func() { + _ = svc.Run("", runner{}) + + guard.Lock() + f := onExit + guard.Unlock() + + // Don't hold this lock in user code. + if f != nil { + f() + } + // Make sure we exit. + os.Exit(0) + }() +} + +func setOnExit(f func()) { + guard.Lock() + onExit = f + guard.Unlock() +} + +type runner struct{} + +func (runner) Execute(args []string, r <-chan svc.ChangeRequest, changes chan<- svc.Status) (bool, uint32) { + const cmdsAccepted = svc.AcceptStop | svc.AcceptShutdown + changes <- svc.Status{State: svc.StartPending} + + changes <- svc.Status{State: svc.Running, Accepts: cmdsAccepted} + for { + c := <-r + switch c.Cmd { + case svc.Interrogate: + changes <- c.CurrentStatus + case svc.Stop, svc.Shutdown: + changes <- svc.Status{State: svc.StopPending} + return false, 0 + } + } + + return false, 0 +}