@@ -0,0 +1,70 @@
|
|||||||
|
name: release
|
||||||
|
run-name: Release ${{ github.ref_name }}
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
tags:
|
||||||
|
- "v*"
|
||||||
|
workflow_dispatch:
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
runs-on: [self-hosted, windows]
|
||||||
|
steps:
|
||||||
|
- name: Checkout
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: Ensure toolchain and install cross
|
||||||
|
shell: pwsh
|
||||||
|
run: |
|
||||||
|
rustc -V
|
||||||
|
cargo -V
|
||||||
|
cargo install cross --git https://github.com/cross-rs/cross
|
||||||
|
|
||||||
|
- name: Cache cargo
|
||||||
|
uses: actions/cache@v4
|
||||||
|
with:
|
||||||
|
path: |
|
||||||
|
~/.cargo/registry
|
||||||
|
~/.cargo/git
|
||||||
|
target
|
||||||
|
key: ${{ runner.os }}-cargo-${{ hashFiles('**/Cargo.lock') }}
|
||||||
|
|
||||||
|
- name: Build (armv7-musl)
|
||||||
|
shell: pwsh
|
||||||
|
run: |
|
||||||
|
./scripts/cross_build.ps1 -Release -Targets armv7-unknown-linux-musleabihf
|
||||||
|
|
||||||
|
- name: Package rootfs tarball
|
||||||
|
shell: pwsh
|
||||||
|
run: |
|
||||||
|
./scripts/package_rootfs.ps1 -Version "${{ github.ref_name }}" -Target armv7-unknown-linux-musleabihf
|
||||||
|
|
||||||
|
- name: Upload artifact
|
||||||
|
uses: actions/upload-artifact@v4
|
||||||
|
with:
|
||||||
|
name: wakey-rootfs
|
||||||
|
path: dist/wakey-rootfs-*armv7-unknown-linux-musleabihf.tgz
|
||||||
|
|
||||||
|
- name: Publish Release to Gitea (API)
|
||||||
|
if: startsWith(github.ref, 'refs/tags/')
|
||||||
|
shell: pwsh
|
||||||
|
env:
|
||||||
|
GITEA_TOKEN: ${{ secrets.GITEA_TOKEN }}
|
||||||
|
run: |
|
||||||
|
if (-not $env:GITEA_TOKEN) { throw "Missing secrets.GITEA_TOKEN" }
|
||||||
|
$repoParts = $env:GITHUB_REPOSITORY -split '/'
|
||||||
|
$owner = $repoParts[0]
|
||||||
|
$name = $repoParts[1]
|
||||||
|
$api = $env:GITHUB_API_URL
|
||||||
|
$tag = $env:GITHUB_REF_NAME
|
||||||
|
$asset = Get-ChildItem dist\wakey-rootfs-*armv7-unknown-linux-musleabihf.tgz | Select-Object -First 1
|
||||||
|
if (-not $asset) { throw "No rootfs artifact found in dist" }
|
||||||
|
$headers = @{ Authorization = "token $env:GITEA_TOKEN" }
|
||||||
|
$body = @{ tag_name=$tag; name=$tag; draft=$false; prerelease=$false } | ConvertTo-Json
|
||||||
|
$release = Invoke-RestMethod -Headers $headers -Uri "$api/repos/$owner/$name/releases" -Method Post -Body $body -ContentType 'application/json'
|
||||||
|
$rid = $release.id
|
||||||
|
if (-not $rid) { throw "Failed to create release: $($release | ConvertTo-Json -Depth 5)" }
|
||||||
|
$uploadUri = "$api/repos/$owner/$name/releases/$rid/assets?name=$($asset.Name)"
|
||||||
|
Invoke-WebRequest -Headers $headers -Uri $uploadUri -Method Post -InFile $asset.FullName -ContentType 'application/gzip' | Out-Null
|
||||||
|
Write-Host "Release published: tag $tag with asset $($asset.Name)"
|
||||||
@@ -0,0 +1,106 @@
|
|||||||
|
# Scripts
|
||||||
|
|
||||||
|
This folder contains helper scripts for building, packaging, releasing, and deploying `wakey`.
|
||||||
|
|
||||||
|
## Overview
|
||||||
|
|
||||||
|
- `act_runner.ps1` — Starts your local Gitea runner as a background daemon on Windows.
|
||||||
|
- `cross_build.ps1` — Cross-compiles the project using `cross` for one or more Linux targets.
|
||||||
|
- `package.ps1` — Builds a developer-friendly tarball/zip containing binaries and init scripts.
|
||||||
|
- `package_rootfs.ps1` — Builds a router-ready rootfs tarball that can be installed via `wget | tar`.
|
||||||
|
- `release.ps1` — One-shot helper to cross build and package.
|
||||||
|
- `publish.ps1` — Optional: bump version in Cargo.toml, build, `cargo publish`, and tag the repo.
|
||||||
|
- `init/openwrt/*` — OpenWrt init scripts (procd) to run `wakey` and other helpers.
|
||||||
|
- `systemd/wakey.service` — A basic systemd unit for Linux hosts.
|
||||||
|
|
||||||
|
## act_runner.ps1
|
||||||
|
|
||||||
|
Starts the Gitea `act_runner` if it isn't already running.
|
||||||
|
|
||||||
|
- Default paths assume `~/Documents/gitea/act_runner.exe` and config at `~/Documents/gitea/.runner`.
|
||||||
|
- Usage:
|
||||||
|
|
||||||
|
```powershell
|
||||||
|
./scripts/act_runner.ps1
|
||||||
|
# or specify custom paths
|
||||||
|
./scripts/act_runner.ps1 -RunnerPath "C:/Users/Admin/Documents/gitea/act_runner.exe" -Config "C:/Users/Admin/Documents/gitea/.runner"
|
||||||
|
```
|
||||||
|
|
||||||
|
## cross_build.ps1
|
||||||
|
|
||||||
|
Cross-compile with `cross` for the targets you need.
|
||||||
|
|
||||||
|
- Requires `cross` installed (`cargo install cross`).
|
||||||
|
- Usage:
|
||||||
|
|
||||||
|
```powershell
|
||||||
|
./scripts/cross_build.ps1 -Release -Targets armv7-unknown-linux-musleabihf
|
||||||
|
```
|
||||||
|
|
||||||
|
## package.ps1
|
||||||
|
|
||||||
|
Create a developer bundle with binaries and init scripts. Doesn’t layout files for `/` directly.
|
||||||
|
|
||||||
|
```powershell
|
||||||
|
./scripts/package.ps1 -Version 0.1.0 -Targets armv7-unknown-linux-musleabihf
|
||||||
|
```
|
||||||
|
|
||||||
|
Artifacts in `dist/wakey-<version>.(tgz|zip)`.
|
||||||
|
|
||||||
|
## package_rootfs.ps1
|
||||||
|
|
||||||
|
Create a router-ready rootfs tarball that installs with a one-liner.
|
||||||
|
|
||||||
|
```powershell
|
||||||
|
./scripts/package_rootfs.ps1 -Version 0.1.0 -Target armv7-unknown-linux-musleabihf
|
||||||
|
```
|
||||||
|
|
||||||
|
This writes `dist/wakey-rootfs-<version>-<target>.tgz` containing:
|
||||||
|
|
||||||
|
- `root/.bin/wakey`
|
||||||
|
- `etc/init.d/wakey` (and any other scripts under `scripts/init/openwrt`)
|
||||||
|
|
||||||
|
Install on OpenWrt:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
wget -O- <URL>/wakey-rootfs-<version>-<target>.tgz | tar -xz -C /
|
||||||
|
chmod +x /etc/init.d/wakey
|
||||||
|
/etc/init.d/wakey enable
|
||||||
|
/etc/init.d/wakey start
|
||||||
|
```
|
||||||
|
|
||||||
|
## release.ps1
|
||||||
|
|
||||||
|
One-shot:
|
||||||
|
|
||||||
|
```powershell
|
||||||
|
./scripts/release.ps1 -Version 0.1.0 -Targets armv7-unknown-linux-musleabihf
|
||||||
|
```
|
||||||
|
|
||||||
|
## publish.ps1
|
||||||
|
|
||||||
|
Optional helper to bump the version, build release, publish the crate, and tag the repo.
|
||||||
|
|
||||||
|
```powershell
|
||||||
|
./scripts/publish.ps1 -Version 0.1.0 -Tag
|
||||||
|
```
|
||||||
|
|
||||||
|
- If you’re not publishing to crates.io, the `cargo publish` step will warn and continue.
|
||||||
|
- Uses a simple regex replace to update the `version = "…"` line in `Cargo.toml`.
|
||||||
|
|
||||||
|
## CI workflow (Gitea)
|
||||||
|
|
||||||
|
A workflow in `.gitea/workflows/release.yml` is provided:
|
||||||
|
|
||||||
|
- Triggers on tag pushes (v\*) and manual dispatch.
|
||||||
|
- Builds with `cross` on your self-hosted Windows runner.
|
||||||
|
- Packages a rootfs tarball.
|
||||||
|
- Publishes a Gitea release via API, attaching the tarball (requires `secrets.GITEA_TOKEN`).
|
||||||
|
|
||||||
|
Once published, you can install on the router with:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
wget -O- <release-asset-URL> | tar -xz -C /
|
||||||
|
```
|
||||||
|
|
||||||
|
Adjust paths and targets as needed for your environment.
|
||||||
@@ -0,0 +1,27 @@
|
|||||||
|
# Starts the Gitea act_runner if not already running.
|
||||||
|
# Usage: ./scripts/act_runner.ps1 -Config "C:/Users/Admin/Documents/gitea/.runner" -RunnerPath "C:/Users/Admin/Documents/gitea/act_runner.exe"
|
||||||
|
param(
|
||||||
|
[string]$RunnerPath = "$HOME/Documents/gitea/act_runner.exe",
|
||||||
|
[string]$Config = "$HOME/Documents/gitea/.runner"
|
||||||
|
)
|
||||||
|
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
if (-not (Test-Path $RunnerPath)) {
|
||||||
|
Write-Error "Runner not found at $RunnerPath"
|
||||||
|
}
|
||||||
|
|
||||||
|
$running = Get-Process | Where-Object { $_.Path -eq $RunnerPath } | Select-Object -First 1
|
||||||
|
if ($running) {
|
||||||
|
Write-Host "act_runner already running (PID=$($running.Id))"
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
|
||||||
|
# Ensure config exists
|
||||||
|
if (-not (Test-Path $Config)) {
|
||||||
|
Write-Host "Config not found. Initializing..."
|
||||||
|
& $RunnerPath configure --no-interactive --config $Config
|
||||||
|
}
|
||||||
|
|
||||||
|
Start-Process -FilePath $RunnerPath -ArgumentList @("daemon", "--config", $Config) -WindowStyle Hidden
|
||||||
|
Write-Host "act_runner started."
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
# Build release binaries using cross for Linux targets.
|
||||||
|
# Requires: cross installed (cargo install cross)
|
||||||
|
param(
|
||||||
|
[string[]]$Targets = @("armv7-unknown-linux-musleabihf"),
|
||||||
|
[switch]$Release
|
||||||
|
)
|
||||||
|
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
$mode = if ($Release) { "--release" } else { "" }
|
||||||
|
|
||||||
|
foreach ($t in $Targets) {
|
||||||
|
Write-Host "Building for $t..."
|
||||||
|
cross build $mode --target $t
|
||||||
|
}
|
||||||
|
|
||||||
|
Write-Host "Done."
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
#!/bin/sh /etc/rc.common
|
||||||
|
# Simple helper to update tailscale before its own init runs
|
||||||
|
# Provides: update_tailscale
|
||||||
|
# Required-Start: $network
|
||||||
|
# Required-Stop:
|
||||||
|
# Default-Start: S # earliest boot stage
|
||||||
|
# Default-Stop:
|
||||||
|
# Short-Description: Pre-flight Tailscale update
|
||||||
|
|
||||||
|
START=50 # Run before Tailscale (typically START~80)
|
||||||
|
USE_PROCD=1
|
||||||
|
|
||||||
|
start_service() {
|
||||||
|
procd_open_instance
|
||||||
|
procd_set_param command /etc/ldlda_help/update_tailscale.sh
|
||||||
|
procd_set_param respawn 0 0 0
|
||||||
|
procd_set_param stdout 1
|
||||||
|
procd_set_param stderr 1
|
||||||
|
procd_close_instance
|
||||||
|
}
|
||||||
|
|
||||||
|
stop_service() {
|
||||||
|
: # one-shot
|
||||||
|
}
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
#!/bin/sh /etc/rc.common
|
||||||
|
|
||||||
|
START=66 # Run after the resolvconf swap
|
||||||
|
USE_PROCD=1
|
||||||
|
|
||||||
|
start_service() {
|
||||||
|
procd_open_instance
|
||||||
|
procd_set_param command /etc/ldlda_help/update_wakey.sh
|
||||||
|
procd_set_param respawn 0 0 0
|
||||||
|
procd_set_param stdout 1
|
||||||
|
procd_set_param stderr 1
|
||||||
|
procd_close_instance
|
||||||
|
}
|
||||||
|
|
||||||
|
stop_service() {
|
||||||
|
: # one-shot
|
||||||
|
}
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
#!/bin/sh /etc/rc.common
|
||||||
|
# OpenWrt init script
|
||||||
|
|
||||||
|
START=99
|
||||||
|
USE_PROCD=1
|
||||||
|
|
||||||
|
NAME=wakey
|
||||||
|
BIN=/root/.bin/wakey
|
||||||
|
|
||||||
|
start_service() {
|
||||||
|
procd_open_instance
|
||||||
|
procd_set_param command "$BIN"
|
||||||
|
procd_set_param respawn 5 1 0
|
||||||
|
procd_set_param stdout 1
|
||||||
|
procd_set_param stderr 1
|
||||||
|
procd_close_instance
|
||||||
|
}
|
||||||
|
|
||||||
|
stop_service() {
|
||||||
|
: # procd manages the process; nothing to do here
|
||||||
|
}
|
||||||
@@ -0,0 +1,53 @@
|
|||||||
|
# Package a release tarball with binaries and init scripts.
|
||||||
|
# Usage: ./scripts/package.ps1 -Version 0.1.0 -OutDir dist
|
||||||
|
param(
|
||||||
|
[Parameter(Mandatory = $true)][string]$Version,
|
||||||
|
[string]$OutDir = "dist",
|
||||||
|
[string[]]$Targets = @("armv7-unknown-linux-musleabihf")
|
||||||
|
)
|
||||||
|
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
$root = Split-Path -Parent $MyInvocation.MyCommand.Path | Split-Path -Parent
|
||||||
|
$dist = Join-Path $root $OutDir
|
||||||
|
New-Item -ItemType Directory -Force -Path $dist | Out-Null
|
||||||
|
|
||||||
|
$pkgName = "wakey-$Version"
|
||||||
|
$pkgDir = Join-Path $dist $pkgName
|
||||||
|
Remove-Item -Recurse -Force -ErrorAction SilentlyContinue $pkgDir
|
||||||
|
New-Item -ItemType Directory -Force -Path $pkgDir | Out-Null
|
||||||
|
|
||||||
|
# Copy LICENSE/README if present
|
||||||
|
if (Test-Path "$root/README.md") { Copy-Item "$root/README.md" $pkgDir }
|
||||||
|
if (Test-Path "$root/LICENSE") { Copy-Item "$root/LICENSE" $pkgDir }
|
||||||
|
|
||||||
|
# Binaries per target
|
||||||
|
foreach ($t in $Targets) {
|
||||||
|
$binName = if ($t -like "*-windows-*") { "wakey.exe" } else { "wakey" }
|
||||||
|
$src = Join-Path $root "target/$t/release/$binName"
|
||||||
|
if (-not (Test-Path $src)) { throw "Missing binary: $src" }
|
||||||
|
$tDir = Join-Path $pkgDir "bin/$t"
|
||||||
|
New-Item -ItemType Directory -Force -Path $tDir | Out-Null
|
||||||
|
Copy-Item $src $tDir
|
||||||
|
}
|
||||||
|
|
||||||
|
# Init scripts
|
||||||
|
$initDir = Join-Path $pkgDir "init"
|
||||||
|
New-Item -ItemType Directory -Force -Path $initDir | Out-Null
|
||||||
|
Copy-Item "$root/scripts/init" $initDir -Recurse
|
||||||
|
|
||||||
|
# Systemd service (for Linux hosts)
|
||||||
|
Copy-Item "$root/scripts/systemd" $initDir -Recurse -ErrorAction SilentlyContinue
|
||||||
|
|
||||||
|
# Tarball
|
||||||
|
Push-Location $dist
|
||||||
|
if (Get-Command tar -ErrorAction SilentlyContinue) {
|
||||||
|
tar -czf "$pkgName.tgz" "$pkgName"
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
# Fallback to zip on Windows
|
||||||
|
Compress-Archive -Path "$pkgName" -DestinationPath "$pkgName.zip" -Force
|
||||||
|
}
|
||||||
|
Pop-Location
|
||||||
|
|
||||||
|
Write-Host "Packaged: $dist/$pkgName.(tgz|zip)"
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Build a rootfs tarball suitable for `wget -O- ... | tar -xz -C /` on OpenWrt.
|
||||||
|
# It lays out files as absolute-root paths inside the archive:
|
||||||
|
# root/.bin/wakey
|
||||||
|
# etc/init.d/wakey
|
||||||
|
# Usage: ./scripts/package_rootfs.ps1 -Version 0.1.0 -Target armv7-unknown-linux-musleabihf -OutDir dist
|
||||||
|
param(
|
||||||
|
[Parameter(Mandatory = $true)][string]$Version,
|
||||||
|
[Parameter(Mandatory = $true)][string]$Target,
|
||||||
|
[string]$OutDir = "dist"
|
||||||
|
)
|
||||||
|
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
$root = Split-Path -Parent $MyInvocation.MyCommand.Path | Split-Path -Parent
|
||||||
|
$dist = Join-Path $root $OutDir
|
||||||
|
New-Item -ItemType Directory -Force -Path $dist | Out-Null
|
||||||
|
|
||||||
|
$binName = if ($Target -like "*-windows-*") { "wakey.exe" } else { "wakey" }
|
||||||
|
$binSrc = Join-Path $root "target/$Target/release/$binName"
|
||||||
|
if (-not (Test-Path $binSrc)) { throw "Missing binary: $binSrc (build it first)" }
|
||||||
|
|
||||||
|
$staging = Join-Path $dist ("rootfs-" + [System.Guid]::NewGuid().ToString("N"))
|
||||||
|
New-Item -ItemType Directory -Force -Path $staging | Out-Null
|
||||||
|
|
||||||
|
# Lay out rootfs tree
|
||||||
|
$rootDir = Join-Path $staging "root/.bin"
|
||||||
|
$etcDir = Join-Path $staging "etc/init.d"
|
||||||
|
New-Item -ItemType Directory -Force -Path $rootDir | Out-Null
|
||||||
|
New-Item -ItemType Directory -Force -Path $etcDir | Out-Null
|
||||||
|
|
||||||
|
Copy-Item $binSrc (Join-Path $rootDir "wakey") -Force
|
||||||
|
|
||||||
|
# Copy all OpenWrt init scripts present in repo
|
||||||
|
Get-ChildItem (Join-Path $root 'scripts/init/openwrt') -File | ForEach-Object {
|
||||||
|
$dest = Join-Path $etcDir $_.Name
|
||||||
|
Copy-Item $_.FullName $dest -Force
|
||||||
|
}
|
||||||
|
|
||||||
|
# Create tarball
|
||||||
|
$pkgName = "wakey-rootfs-$Version-$Target.tgz"
|
||||||
|
Push-Location $staging
|
||||||
|
if (Get-Command tar -ErrorAction SilentlyContinue) {
|
||||||
|
tar -czf (Join-Path $dist $pkgName) *
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
# Fallback to zip (router can unzip too if available); prefer tar if possible
|
||||||
|
Compress-Archive -Path * -DestinationPath (Join-Path $dist ($pkgName -replace '\.tgz$', '.zip')) -Force
|
||||||
|
}
|
||||||
|
Pop-Location
|
||||||
|
|
||||||
|
# Cleanup staging
|
||||||
|
Remove-Item -Recurse -Force $staging
|
||||||
|
|
||||||
|
Write-Host "Rootfs package: " (Join-Path $dist $pkgName)
|
||||||
|
Write-Host "On router: wget -O- <URL/$pkgName> | tar -xz -C /"
|
||||||
|
Write-Host "Then: chmod +x /etc/init.d/wakey && /etc/init.d/wakey enable && /etc/init.d/wakey start"
|
||||||
|
Write-Host "For any additional init scripts (e.g., update_tailscale), also chmod +x and enable/start as needed."
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
# Publish to registry and tag
|
||||||
|
# Usage: ./scripts/publish.ps1 -Version 0.1.0 -Tag
|
||||||
|
param(
|
||||||
|
[string]$Version,
|
||||||
|
[switch]$Tag,
|
||||||
|
[switch]$Publish
|
||||||
|
)
|
||||||
|
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
if ($Version) {
|
||||||
|
$pattern = '(?m)^version\s*=\s*"[^"]+"'
|
||||||
|
$replacement = ('version = "{0}"' -f $Version)
|
||||||
|
(Get-Content Cargo.toml -Raw) -replace $pattern, $replacement | Set-Content Cargo.toml -Encoding UTF8
|
||||||
|
}
|
||||||
|
|
||||||
|
# Ensure build ok
|
||||||
|
cargo build --release
|
||||||
|
|
||||||
|
# Publish crate (only if -Publish and registry auth is available)
|
||||||
|
if ($Publish) {
|
||||||
|
$token = $env:CARGO_REGISTRIES_CRATES_IO_TOKEN
|
||||||
|
if (-not $token) { $token = $env:CARGO_REGISTRY_TOKEN }
|
||||||
|
if (-not $token) {
|
||||||
|
Write-Warning "No registry token found (CARGO_REGISTRIES_CRATES_IO_TOKEN or CARGO_REGISTRY_TOKEN). Skipping cargo publish."
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
try {
|
||||||
|
cargo publish
|
||||||
|
}
|
||||||
|
catch {
|
||||||
|
Write-Warning ("cargo publish failed: {0}" -f $_)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($Tag -and $Version) {
|
||||||
|
git tag -f "v$Version"
|
||||||
|
git push -f origin "v$Version"
|
||||||
|
}
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
# One-shot: build with cross, package, and print artifact location.
|
||||||
|
# Usage: ./scripts/release.ps1 -Version 0.1.0 -Targets armv7-unknown-linux-musleabihf
|
||||||
|
param(
|
||||||
|
[Parameter(Mandatory=$true)][string]$Version,
|
||||||
|
[string[]]$Targets = @("armv7-unknown-linux-musleabihf")
|
||||||
|
)
|
||||||
|
|
||||||
|
$ErrorActionPreference = 'Stop'
|
||||||
|
|
||||||
|
./scripts/cross_build.ps1 -Targets $Targets -Release
|
||||||
|
./scripts/package.ps1 -Version $Version -Targets $Targets
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=Wakey WOL+ARP service
|
||||||
|
After=network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
ExecStart=/usr/local/bin/wakey
|
||||||
|
Restart=on-failure
|
||||||
|
RestartSec=2
|
||||||
|
User=wakey
|
||||||
|
Group=wakey
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
@@ -0,0 +1,89 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
# Update/install wakey on OpenWrt by fetching a rootfs tarball and extracting to /
|
||||||
|
# Supports either a direct URL or auto-detecting the latest release from a Gitea instance.
|
||||||
|
#
|
||||||
|
# Env overrides:
|
||||||
|
# WAKEY_TGZ_URL Direct URL to wakey-rootfs-<ver>-<arch>.tgz
|
||||||
|
# WAKEY_HOST Gitea host, e.g. git.ldlda.com
|
||||||
|
# WAKEY_OWNER Repo owner, e.g. lda
|
||||||
|
# WAKEY_REPO Repo name, e.g. wakey
|
||||||
|
# WAKEY_ARCH Target triplet in filename (default: armv7-unknown-linux-musleabihf)
|
||||||
|
# WAKEY_VERSION Tag name (e.g., v0.1.0). If omitted, fetch latest via API.
|
||||||
|
# WAKEY_INSECURE If set (non-empty), pass --no-check-certificate to wget
|
||||||
|
#
|
||||||
|
# Requires: wget (or uclient-fetch), tar
|
||||||
|
|
||||||
|
set -eu
|
||||||
|
|
||||||
|
ARCH=${WAKEY_ARCH:-armv7-unknown-linux-musleabihf}
|
||||||
|
TMPFILE="/tmp/wakey-rootfs.$$.$ARCH.tgz"
|
||||||
|
API_TOKEN="${WAKEY_TOKEN:-}"
|
||||||
|
|
||||||
|
log() { echo "[update_wakey] $*"; }
|
||||||
|
fail() { echo "[update_wakey] ERROR: $*" >&2; exit 1; }
|
||||||
|
|
||||||
|
fetch() {
|
||||||
|
# fetch <url> <out>
|
||||||
|
if command -v uclient-fetch >/dev/null 2>&1; then
|
||||||
|
uclient-fetch -O "$2" "$1" || return 1
|
||||||
|
elif command -v wget >/dev/null 2>&1; then
|
||||||
|
# shellcheck disable=SC2086
|
||||||
|
wget ${WAKEY_INSECURE:+--no-check-certificate} -O "$2" "$1" || return 1
|
||||||
|
else
|
||||||
|
return 2
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
latest_asset_url() {
|
||||||
|
# prints URL to stdout, returns 0 on success
|
||||||
|
HOST=$1 OWNER=$2 REPO=$3 ARCH=$4 TOKEN=$5
|
||||||
|
API="https://$HOST/api/v1/repos/$OWNER/$REPO/releases/latest"
|
||||||
|
if command -v curl >/dev/null 2>&1; then
|
||||||
|
if [ -n "$TOKEN" ]; then
|
||||||
|
RESP=$(curl -fsSL -H "Authorization: token $TOKEN" "$API") || return 1
|
||||||
|
else
|
||||||
|
RESP=$(curl -fsSL "$API") || return 1
|
||||||
|
fi
|
||||||
|
elif command -v wget >/dev/null 2>&1; then
|
||||||
|
# shellcheck disable=SC2086
|
||||||
|
RESP=$(wget ${WAKEY_INSECURE:+--no-check-certificate} -qO- "$API") || return 1
|
||||||
|
else
|
||||||
|
return 2
|
||||||
|
fi
|
||||||
|
# crude parse for browser_download_url matching arch; avoids jq dependency
|
||||||
|
echo "$RESP" | sed -n "s/.*\"browser_download_url\"\s*:\s*\"\([^\"]*${ARCH}\.tgz\)\".*/\1/p" | head -n1
|
||||||
|
}
|
||||||
|
|
||||||
|
main() {
|
||||||
|
URL="${WAKEY_TGZ_URL:-}"
|
||||||
|
if [ -z "$URL" ]; then
|
||||||
|
HOST=${WAKEY_HOST:-git.ldlda.com}
|
||||||
|
OWNER=${WAKEY_OWNER:-lda}
|
||||||
|
REPO=${WAKEY_REPO:-wakey}
|
||||||
|
if [ -n "${WAKEY_VERSION:-}" ]; then
|
||||||
|
FILE="wakey-rootfs-${WAKEY_VERSION}-${ARCH}.tgz"
|
||||||
|
URL="https://$HOST/$OWNER/$REPO/releases/download/${WAKEY_VERSION}/$FILE"
|
||||||
|
else
|
||||||
|
URL=$(latest_asset_url "$HOST" "$OWNER" "$REPO" "$ARCH" "$API_TOKEN") || fail "unable to resolve latest asset URL"
|
||||||
|
[ -n "$URL" ] || fail "no asset URL found for arch $ARCH"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
log "fetching $URL"
|
||||||
|
if ! fetch "$URL" "$TMPFILE"; then
|
||||||
|
fail "download failed"
|
||||||
|
fi
|
||||||
|
|
||||||
|
log "installing"
|
||||||
|
tar -xz -f "$TMPFILE" -C / || fail "extract failed"
|
||||||
|
rm -f "$TMPFILE"
|
||||||
|
|
||||||
|
if [ -f /etc/init.d/wakey ]; then
|
||||||
|
chmod +x /etc/init.d/wakey || true
|
||||||
|
/etc/init.d/wakey enable || true
|
||||||
|
/etc/init.d/wakey restart || /etc/init.d/wakey start || true
|
||||||
|
fi
|
||||||
|
log "done"
|
||||||
|
}
|
||||||
|
|
||||||
|
main "$@"
|
||||||
+1
-1
@@ -1,3 +1,3 @@
|
|||||||
pub const HOME_2: &str = include_str!("../static/home_2");
|
pub const HOME_2: &str = include_str!("../static/home_2.html");
|
||||||
pub const HOME_2_CSS: &str = include_str!("../static/assets/home_2.css");
|
pub const HOME_2_CSS: &str = include_str!("../static/assets/home_2.css");
|
||||||
pub const HOME_2_JS: &str = include_str!("../static/assets/home_2.js");
|
pub const HOME_2_JS: &str = include_str!("../static/assets/home_2.js");
|
||||||
|
|||||||
Reference in New Issue
Block a user