Native Windows deployment: config file, service, signed auto-update
- internal/config: .env-style config file (gpu-turnstile.env next to the exe, -config flag or GPU_TURNSTILE_CONFIG); process env overrides file. - internal/service: Windows service via golang.org/x/sys/windows/svc — graceful SCM stop, 'service install/remove' commands, restart-on-failure recovery (also applies staged updates). First external dependency, Windows-only; Linux/Docker build unaffected (go.mod stays at 1.23). - internal/update: polls the Gitea releases API, verifies the Ed25519 signature of the downloaded binary against an embedded public key (openssl-signed by CI), swaps it in next to the running exe, and once the GPU lock is idle exits with code 3 so service recovery restarts onto the new version. Dev builds and empty pubkey never update. - CI: tag builds additionally produce gpu-turnstile.exe + .sig + .sha256 attached to a Gitea release. - LOG_FILE env var so the service has somewhere to log.
This commit is contained in:
@@ -47,6 +47,8 @@ type Config struct {
|
||||
// LogColor enables ANSI colors in per-request log lines. Ignored when
|
||||
// the log level is above INFO (request lines are not emitted at all).
|
||||
LogColor bool
|
||||
// LogWriter receives the colored per-request lines; nil means stderr.
|
||||
LogWriter io.Writer
|
||||
|
||||
LLMWaitTimeout time.Duration
|
||||
UnloadTimeout time.Duration
|
||||
@@ -77,6 +79,7 @@ type Config struct {
|
||||
type Server struct {
|
||||
cfg Config
|
||||
log *slog.Logger
|
||||
logWriter io.Writer
|
||||
freeTimeout time.Duration
|
||||
warmTimeout time.Duration
|
||||
captureLimit int64
|
||||
@@ -136,6 +139,7 @@ func New(cfg Config) (*Server, error) {
|
||||
return &Server{
|
||||
cfg: cfg,
|
||||
log: log,
|
||||
logWriter: cfg.LogWriter,
|
||||
freeTimeout: freeTimeout,
|
||||
warmTimeout: warmTimeout,
|
||||
captureLimit: captureLimit,
|
||||
@@ -338,7 +342,11 @@ func (s *Server) reqLine(log *slog.Logger, code, line string, attrs ...any) {
|
||||
fmt.Fprintf(&sb, " %v=%v", attrs[i], attrs[i+1])
|
||||
}
|
||||
sb.WriteByte('\n')
|
||||
os.Stderr.WriteString(sb.String())
|
||||
w := s.logWriter
|
||||
if w == nil {
|
||||
w = os.Stderr
|
||||
}
|
||||
io.WriteString(w, sb.String())
|
||||
}
|
||||
|
||||
// logRequests logs one line per incoming request and one per completed
|
||||
|
||||
Reference in New Issue
Block a user