v2.0.0: Namespaces, Port Management, and File Watching
Pitchfork v2.0.0 is a major release that introduces namespace-qualified daemon IDs, port conflict management, and several important bug fixes. The namespace change is breaking -- daemon IDs are now in namespace/name format -- but short IDs continue to work when unambiguous, and legacy log directories are automatically migrated.
Highlights
- Namespaces: Daemons across different projects no longer collide. Each project gets a namespace (derived from directory name or explicit config), and daemon IDs become
namespace/name. Short names still work when you're inside the project directory. - Port conflict detection: Daemons can declare expected ports and opt into auto-bump, so pitchfork will find an available port if the configured one is already in use.
- File watching actually works: The
watchconfig field was previously broken -- patterns were lost after daemon startup. This release rewrites the watcher to persist patterns in state and dynamically pick up new daemons.
Added
-
Port conflict detection and auto-bump: Declare
expected_portandauto_bump_portin your daemon config, and pitchfork will check for conflicts before starting and automatically increment ports if needed. Resolved ports are injected asPORT,PORT0,PORT1, etc. environment variables. New CLI flags--expected-portand--auto-bump-portare available onrun,start, andconfig add. A network view (presspin the TUI) shows all listening processes. (#259) - @benjaminwestern[daemons.api] run = "npm run dev" expected_port = [3000] auto_bump_port = true
Fixed
- File watching for daemon auto-restart: The
watchfield inpitchfork.tomlwas documented but non-functional. Watch patterns and base directories are now persisted in daemon state and the watcher dynamically refreshes every 10 seconds to pick up new daemons. (#255) - @benjaminwestern pitchfork config addgenerates valid TOML: Previously,pitchfork config addjoined all arguments into a singlerunstring, producing broken config. It now accepts proper CLI flags (--run,--retry,--watch,--depends,--env, etc.) and generates correct TOML with each option as a separate field. (#258) - @benjaminwesternpitchfork logs --tailbypasses pager: Using--tailno longer openslessand blocks with(END)-- logs now stream directly to stdout. (#253) - @jdx- TUI log rendering and scroll behavior: Fixed text wrapping causing lines to be hidden below the viewport. The scroll model was rewritten to track the last visible line rather than the first, and tab characters and ANSI clear-screen codes are now stripped from log output. (#264) - @dimmyjing
Breaking Changes
-
Daemon IDs now include a namespace: All daemon IDs are internally stored as
namespace/name(e.g.,frontend/api). The namespace is derived from the project directory name, or can be explicitly set withnamespace = "..."at the top ofpitchfork.toml. Short IDs (e.g.,api) continue to work when unambiguous. ThePITCHFORK_DAEMON_IDenvironment variable now contains the fully-qualified ID, and a newPITCHFORK_DAEMON_NAMESPACEvariable is available. Log directories are renamed from<name>/to<namespace>--<name>/; existing logs are automatically migrated to alegacynamespace. Thedependsfield now accepts cross-namespace references (e.g.,global/postgres). (#213) - @gaojunranIf you have scripts that parse
PITCHFORK_DAEMON_ID, they will now receivenamespace/nameinstead of justname. Directory names containing--are reserved for internal encoding and will require an explicitnamespaceoverride.
New Contributors
- @gaojunran made their first contribution in #213
- @benjaminwestern made their first contribution in #255
- @dimmyjing made their first contribution in #264
Full Changelog: v1.6.0...v2.0.0