Self-hosted scheduling without GitHub Actions
Postline does not need GitHub Actions, a hosted scheduler, or usage credits. It can stay running on any machine with Node.js 20 or newer and persistent storage.
Install from the GitHub release
Download and install the release package without npm publishing:
npm install --global postline
postline --version
Install Chromium once on machines that render cards:
npx playwright-core@1.64.1 install chromium
Run the built-in daemon
From the content project:
postline daemon --every 15
The first check runs immediately. Later checks run serially at the requested
interval, so one daemon never overlaps itself. Configuration and posts are reloaded
on every check, and a failed check is logged without stopping the daemon. SIGINT
and SIGTERM stop it cleanly.
The machine must remain awake and connected. Keep .postline/ledger.json on
persistent storage. While a check runs, postline holds .postline/publish.lock, so
a second daemon or a manual postline publish on the same project waits for the
next check instead of sending the same post. (--dry-run doesn't take the lock.)
A lock left by a process that crashed is cleared automatically on the same machine.
If a process dies during a network request, the durable attempting entry prevents
an automatic duplicate, and a request that ends without a clear answer is recorded
as uncertain. Inspect the destination and use postline mark or postline retry.
Keep it running with systemd
Copy the example created by postline init and replace every /ABSOLUTE/PATH
placeholder:
mkdir -p ~/.config/systemd/user
cp schedulers/systemd/postline.service.example ~/.config/systemd/user/postline.service
systemctl --user daemon-reload
systemctl --user enable --now postline.service
systemctl --user status postline.service
journalctl --user -u postline.service -f
The environment file contains ordinary NAME=value lines for the channels you
configured. Restrict it to your account:
chmod 600 /absolute/path/to/postline.env
On a Linux server, enable user lingering if the service must continue after logout:
loginctl enable-linger "$USER"
Other process managers
Launchd, Docker Compose, Kubernetes, PM2, supervisord, and Windows Task Scheduler
can all run postline daemon --every 15. If the scheduler invokes one-shot jobs,
run postline publish from the content project and ensure jobs cannot overlap.
For disposable runners, use publish --prepare-only, persist the ledger, run
publish --resume-prepared, and persist the final ledger. That two-phase sequence
is required because the local filesystem disappears between runs.