diff --git a/README.md b/README.md index 0eeeb86..366ccf0 100644 --- a/README.md +++ b/README.md @@ -40,7 +40,7 @@ sudo apt install golang gcc libgl1-mesa-dev xorg-dev Windows: ```powershell -.\scripts\build-windows.ps1 +.\scripts\build-windows.bat ``` The binary is written to: @@ -64,8 +64,9 @@ dist/linux/pysentry Linux using Docker: -```powershell -.\scripts\build-linux-docker.ps1 +```bash +chmod +x ./scripts/build-linux-docker.sh +./scripts/build-linux-docker.sh ``` The binary is copied to: @@ -157,11 +158,13 @@ Changing `jobs_dir` saves the current job list to the new directory. ## Project Layout - `cmd/pysentry` starts the desktop app. -- `internal/app` contains the GUI. -- `internal/core` contains YAML storage, command execution, scheduling, and log cleanup. +- `src/gui` contains the GUI. +- `src/core` contains YAML storage, command execution, scheduling, and log cleanup. - `assets` contains app icons. - `scripts` contains build helpers. +Build outputs are written to `dist/`. The old local `bin/` directory is not used. + ## Dependencies PySentry keeps the direct dependency list intentionally small: diff --git a/assets/pysentry-icon.png b/assets/pysentry-icon.png index bcc1ddd..d636b4e 100644 Binary files a/assets/pysentry-icon.png and b/assets/pysentry-icon.png differ diff --git a/assets/pysentry-icon.svg b/assets/pysentry-icon.svg new file mode 100644 index 0000000..7f675d8 --- /dev/null +++ b/assets/pysentry-icon.svg @@ -0,0 +1,8 @@ + + + + + + + + diff --git a/assets/pysentry.ico b/assets/pysentry.ico new file mode 100644 index 0000000..1c5f342 Binary files /dev/null and b/assets/pysentry.ico differ diff --git a/cmd/pysentry/main.go b/cmd/pysentry/main.go index a6dfd26..def4ea4 100644 --- a/cmd/pysentry/main.go +++ b/cmd/pysentry/main.go @@ -1,7 +1,7 @@ package main -import "github.com/pysentry/pysentry/internal/app" +import "github.com/pysentry/pysentry/src/gui" func main() { - app.Run() + gui.Run() } diff --git a/internal/app/assets/pysentry-icon.png b/internal/app/assets/pysentry-icon.png deleted file mode 100644 index bcc1ddd..0000000 Binary files a/internal/app/assets/pysentry-icon.png and /dev/null differ diff --git a/packaging/windows/pysentry.ico b/packaging/windows/pysentry.ico deleted file mode 100644 index 05f02e9..0000000 Binary files a/packaging/windows/pysentry.ico and /dev/null differ diff --git a/packaging/windows/pysentry.rc b/packaging/windows/pysentry.rc index e65ae48..24870b0 100644 --- a/packaging/windows/pysentry.rc +++ b/packaging/windows/pysentry.rc @@ -1 +1 @@ -IDI_ICON1 ICON "packaging/windows/pysentry.ico" +IDI_ICON1 ICON "assets/pysentry.ico" diff --git a/scripts/build-linux-docker.ps1 b/scripts/build-linux-docker.ps1 deleted file mode 100644 index b0bf96b..0000000 --- a/scripts/build-linux-docker.ps1 +++ /dev/null @@ -1,13 +0,0 @@ -param( - [string]$Output = "dist\linux\pysentry" -) - -$ErrorActionPreference = "Stop" - -docker build -f Dockerfile.linux -t pysentry-linux-builder . -$containerId = docker create pysentry-linux-builder -New-Item -ItemType Directory -Force -Path (Split-Path $Output) | Out-Null -docker cp "${containerId}:/out/pysentry" $Output -docker rm $containerId | Out-Null - -Write-Host "Built $Output" diff --git a/scripts/build-linux-docker.sh b/scripts/build-linux-docker.sh new file mode 100644 index 0000000..691e5c8 --- /dev/null +++ b/scripts/build-linux-docker.sh @@ -0,0 +1,14 @@ +#!/usr/bin/env bash +set -euo pipefail + +output="${1:-dist/linux/pysentry}" + +docker build -f Dockerfile.linux -t pysentry-linux-builder . +container_id="$(docker create pysentry-linux-builder)" +mkdir -p "$(dirname "$output")" +docker cp "${container_id}:/out/pysentry" "$output" +docker rm "$container_id" >/dev/null +rm -rf "$(dirname "$output")/assets" +cp -R assets "$(dirname "$output")/assets" + +echo "Built $output" diff --git a/scripts/build-linux.sh b/scripts/build-linux.sh index b71a8df..b3d11a8 100644 --- a/scripts/build-linux.sh +++ b/scripts/build-linux.sh @@ -9,5 +9,7 @@ export GOOS=linux export GOARCH=amd64 go build -trimpath -ldflags "-s -w" -o "$output" ./cmd/pysentry +rm -rf "$(dirname "$output")/assets" +cp -R assets "$(dirname "$output")/assets" echo "Built $output" diff --git a/scripts/build-windows.bat b/scripts/build-windows.bat new file mode 100644 index 0000000..97f4bf5 --- /dev/null +++ b/scripts/build-windows.bat @@ -0,0 +1,29 @@ +@echo off +setlocal enabledelayedexpansion + +set "OUTPUT=%~1" +if "%OUTPUT%"=="" set "OUTPUT=dist\windows\pysentry.exe" + +set "GOEXE=%ProgramFiles%\Go\bin\go.exe" +if not exist "%GOEXE%" set "GOEXE=go" + +if exist "C:\msys64\ucrt64\bin" set "PATH=C:\msys64\ucrt64\bin;%PATH%" + +set "CGO_ENABLED=1" +set "GOOS=windows" +set "GOARCH=amd64" + +for %%I in ("%OUTPUT%") do set "OUTDIR=%%~dpI" +if not exist "%OUTDIR%" mkdir "%OUTDIR%" + +where windres.exe >nul 2>nul +if %ERRORLEVEL%==0 ( + windres.exe -O coff -o cmd\pysentry\rsrc_windows_amd64.syso packaging\windows\pysentry.rc +) + +"%GOEXE%" build -trimpath -ldflags "-s -w" -o "%OUTPUT%" .\cmd\pysentry +if errorlevel 1 exit /b 1 + +xcopy /E /I /Y assets "%OUTDIR%assets" >nul + +echo Built %OUTPUT% diff --git a/scripts/build-windows.ps1 b/scripts/build-windows.ps1 deleted file mode 100644 index 013fe37..0000000 --- a/scripts/build-windows.ps1 +++ /dev/null @@ -1,30 +0,0 @@ -param( - [string]$Output = "dist\windows\pysentry.exe" -) - -$ErrorActionPreference = "Stop" - -$go = "${env:ProgramFiles}\Go\bin\go.exe" -if (-not (Test-Path $go)) { - $go = "go" -} - -$msys2Bin = "C:\msys64\ucrt64\bin" -if (Test-Path $msys2Bin) { - $env:Path = "$msys2Bin;$env:Path" -} - -$env:CGO_ENABLED = "1" -$env:GOOS = "windows" -$env:GOARCH = "amd64" - -New-Item -ItemType Directory -Force -Path (Split-Path $Output) | Out-Null - -$windres = Get-Command windres.exe -ErrorAction SilentlyContinue -if ($windres) { - & $windres.Source -O coff -o .\cmd\pysentry\rsrc_windows_amd64.syso .\packaging\windows\pysentry.rc -} - -& $go build -trimpath -ldflags "-s -w" -o $Output .\cmd\pysentry - -Write-Host "Built $Output" diff --git a/internal/core/model.go b/src/core/model.go similarity index 100% rename from internal/core/model.go rename to src/core/model.go diff --git a/internal/core/paths.go b/src/core/paths.go similarity index 100% rename from internal/core/paths.go rename to src/core/paths.go diff --git a/internal/core/runner.go b/src/core/runner.go similarity index 100% rename from internal/core/runner.go rename to src/core/runner.go diff --git a/internal/core/runner_test.go b/src/core/runner_test.go similarity index 100% rename from internal/core/runner_test.go rename to src/core/runner_test.go diff --git a/internal/core/scheduler.go b/src/core/scheduler.go similarity index 100% rename from internal/core/scheduler.go rename to src/core/scheduler.go diff --git a/internal/core/scheduler_test.go b/src/core/scheduler_test.go similarity index 100% rename from internal/core/scheduler_test.go rename to src/core/scheduler_test.go diff --git a/internal/core/store.go b/src/core/store.go similarity index 100% rename from internal/core/store.go rename to src/core/store.go diff --git a/internal/core/store_test.go b/src/core/store_test.go similarity index 100% rename from internal/core/store_test.go rename to src/core/store_test.go diff --git a/internal/app/app.go b/src/gui/app.go similarity index 96% rename from internal/app/app.go rename to src/gui/app.go index abe8907..9cd88f4 100644 --- a/internal/app/app.go +++ b/src/gui/app.go @@ -1,13 +1,14 @@ -package app +package gui import ( - _ "embed" "fmt" + "os" + "path/filepath" "strconv" "strings" "time" - "github.com/pysentry/pysentry/internal/core" + "github.com/pysentry/pysentry/src/core" "fyne.io/fyne/v2" "fyne.io/fyne/v2/app" @@ -26,9 +27,6 @@ const noFolder = "No folder" type job = core.Job type event = core.RunRecord -//go:embed assets/pysentry-icon.png -var iconBytes []byte - func Run() { a := app.NewWithID(appID) a.SetIcon(loadAppIcon()) @@ -41,7 +39,19 @@ func Run() { } func loadAppIcon() fyne.Resource { - return fyne.NewStaticResource("pysentry-icon.png", iconBytes) + candidates := []string{} + if executable, err := os.Executable(); err == nil { + candidates = append(candidates, filepath.Join(filepath.Dir(executable), "assets", "pysentry-icon.png")) + } + if workingDir, err := os.Getwd(); err == nil { + candidates = append(candidates, filepath.Join(workingDir, "assets", "pysentry-icon.png")) + } + for _, path := range candidates { + if resource, err := fyne.LoadResourceFromPath(path); err == nil { + return resource + } + } + return theme.ComputerIcon() } func configureSystemTray(a fyne.App, w fyne.Window) { @@ -630,10 +640,12 @@ func settingsView(w fyne.Window, store *core.Store, jobs *[]job) fyne.CanvasObje } func chooseFolder(w fyne.Window, target *widget.Entry) { - dialog.ShowFolderOpen(func(uri fyne.ListableURI, err error) { + folderDialog := dialog.NewFolderOpen(func(uri fyne.ListableURI, err error) { if err != nil || uri == nil { return } target.SetText(uri.Path()) }, w) + folderDialog.Resize(fyne.NewSize(900, 640)) + folderDialog.Show() }