2 Commits

Author SHA1 Message Date
69621c22c7 ci: add Gitea Actions workflow for lint, build, test, and COPR publish
Some checks failed
CI / Format, lint, build, test (push) Failing after 3s
CI / Build SRPM (push) Has been skipped
CI / Publish to COPR (push) Has been skipped
Three-stage pipeline:
- check: cargo fmt/clippy/build/test, frontend builds, desktop/appstream validation
- rpm: generate source + vendor tarballs, build SRPM
- copr: submit SRPM to Fedora COPR (main branch and tags only)

Runs on bare Fedora hosts via act_runner, no containers.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-05 11:01:28 +03:00
f3b8190e68 feat: add RPM spec, systemd service, and COPR packaging
- monsoon.spec: two subpackages (monsoon desktop, monsoon-server
  headless) with vendored deps, desktop/appstream validation, and
  systemd integration
- data/monsoon-server.service: runs as dedicated monsoon user with
  StateDirectory/ConfigurationDirectory/CacheDirectory
- dist.sh: generates source + vendored dependency tarballs for
  offline builds
- .copr/Makefile: SCM integration for automated COPR builds

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-05 08:04:28 +03:00
6 changed files with 268 additions and 0 deletions

5
.copr/Makefile Normal file
View File

@@ -0,0 +1,5 @@
srpm:
./dist.sh
rpmbuild -bs monsoon.spec \
--define "_sourcedir $(CURDIR)" \
--define "_srcrpmdir $(outdir)"

95
.gitea/workflows/ci.yml Normal file
View File

@@ -0,0 +1,95 @@
name: CI
on:
push:
branches: [main]
tags: ['v*']
pull_request:
branches: [main]
jobs:
check:
name: Format, lint, build, test
runs-on: fedora
steps:
- uses: actions/checkout@v4
- name: Check formatting
run: cargo fmt --check --all
- name: Clippy
run: cargo clippy --workspace -- -D warnings
- name: Build (Rust)
run: cargo build --workspace
- name: Test (Rust)
run: cargo test --workspace
- name: Install frontend deps
run: pnpm install --frozen-lockfile
- name: Build desktop frontend
run: pnpm build
- name: Install web frontend deps
run: cd monsoon-web && pnpm install --frozen-lockfile
- name: Build web frontend
run: cd monsoon-web && pnpm build
- name: Validate desktop file
run: desktop-file-validate data/cafe.lair.monsoon.desktop
- name: Validate AppStream metadata
run: appstreamcli validate data/cafe.lair.monsoon.metainfo.xml
rpm:
name: Build SRPM
runs-on: fedora
needs: check
steps:
- uses: actions/checkout@v4
- name: Generate source tarball
run: |
VERSION=$(grep '^version' monsoon-server/Cargo.toml | head -1 | cut -d'"' -f2)
git archive --prefix=monsoon-${VERSION}/ HEAD | gzip > monsoon-${VERSION}.tar.gz
- name: Vendor Rust dependencies
run: |
VERSION=$(grep '^version' monsoon-server/Cargo.toml | head -1 | cut -d'"' -f2)
cargo vendor vendor/
tar czf monsoon-${VERSION}-vendor.tar.gz vendor/
rm -rf vendor/
- name: Build SRPM
run: |
rpmbuild -bs monsoon.spec \
--define "_sourcedir $(pwd)" \
--define "_srcrpmdir $(pwd)"
- name: Upload SRPM artifact
uses: actions/upload-artifact@v3
with:
name: srpm
path: '*.src.rpm'
copr:
name: Publish to COPR
runs-on: fedora
needs: rpm
if: github.ref == 'refs/heads/main' || startsWith(github.ref, 'refs/tags/v')
steps:
- name: Download SRPM
uses: actions/download-artifact@v3
with:
name: srpm
- name: Configure copr-cli
run: |
mkdir -p ~/.config
echo "${{ secrets.COPR_CONFIG }}" > ~/.config/copr
- name: Submit build to COPR
run: copr-cli build monsoon *.src.rpm

3
.gitignore vendored
View File

@@ -1,5 +1,8 @@
/target /target
/dist /dist
/node_modules /node_modules
/vendor
*.tar.gz
*.src.rpm
*.log *.log
.env .env

View File

@@ -0,0 +1,17 @@
[Unit]
Description=Monsoon BitTorrent Server
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
ExecStart=/usr/bin/monsoon-server
User=monsoon
Group=monsoon
Environment=MONSOON_WEB_DIR=/usr/share/monsoon/web
StateDirectory=monsoon
ConfigurationDirectory=monsoon
CacheDirectory=monsoon
[Install]
WantedBy=multi-user.target

23
dist.sh Executable file
View File

@@ -0,0 +1,23 @@
#!/bin/bash
set -e
VERSION=$(grep '^version' monsoon-server/Cargo.toml | head -1 | cut -d'"' -f2)
NAME=monsoon
echo "Packaging ${NAME}-${VERSION}..."
# Source tarball from git
git archive --prefix=${NAME}-${VERSION}/ HEAD | gzip > ${NAME}-${VERSION}.tar.gz
echo " Created ${NAME}-${VERSION}.tar.gz"
# Vendored Rust dependencies (includes git deps like vortex)
cargo vendor vendor/
tar czf ${NAME}-${VERSION}-vendor.tar.gz vendor/
rm -rf vendor/
echo " Created ${NAME}-${VERSION}-vendor.tar.gz"
echo ""
echo "To build SRPM:"
echo " rpmbuild -bs ${NAME}.spec \\"
echo " --define \"_sourcedir \$(pwd)\" \\"
echo " --define \"_srcrpmdir \$(pwd)\""

125
monsoon.spec Normal file
View File

@@ -0,0 +1,125 @@
Name: monsoon
Version: 0.1.0
Release: 1%{?dist}
Summary: A fast BitTorrent client powered by io-uring
License: GPL-3.0-or-later
URL: https://git.lair.cafe/monsoon/monsoon
Source0: %{name}-%{version}.tar.gz
Source1: %{name}-%{version}-vendor.tar.gz
ExclusiveArch: x86_64
BuildRequires: rust >= 1.85
BuildRequires: cargo
BuildRequires: gcc
BuildRequires: webkit2gtk4.1-devel
BuildRequires: gtk3-devel
BuildRequires: libsoup3-devel
BuildRequires: pango-devel
BuildRequires: gdk-pixbuf2-devel
BuildRequires: glib2-devel
BuildRequires: libappindicator-gtk3-devel
BuildRequires: nodejs
BuildRequires: pnpm
BuildRequires: desktop-file-utils
BuildRequires: libappstream-glib
BuildRequires: systemd-rpm-macros
%description
Monsoon is a modern BitTorrent client for the GNOME desktop,
built on the high-performance Vortex bittorrent engine which uses
Linux io-uring for efficient I/O. It supports magnet links,
DHT peer discovery, and simultaneous multi-torrent management.
%package server
Summary: Monsoon headless BitTorrent server with REST API
Requires(pre): shadow-utils
%description server
Headless BitTorrent daemon with REST API, WebSocket event streaming,
and web GUI for remote torrent management. Designed for deployment
on LAN servers to offload torrent downloading with completion
notifications for post-download automation.
%prep
%autosetup
tar xf %{SOURCE1}
mkdir -p .cargo
cat > .cargo/config.toml << 'EOF'
[source.crates-io]
replace-with = "vendored-sources"
[source."git+https://github.com/grenade/vortex.git?branch=fix-double-panic"]
git = "https://github.com/grenade/vortex.git"
branch = "fix-double-panic"
replace-with = "vendored-sources"
[source.vendored-sources]
directory = "vendor"
EOF
%build
# Build web GUI for server
cd monsoon-web && pnpm install --offline && pnpm build && cd ..
# Build server binary
cargo build --release -p monsoon-server
# Build desktop frontend
pnpm install --offline
pnpm build
# Build desktop binary (reads frontend from dist/)
cargo build --release -p monsoon
%install
# Desktop app
install -Dm755 target/release/monsoon %{buildroot}%{_bindir}/monsoon
install -Dm644 data/cafe.lair.monsoon.desktop %{buildroot}%{_datadir}/applications/cafe.lair.monsoon.desktop
install -Dm644 data/cafe.lair.monsoon.metainfo.xml %{buildroot}%{_metainfodir}/cafe.lair.monsoon.metainfo.xml
install -Dm644 src-tauri/icons/icon.png %{buildroot}%{_datadir}/icons/hicolor/256x256/apps/cafe.lair.monsoon.png
install -Dm644 src-tauri/icons/128x128.png %{buildroot}%{_datadir}/icons/hicolor/128x128/apps/cafe.lair.monsoon.png
install -Dm644 src-tauri/icons/32x32.png %{buildroot}%{_datadir}/icons/hicolor/32x32/apps/cafe.lair.monsoon.png
# Server
install -Dm755 target/release/monsoon-server %{buildroot}%{_bindir}/monsoon-server
install -Dm644 data/monsoon-server.service %{buildroot}%{_unitdir}/monsoon-server.service
install -dm755 %{buildroot}%{_datadir}/monsoon/web
cp -r monsoon-web/dist/* %{buildroot}%{_datadir}/monsoon/web/
%check
desktop-file-validate %{buildroot}%{_datadir}/applications/cafe.lair.monsoon.desktop
appstream-util validate-relax --nonet %{buildroot}%{_metainfodir}/cafe.lair.monsoon.metainfo.xml
%pre server
getent group monsoon >/dev/null || groupadd -r monsoon
getent passwd monsoon >/dev/null || useradd -r -g monsoon -d /var/lib/monsoon -s /sbin/nologin monsoon
%post server
%systemd_post monsoon-server.service
%preun server
%systemd_preun monsoon-server.service
%postun server
%systemd_postun_with_restart monsoon-server.service
%files
%license LICENSE
%doc README.md
%{_bindir}/monsoon
%{_datadir}/applications/cafe.lair.monsoon.desktop
%{_metainfodir}/cafe.lair.monsoon.metainfo.xml
%{_datadir}/icons/hicolor/*/apps/cafe.lair.monsoon.png
%files server
%license LICENSE
%doc README.md
%{_bindir}/monsoon-server
%{_unitdir}/monsoon-server.service
%{_datadir}/monsoon/
%changelog
* Sun Apr 05 2026 Rob Thijssen <grenade@rob.tn> - 0.1.0-1
- Initial package