Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions .github/dependabot.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
version: 2
updates:
# Maintain GitHub Actions
- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
open-pull-requests-limit: 5
105 changes: 105 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
name: CI

on:
push:
pull_request:

permissions:
contents: read

env:
RELEASEVER: "44"

jobs:
format:
name: Check Nim formatting
runs-on: ubuntu-latest
steps:
- name: Check out repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
submodules: recursive

- name: Install Nim
uses: jiro4989/setup-nim-action@cb1fc1270b117457dd0d9f610ec981fad3369cec # v2.3.0
with:
nim-version: "2.2.10"

- name: Check formatting
run: ./scripts/check-format.sh

build:
name: Build application
runs-on: ubuntu-latest
steps:
- name: Check out repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
submodules: recursive

- name: Install system dependencies
run: |
sudo apt-get update
sudo apt-get install --no-install-recommends -y \
libadwaita-1-dev \
libgtk-4-dev \
pkg-config

- name: Install Nim
uses: jiro4989/setup-nim-action@cb1fc1270b117457dd0d9f610ec981fad3369cec # v2.3.0
with:
nim-version: "2.2.10"

- name: Build
run: nimble build --define:releasever=${RELEASEVER} --verbose

- name: Prepare build artifact
run: |
if [[ ! -x ./umswitch ]]; then
candidate=$(find . "$HOME/.nimble/bin" \
-type f -name umswitch -not -path './umswitch' \
-print -quit 2>/dev/null || true)
if [[ -z "$candidate" ]]; then
echo "umswitch binary was not produced. Build outputs:" >&2
find . "$HOME/.nimble/bin" -maxdepth 4 -type f -print 2>/dev/null | sort >&2
exit 1
fi
cp "$candidate" ./umswitch
fi
test -x ./umswitch
file ./umswitch

- name: Upload binary
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: umswitch
path: umswitch
if-no-files-found: error

test:
name: Compile tests
runs-on: ubuntu-latest
steps:
- name: Check out repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
submodules: recursive

- name: Install Nim
uses: jiro4989/setup-nim-action@cb1fc1270b117457dd0d9f610ec981fad3369cec # v2.3.0
with:
nim-version: "2.2.10"

- name: Install test dependencies
run: |
mkdir -p /tmp/hop-test-deps
printf 'version = "0.0.1"\nauthor = "CI"\ndescription = "CI test dependencies"\nlicense = "MIT"\nrequires "fungus == 0.1.19"\n' > /tmp/hop-test-deps/testdeps.nimble
cd /tmp/hop-test-deps
nimble install -y

- name: Compile test program
run: |
nim c --hints:off \
--path:$HOME/.nimble/pkgs2/fungus-* \
--path:$HOME/.nimble/pkgs2/micros-* \

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what is this

test.nim
23 changes: 23 additions & 0 deletions scripts/check-format.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
#!/usr/bin/env bash
set -euo pipefail

repo_root=$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)
tmp_dir=$(mktemp -d)
trap 'rm -rf "$tmp_dir"' EXIT

status=0
while IFS= read -r -d '' file; do
formatted="$tmp_dir/$(basename "$file")"
nimpretty --out:"$formatted" "$repo_root/$file" >/dev/null
nimpretty "$formatted" >/dev/null
if ! diff -u "$repo_root/$file" "$formatted"; then
status=1
fi
done < <(git -C "$repo_root" ls-files -z -- '*.nim')

if [[ "$status" -ne 0 ]]; then
echo "Formatting check failed. Run nimpretty on the files above." >&2
exit "$status"
fi

echo "All Nim files are formatted."
5 changes: 3 additions & 2 deletions src/backend/add.nim
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,8 @@ const de_to_pkgs_to_add: Table[string, seq[string]] = {
"XFCE": @["@ultramarine-xfce-product-environment"],
}.toTable()

proc add_de_offline*(hub: ref Hub, de: string): Result[void, string] {.thread.} =
proc add_de_offline*(hub: ref Hub, de: string): Result[void,
string] {.thread.} =
?ensure_dnf5()
echo "Downloading packages..."
hub.toMain.send UpdateState.init "Downloading packages..."
Expand All @@ -21,7 +22,7 @@ proc add_de_offline*(hub: ref Hub, de: string): Result[void, string] {.thread.}
let time = now()
var args = @["in", "-y", "--offline"]
args &= pkgs
let process = startProcess("/usr/bin/dnf5", args=args, options = {poStdErrToStdOut})
let process = startProcess("/usr/bin/dnf5", args = args, options = {poStdErrToStdOut})
track_dnf5_download_progress(process, some(hub))
?end_proc(process, time, "Downloading Packages", "arrange offline DE install")
hub.toMain.send MsgToMain DownloadFinish.init
Expand Down
3 changes: 2 additions & 1 deletion src/backend/change.nim
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,8 @@ proc swap*(hub: ref Hub, to: string): Result[void, string] {.thread.} =
echo "├═ New: "&to
stdout.write "┊ "
let time = now()
let process = startProcess("/usr/bin/dnf5", args=["swap", "-y", "ultramarine-release-identity", to], options = {poStdErrToStdOut})
let process = startProcess("/usr/bin/dnf5", args = ["swap", "-y",
"ultramarine-release-identity", to], options = {poStdErrToStdOut})
track_dnf5_download_progress(process, some(hub))
?end_proc(process, time, "Swap Editions", "swap editions")
hub.toMain.send MsgToMain DownloadFinish.init
Expand Down
5 changes: 3 additions & 2 deletions src/backend/delete.nim
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@ const de_to_pkgs_to_rm: Table[string, seq[string]] = {
"XFCE": @["@ultramarine-xfce-product-environment"],
}.toTable()

proc remove_de_offline*(hub: ref Hub, de: string): Result[void, string] {.thread.} =
proc remove_de_offline*(hub: ref Hub, de: string): Result[void,
string] {.thread.} =
?ensure_dnf5()
echo "Removing packages..."
hub.toMain.send UpdateState.init("Running dnf5...")
Expand All @@ -22,7 +23,7 @@ proc remove_de_offline*(hub: ref Hub, de: string): Result[void, string] {.thread
let time = now()
var args = @["rm", "-y", "--offline"]
args &= pkgs
let process = startProcess("/usr/bin/dnf5", args=args, options = {poStdErrToStdOut})
let process = startProcess("/usr/bin/dnf5", args = args, options = {poStdErrToStdOut})
track_dnf5_download_progress(process, none(ref Hub))
?end_proc(process, time, "Remove DE Offline", "arrange offline DE remove")
?reboot_apply_offline hub
Expand Down
8 changes: 5 additions & 3 deletions src/backend/pkgs.nim
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,8 @@ proc ensure_dnf5*(): Result[void, string] =
return err fmt"Fail to install dnf5 ({rc=})"
ok()

proc track_dnf5_download_progress*(process: Process, hub: Option[ref Hub]) {.thread.} =
proc track_dnf5_download_progress*(process: Process, hub: Option[
ref Hub]) {.thread.} =
let outs = process.outputStream
var line = ""
var progress = 0.0
Expand Down Expand Up @@ -76,7 +77,8 @@ proc track_dnf5_download_progress*(process: Process, hub: Option[ref Hub]) {.thr
hub.get.toMain.send Progress.init progress
except: discard

proc end_proc*(process: Process, startTime: DateTime, action: string, errAction: string = ""): Result[void, string] {.thread.} =
proc end_proc*(process: Process, startTime: DateTime, action: string,
errAction: string = ""): Result[void, string] {.thread.} =
defer: process.close()
let errAction = if errAction == "": action else: errAction
let rc = process.peekExitCode
Expand All @@ -90,7 +92,7 @@ proc end_proc*(process: Process, startTime: DateTime, action: string, errAction:
echo "end_proc finished!"
ok()

proc reboot_apply_offline*(hub: ref Hub): Result[void, string] =
proc reboot_apply_offline*(hub: ref Hub): Result[void, string] =
echo "reboot_apply_offline()"
hub.toMain.send UpdateState.init("Rebooting...")
let rc = execCmd("dnf5 offline reboot -y")
Expand Down
4 changes: 2 additions & 2 deletions src/pages/addDownload.nim
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,13 @@ viewable AddDownloadPage:
hub: ref Hub
first: bool = true
progress: float = 0.0

hooks:
afterBuild:
proc redrawer(): bool =
if state.hub[].toMain.peek > 0:
discard redraw state

const KEEP_LISTENER_ACTIVE = true
return KEEP_LISTENER_ACTIVE
discard addGlobalTimeout(200, redrawer)
Expand Down
2 changes: 1 addition & 1 deletion src/pages/changeApply.nim
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ viewable ChangeApplyPage:
proc redrawer(): bool =
if state.hub[].toMain.peek > 0:
discard redraw state

const KEEP_LISTENER_ACTIVE = true
return KEEP_LISTENER_ACTIVE
discard addGlobalTimeout(200, redrawer)
Expand Down
2 changes: 1 addition & 1 deletion src/pages/deleteReboot.nim
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ viewable DeleteRebootPage:
proc redrawer(): bool =
if state.hub[].toMain.peek > 0:
discard redraw state

const KEEP_LISTENER_ACTIVE = true
return KEEP_LISTENER_ACTIVE
discard addGlobalTimeout(200, redrawer)
Expand Down
21 changes: 13 additions & 8 deletions src/umswitch.nim
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import std/[os, osproc, sequtils, envvars, sugar]
import owlkettle, owlkettle/adw
import app
import pages/[action, add, addDownload, delete, deleteReboot, change, changeApply, zNotFound, zError]
import pages/[action, add, addDownload, delete, deleteReboot, change,
changeApply, zNotFound, zError]
import backend/pkgs

const
Expand Down Expand Up @@ -39,21 +40,25 @@ proc main =
# let logfile = open(logfilepath, fmWrite)
# defer: logfile.close()
adw.brew(gui App(
installed_desktops=package_installed(editions.values.toSeq),
installed_identities=package_installed(identities.values.toSeq),
), stylesheets=stylesheets)
installed_desktops = package_installed(editions.values.toSeq),
installed_identities = package_installed(identities.values.toSeq),
), stylesheets = stylesheets)

when isMainModule:
if os.isAdmin():
main()
quit(0)
when usesudo != 0:
quit findExe("sudo").startProcess(args=getAppFilename()&commandLineParams(), options={poParentStreams}).waitForExit
quit findExe("sudo").startProcess(args = getAppFilename()&commandLineParams(
), options = {poParentStreams}).waitForExit
# run umswitch as root via pkexec
discard findExe("xhost").startProcess(args=["si:localuser:root", "+localhost"], options={poParentStreams}).waitForExit
discard findExe("xhost").startProcess(args = ["si:localuser:root",
"+localhost"], options = {poParentStreams}).waitForExit
let envs = collect:
for k, v in envPairs():
k&"="&v
let rc = findExe("pkexec").startProcess(args = @["env"]&envs&getAppFilename()&commandLineParams(), options={poParentStreams}).waitForExit
discard findExe("xhost").startProcess(args=["-si:localuser:root", "-localhost"], options={poParentStreams}).waitForExit
let rc = findExe("pkexec").startProcess(args = @["env"]&envs&getAppFilename(
)&commandLineParams(), options = {poParentStreams}).waitForExit
discard findExe("xhost").startProcess(args = ["-si:localuser:root",
"-localhost"], options = {poParentStreams}).waitForExit
quit rc
10 changes: 7 additions & 3 deletions umswitch.nimble
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,16 @@ bin = @["umswitch"]


import nimsutils/src/nimsutils
import std/[syncio, strutils]
import std/[envvars, syncio, strutils]

proc get_releasever(): int =
let requested = getEnv("RELEASEVER")
if requested != "":
return requested.parseInt
for l in readFile("/etc/os-release").splitLines:
if l.starts_with("VERSION_ID="):
return l[11..12].parseInt
let version = l["VERSION_ID=".len .. ^1].strip(chars = {'"'})
return version.split('.')[0].parseInt
error("cannot find VERSION_ID in /etc/os-release")
quit 1

Expand All @@ -29,4 +33,4 @@ xtask r, "alias for run": setCommand "run"
requires "nim >= 2.0.0"
requires "https://github.com/can-lehmann/owlkettle#HEAD"
requires "fungus"
requires "results == 0.5.0"
requires "results == 0.5.0"