Releases: jvgomg/podkit
Release list
podkit 0.6.0
podkit v0.6.0
The biggest release since video sync landed — new commands, a reworked sync engine, a pile of bug fixes, and quality of life improvements that make podkit feel more solid day-to-day.
If you're upgrading from 0.5.x, everything is backwards-compatible. No config changes needed.
podkit doctor
This release introduces podkit doctor — the start of making podkit useful beyond just syncing content. The idea is simple: podkit already knows your iPod inside and out, so it should be able to diagnose and fix problems too.
The first check tackles something every iPod user has run into at some point: corrupted album artwork. Wrong covers, glitched images, artwork from a completely different album showing up — the iPod's artwork database is fragile and it doesn't take much to break it. podkit doctor detects integrity issues and rebuilds the artwork from your source collection automatically. See the artwork repair guide for the full walkthrough.
The second check finds orphan files — tracks sitting on the iPod that aren't referenced by the database, quietly eating up space. --verbose breaks them down by directory and extension; --format csv exports the full list for inspection.
More checks are coming. The goal is for podkit doctor to be a swiss army knife for iPod maintenance — useful even if you don't use podkit for syncing.
Highlights
podkit device scan — Discover connected iPods without guessing mount paths. Shows volume name, UUID, size, and mount status. Especially useful for finding the volume UUID needed to configure multi-device or Docker setups.
Graceful shutdown — Ctrl+C during sync now finishes the current operation and saves all completed work to the iPod database before exiting (code 130). Previously, Ctrl+C killed the process immediately, potentially leaving orphaned files and unsaved progress. A second Ctrl+C force-quits if you really need out. The database is also saved every 50 tracks during sync, so even a crash or force-quit loses minimal work.
Unified sync pipeline — Music and video sync now run through the same engine (SyncDiffer → SyncPlanner → SyncExecutor). This means video sync gets all the reliability features music had — self-healing upgrades, error categorization with configurable retries, and consistent progress reporting. The ContentTypeHandler pattern makes it straightforward to add new content types down the road.
Under the Hood
- Dual progress bars — sync output now shows both overall progress and per-file progress simultaneously, so you can see how far along a large sync is at a glance.
- Album artwork cache cuts redundant artwork extractions by ~10x — one extraction per album instead of per track. The
podkit doctorrepair routine shares the same cache. - Full USB eject —
podkit device ejectnow fully detaches the USB device, not just unmounts the volume. On macOS, the iPod disappears from Disk Utility; on Linux, the USB device is powered off. - Incremental saves during video sync — the database saves every 10 completed video transfers, reducing data loss from interruptions during long video syncs.
- The daemon forwards SIGINT to the sync child process on SIGTERM, so Docker's 10-second shutdown window is actually used for graceful draining instead of a hard kill.
- Docker image layers optimized with
COPY --chmod=755instead of separateRUN chmodsteps.
Bug Fixes
--deleteflag was removing tracks of the wrong content type — syncing music could delete videos and vice versa- Episode/season number
0was treated as unset (||vs??), causing S01E00 episodes to be deleted and re-added every sync - Track removal left audio/video files on disk —
track.remove()now deletes the file by default - Duplicate source tracks caused an infinite metadata update loop — the diff engine now deduplicates, first match wins
- Video sync overall progress counter was incrementing on every transcode sub-tick instead of once per video
podkit doctororphan detection now skips macOS._resource fork files that were inflating the count- Graceful shutdown fixes: video sync interruptions could silently skip the database save; "Force quit" appeared immediately on first Ctrl+C via
bun run; Ctrl+C during read-only phases now exits instantly
Full changelog
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
podkit@0.6.0
Minor Changes
-
4dd7b44Thanks @jvgomg! - Addpodkit device scancommand to discover connected iPod devices. Shows each iPod's volume name, UUID, size, and mount status — useful for finding the volume UUID needed to configure multi-device setups, especially in Docker. -
d19d6e3Thanks @jvgomg! - Addpodkit doctorcommand for running diagnostic checks on an iPod, andpodkit device reset-artworkfor wiping artwork and clearing sync tags.podkit doctorruns all checks and reports problems;podkit doctor --repair artwork-integrity -c <collection>repairs by check ID using the source collection. @podkit/core exportsresetArtworkDatabaseandrebuildArtworkDatabaseprimitives, and a diagnostic framework in thediagnostics/module built on aDiagnosticCheckinterface (check + repair pattern). Includes a binary ArtworkDB parser and integrity checker. -
b698a07Thanks @jvgomg! - Add dual progress bars to sync output showing both overall and per-file progress simultaneously. Video sync now displays total file count alongside per-file transcode percentage and speed, so users can see how far along a large sync is. Music sync uses the same layout for consistency. -
2873f14Thanks @jvgomg! - Add graceful shutdown handling for sync and doctor commandsPressing Ctrl+C during
podkit syncnow triggers a graceful shutdown: the current operation finishes, all completed tracks are saved to the iPod database, and the process exits cleanly with code 130. Previously, Ctrl+C killed the process immediately, potentially leaving orphaned files and unsaved work.- Sync: first Ctrl+C drains the current operation and saves; second Ctrl+C force-quits
- Doctor: repair operations save partial progress on interrupt
- Incremental saves: the database is now saved every 50 completed tracks during sync, reducing data loss from force-quits or crashes
- New
podkit doctorcheck: detects orphaned files on the iPod (files not referenced by the database) with optional cleanup via--repair orphan-files
-
7624265Thanks @jvgomg! - Unify sync pipeline with ContentTypeHandler pattern- Add generic
ContentTypeHandler<TSource, TDevice>interface for media-type-specific sync logic - Add
MusicHandlerandVideoHandlerimplementations - Add
UnifiedDiffer,UnifiedPlanner, andUnifiedExecutorgeneric pipeline components - Add shared error categorization and retry logic (
error-handling.ts) - Add handler registry for looking up handlers by type string
- Video sync now routes through the unified pipeline in the CLI
- Video executor supports self-healing upgrades (preset-change, metadata-correction)
- Video executor categorizes errors and supports configurable per-category retries
- Fix album artwork cache incorrectly sharing artwork between tracks with and without artwork
- Generic
CollectionAdapter<TItem, TFilter>interface replaces separate music/video adapter contracts
- Add generic
Patch Changes
-
67d1357Thanks @jvgomg! - Fix--deleteflag removing video tracks when syncing music (and vice versa). The delete flag now only considers tracks of the content type being synced. -
120a7b1Thanks @jvgomg! - Improvepodkit doctororphan file reporting. Orphan detection now skips macOS._resource fork files that were inflating the count. Add--verboseoutput showing orphan breakdown by directory, file extension, and the 10 largest files. Add--format csvto export the full orphan file list for inspection. -
3f56a1bThanks @jvgomg! - Fix video sync deleting and re-adding episodes with episode number 0 (e.g., S01E00)The
||operator treated episode/season number0as falsy, converting it toundefined. This broke diff key matching for episode 0, causing every sync to delete and re-add the video. Changed to??(nullish coalescing) which only convertsnull/undefined, preserving0as a valid value. -
3db2bbbThanks [@jvgomg](https://github.com...
podkit 0.5.1
podkit v0.5.1
A quick patch release with two bug fixes that improve reliability on NAS setups and Subsonic connections.
Bug Fixes
iPod detection on Synology NAS and NVMe systems — The Linux device manager was tripping over non-standard partition names. On Synology, block devices look like usb1p2 instead of the usual sda1, and on NVMe drives you get nvme0n1p2. The old regex for stripping partition suffixes would mangle these names (turning usb1p2 into usb1p instead of usb1), which meant podkit couldn't find the USB identity of the device and silently failed to detect the iPod. The fix properly handles both partition naming conventions — so if you're running podkit on a Synology NAS in daemon mode, your iPod should now be detected automatically.
Subsonic connections no longer hang indefinitely — When a Subsonic server was unreachable (DNS failure, connection refused, server down), the adapter would just... wait. Forever. Now it retries 3 times with exponential backoff (1s, 2s, 4s), then fails with a clear error message that includes the server URL and what went wrong. If you're running in Docker, the error even suggests checking DNS, network mode, and firewall settings — the usual suspects for container networking issues. Non-connection errors like 401 or 403 fail immediately without retrying.
Full auto-generated changelog
Releases
podkit@0.5.1
Patch Changes
@podkit/core@0.5.1
Patch Changes
-
2e7ba81Thanks @jvgomg! - Fix iPod detection on Synology NAS and NVMe-based systems where block device names use non-standard partition suffixes -
e1b0fbcThanks @jvgomg! - Fix Subsonic connection failures hanging indefinitely instead of failing with a clear error message
@podkit/daemon@0.2.1
Patch Changes
@podkit/docker@0.2.1
Patch Changes
- Updated dependencies []:
- podkit@0.5.1
- @podkit/daemon@0.2.1
Changelog
Patch Changes
Checksums (SHA256)
ddbcc85c17c4f28d327c76434f0fd988fa05c7ae9eed53b6f92a72f0ed4c5ffd podkit-daemon-linux-arm64.tar.gz
26118b44a31c3fd042b77b570d57a5ebf2846c6b889f44fa2779df30e24e5b54 podkit-daemon-linux-x64.tar.gz
64695dc0ecafc73e89753d459826dabf82bcc33314debd77a4d233392eb20da9 podkit-darwin-arm64.tar.gz
a434215b7ebc966bd24b57d1ae3e01b455382c72868a38e2740b988253ca7eaf podkit-darwin-x64.tar.gz
217558cb3a0f921bb2cc33fd237c27de285b186ec165510ac71361324608ae76 podkit-linux-arm64.tar.gz
f60b11d48fee874830c4170d0d1de4cfb804912e9b1db4d347c6f72f1e443111 podkit-linux-x64.tar.gz
podkit 0.5.0
podkit v0.5.0
podkit 0.5.0 brings Docker daemon mode, a config migration system, smarter shell completions, a new --force-metadata flag, and more reliable iPod ejecting. Since we're still pre-v1, some of these are technically breaking (the config version field), but nothing should require you to change how you use podkit today.
Highlights
Daemon mode for Docker — podkit can now run as a long-running service that polls for iPod devices and auto-syncs them when plugged in. Perfect for NAS setups where you want hands-free syncing. Supports Apprise notifications (ntfy, Slack, Discord, Telegram) so you know when a sync completes. See the daemon mode guide.
Config migration system — Config files now have a version field, and podkit migrate walks you through upgrading when the format changes. Supports --dry-run to preview changes, automatic backups, and interactive migrations that can prompt for decisions. If you're running an older config, podkit will tell you exactly what to do. See the migration docs.
Shell completions for option values — Tab completion now goes beyond just subcommands and flags. Options like --quality, --type, --encoding, and --format complete their known values (e.g., max, high, medium, low). Even --device and --collection complete with names from your config file. Works in both zsh and bash — see the CLI reference.
--force-metadata flag — Rewrite metadata on all synced tracks without re-transcoding or re-transferring audio files. Useful when you've updated tags in your source library and want to push those changes to your iPod quickly.
Under the Hood
Eject reliability on macOS — If you've ever had macOS refuse to eject your iPod because Finder or Spotlight was holding a reference, this one's for you. podkit now uses diskutil eject (proper removable-media handling), flushes filesystem buffers first, and automatically retries up to 3 times when the device is busy. On Linux, busy errors from udisksctl are now surfaced properly so the retry logic can kick in.
Docker and daemon are now versioned packages — @podkit/docker and @podkit/daemon ship as proper versioned packages with changelogs, OCI image labels, and a /usr/local/share/podkit-versions.json manifest for inspecting component versions inside the container.
Quality of Life
- Docker image published as multi-arch (linux/amd64 + linux/arm64) to
ghcr.io/jvgomg/podkit - Daemon supports configurable poll intervals (
PODKIT_POLL_INTERVAL) and graceful shutdown - File-based health check at
/tmp/podkit-daemon-healthfor Docker healthcheck integration
Full auto-generated changelog
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
podkit@0.5.0
Minor Changes
-
6b90ef7Thanks @jvgomg! - Add config migration system withpodkit migratecommandConfig files now have a
versionfield. Running any command with an outdated config shows a clear error directing you to runpodkit migrate. The migrate command detects your config version, shows what will change, backs up your original file, and applies updates. Supports--dry-runto preview changes and interactive migrations that can prompt for decisions. Configs without a version field are treated as version 0 and can be migrated withpodkit migrate. -
0019607Thanks @jvgomg! - Add--force-metadataflag to rewrite metadata on all synced tracks without re-transcoding or re-transferring files -
4edaddeThanks @jvgomg! - Add tab completion for option values and dynamic config namesOptions like
--quality,--type,--encoding, and--formatnow offer their known values when pressing tab (e.g.max,high,medium,low). The--deviceand--collectionflags complete with names from your config file. Works in both zsh and bash.
Patch Changes
-
8dddd29Thanks @jvgomg! - Improve iPod eject reliability with automatic retry and filesystem sync- Use
diskutil ejectinstead ofdiskutil unmounton macOS for proper removable-media handling (unmounts + detaches the disk) - Flush filesystem buffers before ejecting to ensure all writes are persisted
- Automatically retry eject up to 3 times when the device is temporarily busy (common on macOS when Finder/Spotlight holds a reference)
- Show progress output during retry so you know what's happening
- On Linux, return busy errors from udisksctl immediately so the retry wrapper can handle them instead of silently falling through
- Use
-
Updated dependencies [
8dddd29,0019607]:- @podkit/core@0.5.0
@podkit/core@0.5.0
Minor Changes
0019607Thanks @jvgomg! - Add--force-metadataflag to rewrite metadata on all synced tracks without re-transcoding or re-transferring files
Patch Changes
8dddd29Thanks @jvgomg! - Improve iPod eject reliability with automatic retry and filesystem sync- Use
diskutil ejectinstead ofdiskutil unmounton macOS for proper removable-media handling (unmounts + detaches the disk) - Flush filesystem buffers before ejecting to ensure all writes are persisted
- Automatically retry eject up to 3 times when the device is temporarily busy (common on macOS when Finder/Spotlight holds a reference)
- Show progress output during retry so you know what's happening
- On Linux, return busy errors from udisksctl immediately so the retry wrapper can handle them instead of silently falling through
- Use
@podkit/daemon@0.2.0
Minor Changes
-
0aed896Thanks @jvgomg! - Initial release of@podkit/dockerand@podkit/daemonas versioned packages.@podkit/daemonis a long-running service that polls for iPod devices and automatically syncs them. It detects when an iPod is plugged in, mounts it, runs a full podkit sync, and ejects it — hands-free. Designed for always-on setups like NAS devices running Docker. Supports configurable poll intervals (PODKIT_POLL_INTERVAL) and Apprise notifications (PODKIT_APPRISE_URL). Handles graceful shutdown, waiting for any in-progress sync to complete before exiting.@podkit/dockeris the Docker distribution of podkit, published as a multi-arch image (linux/amd64, linux/arm64) toghcr.io/jvgomg/podkit. Bundles the CLI and daemon binaries in an Alpine-based image following LinuxServer.io conventions (PUID/PGID, /config volume). Supports two modes: CLI (default, runsyncon demand) and daemon (opt-in, auto-detect and sync iPods on plug-in). Component versions are inspectable via OCI image labels and/usr/local/share/podkit-versions.json.
@podkit/docker@0.2.0
Minor Changes
-
0aed896Thanks @jvgomg! - Initial release of@podkit/dockerand@podkit/daemonas versioned packages.@podkit/daemonis a long-running service that polls for iPod devices and automatically syncs them. It detects when an iPod is plugged in, mounts it, runs a full podkit sync, and ejects it — hands-free. Designed for always-on setups like NAS devices running Docker. Supports configurable poll intervals (PODKIT_POLL_INTERVAL) and Apprise notifications (PODKIT_APPRISE_URL). Handles graceful shutdown, waiting for any in-progress sync to complete before exiting.@podkit/dockeris the Docker distribution of podkit, published as a multi-arch image (linux/amd64, linux/arm64) toghcr.io/jvgomg/podkit. Bundles the CLI and daemon binaries in an Alpine-based image following LinuxServer.io conventions (PUID/PGID, /config volume). Supports two modes: CLI (default, runsyncon demand) and daemon (opt-in, auto-detect and sync iPods on plug-in). Component versions are inspectable via OCI image labels and/usr/local/share/podkit-versions.json.
Patch Changes
Changelog
Minor Changes
- [`6b90ef...
podkit 0.4.0
podkit 0.4.0
This is a big one. podkit 0.4.0 brings Linux support, Docker distribution, environment-variable-driven configuration, shell completions, and a major overhaul of video metadata handling. It also fixes a critical bug where Homebrew and standalone binary installations were completely non-functional for iPod operations. As a pre-v1 project, this release includes some minor breaking changes to config defaults.
Highlights
-
Linux device management —
podkit mount,podkit eject, andpodkit device addnow work on Debian, Ubuntu, Alpine, and other Linux distributions. Usesudisksctlfor unprivileged operation (withmount/umountfallback),lsblkfor device enumeration, and reads USB identity from/sysfor iPod auto-detection. iFlash adapter detection works too. Docs -
Docker image — Official image at
ghcr.io/jvgomg/podkitforlinux/amd64andlinux/arm64. Based on Alpine with FFmpeg pre-installed, PUID/PGID support, and Docker Compose examples. This release also adds musl-compatible standalone binaries to release assets. Docs -
Environment variable config — Define collections and devices entirely via env vars — no config file required. Set
PODKIT_MUSIC_PATH=/musicand go. Supports named collections, Subsonic sources, video collections, and per-device overrides. Docs -
Shell completions — Tab completion for all commands, subcommands, and options via
podkit completions install. Supports zsh and bash, with a--aliasdev mode for local development. Generated automatically from the CLI structure, so new commands just work. Docs -
Video metadata overhaul — The filename parser now handles anime fansub naming conventions (
[Group]_Show_Name_EP_(codec)_[CRC].ext), prefers folder-based series titles for richer metadata, strips scene release cruft from episode titles, and detects language and edition tags. A new configurableshowLanguagetransform reformats language markers in series titles (e.g.,(JPN)→(Japanese)). Changing language preferences triggers metadata-only updates, not file re-transfers. Show language docs
Under the Hood
-
The big one nobody noticed — The compiled CLI binary (Homebrew installs, standalone downloads) was completely broken for any command that actually talked to an iPod. The native
.nodeaddon that bridges to libgpod wasn't being bundled into the single-file binary, so every iPod database operation silently failed. This went undetected because development usesbun run(which resolves the addon fromnode_modules), not the compiled binary. The fix embeds the addon directly in the binary and fully statically links all native dependencies — including on Linux, where builds now use musl/Alpine for universal compatibility across distros. -
Video episode titles — Episodes without an explicit title in the filename (e.g.,
Show - S01E01.mkv) were showing the series name as the episode title on iPod, so you'd see "My Show" repeated for every episode instead of something useful. They now display asS01E01, and episodes with titles show asS01E01 - Episode Title.
Quality of Life
volumeUuidis now optional in device config — UUID validation still protects against syncing to the wrong iPod when configured, but you no longer need it for simple setups--dry-runoutput now showsshowLanguagetransform info so you can preview how language tags will be reformatted before syncing
Full changelog
Releases
podkit@0.4.0
Minor Changes
-
8c121ffThanks @jvgomg! - Add shell completion support withpodkit completionscommand. Tab completion for all commands, subcommands, and options is generated automatically from the CLI structure. Supports zsh and bash viapodkit completions installfor guided setup, including a dev mode (--alias) that creates a shorthand function with completions for local development workflows. -
#37
424e0e9Thanks @jvgomg! - Add official Docker image for running podkit in containers. The image is based on Alpine Linux and supports bothlinux/amd64andlinux/arm64architectures. Published to GitHub Container Registry on each release.Also adds musl-compatible Linux binaries to release assets for users on Alpine and other musl-based distributions.
-
#38
50e529cThanks @jvgomg! - Add environment variable support for defining collections and devices without a config file. SetPODKIT_MUSIC_PATH=/musicto configure a music collection entirely via env vars — no config file needed. Supports named collections (PODKIT_MUSIC_MAIN_PATH), Subsonic sources (PODKIT_MUSIC_TYPE=subsonic), and video collections (PODKIT_VIDEO_PATH). DevicevolumeUuidis now optional, and UUID validation protects against syncing to the wrong iPod when configured. -
#38
50e529cThanks @jvgomg! - Add Linux device manager support for mount, eject, and device detection. podkit now supportspodkit mount,podkit eject, andpodkit device addon Debian, Ubuntu, Alpine, and other Linux distributions. Useslsblkfor device enumeration,udisksctlfor unprivileged mount/eject (with fallback tomount/umount), and USB identity from/sysfor iPod auto-detection. iFlash adapter detection works on Linux via block size and capacity signals. -
#38
50e529cThanks @jvgomg! - Improve video filename parsing and add show language transform for video syncFilename parsing improvements:
- Add anime fansub filename pattern support (
[Group]_Show_Name_EP_(codec)_[CRC].ext) - Prefer folder-based series titles over filename-only parsing for richer metadata
- Strip scene release cruft (quality tags, codecs, release groups) from episode titles
- Detect language and edition tags from filenames and folder paths
- Add
languageandeditionoptional fields toCollectionVideo
Show language transform:
- Add configurable
showLanguagetransform that reformats language markers in video series titles (e.g.,(JPN)→(Japanese)) - Enabled by default with abbreviated format — configure via config file, per-device overrides, or
PODKIT_SHOW_LANGUAGE*env vars - Changing language display preferences causes metadata-only updates, not file re-transfers (dual-key matching in video differ)
CLI:
- Add
showLanguageconfig support (boolean shorthand or[showLanguage]table withformatandexpandoptions) - Add per-device
showLanguageoverrides - Show transform info in
--dry-runoutput - Add
@podkit/libgpod-nodeas explicit dependency for reliable native binding resolution in worktrees
- Add anime fansub filename pattern support (
Patch Changes
-
#38
50e529cThanks @jvgomg! - Fix native libgpod binding not loading in compiled CLI binary. The Homebrew and standalone binary distributions were completely broken for any command that touched the iPod database. The.nodeaddon is now embedded directly in the single-file binary, and all native dependencies are fully statically linked — including on Linux, where builds now use musl/Alpine for universal compatibility across all distros (Debian, Ubuntu, RHEL, Fedora, Arch, Alpine, etc.). -
Updated dependencies [
50e529c,21ab79a,50e529c]:- @podkit/core@0.4.0
@podkit/core@0.4.0
Minor Changes
-
#38
50e529cThanks @jvgomg! - Add Linux device manager support for mount, eject, and device detection. podkit now supportspodkit mount,podkit eject, andpodkit device addon Debian, Ubuntu, Alpine, and other Linux distributions. Useslsblkfor device enumeration,udisksctlfor unprivileged mount/eject (with fallback tomount/umount), and USB identity from/sysfor iPod auto-detection. iFlash adapter detection works on Linux via block size and capacity signals. -
#38
50e529cThanks @jvgomg! - Improve video filename parsing and add show language transform for video syncFilename parsing improvements:
- Add anime fansub filename pattern support (
[Group]_Show_Name_EP_(codec)_[CRC].ext) - Prefer folder-based series titles over filename-only parsing for richer metadata
- Strip scene release cruft (qua...
- Add anime fansub filename pattern support (
podkit 0.3.0
podkit v0.3.0
This is a big release! podkit now keeps your iPod in sync much more intelligently — it detects when your source files have improved and upgrades tracks automatically, handles volume normalization, understands compilation albums, and can even spot when your album artwork has changed.
There are a few breaking changes to the CLI and config format (details below). We're still pre-v1, so we're taking this opportunity to clean up the interface while the project is young. Migration is straightforward — see the breaking changes section for exactly what to update.
Highlights
-
Self-healing sync — podkit now detects when a source file has improved (format upgrade, higher quality, new artwork, corrected metadata) and upgrades the track on your iPod in place, preserving play counts, ratings, and playlist membership. No more removing and re-adding tracks to get better quality. Read more →
-
Sound Check — Volume normalization is here. podkit reads ReplayGain and iTunNORM tags from your source files (and Subsonic servers via OpenSubsonic) and writes Sound Check values to the iPod database, so tracks play back at consistent volumes. Verbose mode shows a breakdown of tag formats found in your collection. Read more →
-
Device-aware quality presets — Quality presets have been redesigned into four tiers:
max,high,medium,low. Themaxpreset automatically picks lossless ALAC on devices that support it and falls back to high-quality AAC on others. If you change your preset, podkit detects the mismatch and re-transcodes on the next sync. Read more → -
Artwork change detection — Use
--check-artworkto detect when album art has changed in your source collection and update it on your iPod without re-transferring audio. Artwork fingerprints are built up progressively during normal syncs, so there's nothing extra to set up. Read more → -
Compilation albums — Compilation metadata from FLAC, MP3, M4A files and Subsonic servers is now written to the iPod database correctly, so compilation albums show up under "Compilations" where they belong. Read more →
Breaking Changes
CLI: Named flags replace positional arguments — All device names, collection names, and sync types now use named flags. This makes commands more readable and consistent. CLI reference →
- podkit sync music -c main
+ podkit sync -t music -c main
- podkit device add myipod /Volumes/IPOD
+ podkit device add -d myipod --path /Volumes/IPOD
- podkit device info myipod
+ podkit device info -d myipodConfig: ftintitle renamed to cleanArtists — The [transforms.ftintitle] config section is now a top-level cleanArtists key. Supports a simple cleanArtists = true or a table with options. Clean Artists docs →
- [transforms.ftintitle]
- enabled = true
+ cleanArtists = trueConfig: Quality presets redesigned — Presets are now max, high, medium, low (default: high). A new encoding option replaces the old CBR preset variants, and lossyQuality has been removed. Quality presets docs →
Under the Hood
-
The curious case of the backwards encoder — Turns out macOS's AudioToolbox AAC encoder uses a quality scale where 0 is best and 14 is worst. Our mapping had it the wrong way around, which meant the "high" VBR preset was quietly producing ~44 kbps audio instead of ~256 kbps. If you've been on macOS and wondering why your transcodes sounded a bit rough — mystery solved. This release fixes the mapping using empirically-measured bitrate targets, so presets now sound the way they should.
-
Sync tags — podkit now embeds small metadata tags in the iPod track's comment field recording exactly what transcode settings produced each file. This eliminates false re-transcoding caused by natural VBR bitrate variance — previously, a track encoded at 248 kbps targeting 256 kbps might get re-transcoded unnecessarily. You can retrofit tags onto existing tracks with
--force-sync-tags. Sync tags reference → -
Subsonic prefetch pipeline — Syncing from Subsonic/Navidrome is now faster. Previously, each track was downloaded then transcoded sequentially, leaving the network idle during CPU work. The sync executor now pipelines downloads ahead of transcoding so network I/O overlaps with FFmpeg encoding.
-
replaceTrackFile()in libgpod-node — A new native binding that replaces a track's audio file while preserving the database entry. This is the foundation that makes self-healing sync possible — the old file is deleted, libgpod generates a fresh device path with the correct extension, and the iPod firmware uses the right decoder.
Quality of Life
unmountnow works as an alias foreject--no-tipsflag (andtipsconfig option) to suppress contextual tips- Mount command tries
diskutil mountbefore falling back to sudo, with better error messages explaining what's happening device clearconfirmation prompt now shows the[y/N]hint- Transcoding progress no longer wraps on narrow terminals
- Video sync time estimates are now ~20x more accurate
Full changelog
Releases
@podkit/libgpod-node@0.1.0
Minor Changes
-
e4485a1Thanks @jvgomg! - Add self-healing sync for changed and upgraded source files. Sync now detects when a source file has improved — format upgrade (MP3 replaced with FLAC), quality upgrade (higher bitrate), artwork added, Sound Check values changed, or metadata corrected — and upgrades the iPod track in place, preserving play counts, star ratings, and playlist membership.Upgrades happen by default as part of normal sync. Use
--skip-upgradesor theskipUpgradesconfig option to disable file-replacement upgrades when short on time or space. TheskipUpgradessetting follows the standard resolution order (CLI flag → device config → global config → default).Add
replaceTrackFile()to@podkit/libgpod-nodefor replacing a track's audio file while preserving the database entry. The old file is deleted and libgpod generates a fresh path with the correct extension for the new format, ensuring the iPod firmware uses the right decoder.Add
hasArtworkfield toCollectionTrack— populated by the directory adapter (from embedded pictures) and Subsonic adapter (from cover art metadata).Fix copied tracks (MP3, M4A) not having their bitrate recorded in the iPod database, which is needed for quality-upgrade detection.
Breaking:
ConflictTracktype andSyncDiff.conflictsarray removed from@podkit/core— metadata conflicts are now handled asmetadata-correctionupgrades. -
d40371fThanks @jvgomg! - Add Sound Check (volume normalization) support. podkit now reads ReplayGain and iTunNORM tags from source files and writes the Sound Check value to the iPod database during sync, enabling automatic volume normalization on playback. The dry-run output shows how many tracks have normalization data, and a newsoundcheckfield is available indevice musicandcollection musiccommands via--fields.
podkit@0.3.0
Minor Changes
-
2a4799bThanks @jvgomg! - Add artwork change detection with--check-artworkflag. When enabled, podkit detects when album artwork has changed in your source collection and updates the artwork on your iPod without re-transferring audio files. Artwork fingerprints are written progressively during normal syncs, building baselines automatically over time. Sync tag display now shows consistency breakdown in device info and track listings. For directory sources, artwork added and removed is also detected automatically. Subsonic sources support artwork change detection but not artwork added/removed detection due to limitations in the Subsonic API. -
0aff870Thanks @jvgomg! - Renameftintitletransform tocleanArtistswith a simpler config formatBreaking change (minor bump — not yet v1): The
[transforms.ftintitle]config section has been replaced with a top-levelcleanArtistskey. This is a cleaner, more intuitive name that communicates the feature's value. The new format supports both a simple boolean (cleanArtists = true) and a table form with options ([cleanArtists]). Per-device overrides usecleanArtists = falseor[devices.<name>.cleanArtists]. Environment variablesPODKIT_CLEAN_ARTISTS,PODKIT_CLEAN_ARTISTS_DROP,PODKIT_CLEAN_ARTISTS_FORMAT, andPODKIT_CLEAN_ARTISTS_IGNOREare now supported. TheFtInTitleConfigtype is renamed toCleanArtistsConfigandDEFAULT_FTINTITLE_CONFIGtoDEFAULT_CLEAN_ARTISTS_CONFIG. -
e47456aThanks @jvgomg! - Add compilation album support to sync pipeline and CLI display. Compilation metadata from source files (FLAC, MP3, M4A) and Subsonic servers is now correctly written to the iPod database, ensuring compil...
podkit 0.2.0
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
podkit@0.2.0
Minor Changes
d3b8eb2Thanks @jvgomg! - Improvepodkit device addto detect and handle unmounted iPods, including iFlash-modified devices that macOS refuses to automount.- Scans for both mounted and unmounted iPods — no longer requires the device to be pre-mounted
- Assesses unmounted devices before attempting to mount: reads block size and capacity from diskutil, queries USB product ID via system_profiler, and resolves it to a model name (e.g. "iPod Classic 6th generation")
- Confirms iFlash adapters via two independent signals: 2048-byte block size (iFlash emulates optical media sectors) and capacity exceeding the original iPod Classic maximum of 160 GB
- Attempts
diskutil mountfirst (no elevated privileges required); falls back tomount -t msdosfor large FAT32 volumes that macOS refuses to mount through its normal mechanisms - When sudo is required, explains exactly why with per-signal detail and shows the exact command to run (
sudo podkit device add <name>) - Exports
DeviceAssessment,IFlashAssessment,IFlashEvidence, andUsbDeviceInfotypes from@podkit/core
Patch Changes
-
f268d71Thanks @jvgomg! - Extract filesystem validation into a shared utility module for improved testability -
b3d530fThanks @jvgomg! - Add support for PODKIT_CONFIG environment variable to set config file path -
Updated dependencies [
d3b8eb2]:- @podkit/core@0.2.0
@podkit/core@0.2.0
Minor Changes
d3b8eb2Thanks @jvgomg! - Improvepodkit device addto detect and handle unmounted iPods, including iFlash-modified devices that macOS refuses to automount.- Scans for both mounted and unmounted iPods — no longer requires the device to be pre-mounted
- Assesses unmounted devices before attempting to mount: reads block size and capacity from diskutil, queries USB product ID via system_profiler, and resolves it to a model name (e.g. "iPod Classic 6th generation")
- Confirms iFlash adapters via two independent signals: 2048-byte block size (iFlash emulates optical media sectors) and capacity exceeding the original iPod Classic maximum of 160 GB
- Attempts
diskutil mountfirst (no elevated privileges required); falls back tomount -t msdosfor large FAT32 volumes that macOS refuses to mount through its normal mechanisms - When sudo is required, explains exactly why with per-signal detail and shows the exact command to run (
sudo podkit device add <name>) - Exports
DeviceAssessment,IFlashAssessment,IFlashEvidence, andUsbDeviceInfotypes from@podkit/core
Changelog
Minor Changes
d3b8eb2Thanks @jvgomg! - Improvepodkit device addto detect and handle unmounted iPods, including iFlash-modified devices that macOS refuses to automount.- Scans for both mounted and unmounted iPods — no longer requires the device to be pre-mounted
- Assesses unmounted devices before attempting to mount: reads block size and capacity from diskutil, queries USB product ID via system_profiler, and resolves it to a model name (e.g. "iPod Classic 6th generation")
- Confirms iFlash adapters via two independent signals: 2048-byte block size (iFlash emulates optical media sectors) and capacity exceeding the original iPod Classic maximum of 160 GB
- Attempts
diskutil mountfirst (no elevated privileges required); falls back tomount -t msdosfor large FAT32 volumes that macOS refuses to mount through its normal mechanisms - When sudo is required, explains exactly why with per-signal detail and shows the exact command to run (
sudo podkit device add <name>) - Exports
DeviceAssessment,IFlashAssessment,IFlashEvidence, andUsbDeviceInfotypes from@podkit/core
Patch Changes
-
f268d71Thanks @jvgomg! - Extract filesystem validation into a shared utility module for improved testability -
b3d530fThanks @jvgomg! - Add support for PODKIT_CONFIG environment variable to set config file path -
Updated dependencies [
d3b8eb2]:- @podkit/core@0.2.0
Checksums (SHA256)
16fcab7ae7b751dd2ca8c65abf21cd042fbe048a0d6cad0c591766f307fdfb33 podkit-darwin-arm64.tar.gz
3e232a9ae1d66061ee09f9ea7451db8062f1f5816b9d86a183861580c0178a97 podkit-darwin-x64.tar.gz
60a17e61caf2ad0b3c6a59078c1566ad2b5d40325b193c5ca03294949451311c podkit-linux-arm64.tar.gz
7dc87508c07b0650a7a0bd1c3fb1599e4ab926eff2e5d2a612541cc1ff3c88e1 podkit-linux-x64.tar.gz
podkit 0.1.0
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
podkit@0.1.0
Minor Changes
-
83743ddThanks @jvgomg! - Add device validation and capability communication- Detect unsupported devices (iPod Touch, iPhone, iPad, buttonless Shuffles, Nano 6th gen) with clear error messages explaining why they won't work
- Warn when iPod model cannot be identified, with instructions to fix SysInfo
- Show device capability indicators (+/-) in
podkit device infooutput - Block
podkit device addfor unsupported devices and show capabilities during confirmation - Add sync pre-flight checks that block unsupported devices and warn about incompatible content types
- Include structured capabilities and validation data in JSON output
-
39e3129Thanks @jvgomg! - Add stats, albums, and artists views to content listing commandsdevice music,device video,collection music, andcollection videonow show summary stats by default (track/album/artist counts and file type breakdown)- Add
--tracksflag to list all tracks (previous default behavior) - Add
--albumsflag to list albums with track counts - Add
--artistsflag to list artists with album/track counts --tracks --jsonon device commands now includes all iPod metadata fields (play stats, timestamps, video fields, etc.)
Patch Changes
- Updated dependencies [
83743dd]:- @podkit/core@0.1.0
@podkit/core@0.1.0
Minor Changes
83743ddThanks @jvgomg! - Add device validation and capability communication- Detect unsupported devices (iPod Touch, iPhone, iPad, buttonless Shuffles, Nano 6th gen) with clear error messages explaining why they won't work
- Warn when iPod model cannot be identified, with instructions to fix SysInfo
- Show device capability indicators (+/-) in
podkit device infooutput - Block
podkit device addfor unsupported devices and show capabilities during confirmation - Add sync pre-flight checks that block unsupported devices and warn about incompatible content types
- Include structured capabilities and validation data in JSON output
Changelog
Minor Changes
-
83743ddThanks @jvgomg! - Add device validation and capability communication- Detect unsupported devices (iPod Touch, iPhone, iPad, buttonless Shuffles, Nano 6th gen) with clear error messages explaining why they won't work
- Warn when iPod model cannot be identified, with instructions to fix SysInfo
- Show device capability indicators (+/-) in
podkit device infooutput - Block
podkit device addfor unsupported devices and show capabilities during confirmation - Add sync pre-flight checks that block unsupported devices and warn about incompatible content types
- Include structured capabilities and validation data in JSON output
-
39e3129Thanks @jvgomg! - Add stats, albums, and artists views to content listing commandsdevice music,device video,collection music, andcollection videonow show summary stats by default (track/album/artist counts and file type breakdown)- Add
--tracksflag to list all tracks (previous default behavior) - Add
--albumsflag to list albums with track counts - Add
--artistsflag to list artists with album/track counts --tracks --jsonon device commands now includes all iPod metadata fields (play stats, timestamps, video fields, etc.)
Patch Changes
- Updated dependencies [
83743dd]:- @podkit/core@0.1.0
Checksums (SHA256)
246f9f5bbf2892249392ad27d0d53ccbe06142805a09a9a5d56122a51de3b389 podkit-darwin-arm64.tar.gz
b4f0f943f9fc789d2c05b0863a50d998efe2dc9a16054460b4b4b424d906b4e0 podkit-darwin-x64.tar.gz
e06671d769a63ebc9f0cefdc3a5c67c00c5422531905aba3ea4f51308e8ac96a podkit-linux-arm64.tar.gz
e2f6d12681eeea3394e3c7b21dec3e3eb27372c5cf45c4b8b1c950812eb0b69a podkit-linux-x64.tar.gz
podkit 0.0.3
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
podkit@0.0.3
Patch Changes
Changelog
Patch Changes
Checksums (SHA256)
d0242788652afb4dca25ea74dda74fd0ae9041a0f1947da650b1abdb629bd9f4 podkit-darwin-arm64.tar.gz
a666d0e3aff1f03a1b827639c764e25b2d326654fe62df3f6fc86dbc60cb6968 podkit-darwin-x64.tar.gz
517c303ffdb5783d63384cc1bbcc4018327d86d46331c7764fee1eaf184fd9c8 podkit-linux-arm64.tar.gz
e9e26e0e4af3cbff3ff29c4d4ae7509b217f5f4522fdf97e797ffb261920be0a podkit-linux-x64.tar.gz
podkit 0.0.2
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
podkit@0.0.2
Patch Changes
Changelog
Patch Changes
Checksums (SHA256)
eb738bbfeda29a8ccaadc0ed59ff6bcc5acdd5feb95a026388e64eff72bac908 podkit-darwin-arm64.tar.gz
1088ede2dda52c4c1cd976684e833b185bf5cb94078176000d9d1a7abb591603 podkit-darwin-x64.tar.gz
e254e4156ccd05bcdc556ba05ccc7bca708bee09f260a03dadfd58075c305ebb podkit-linux-arm64.tar.gz
fa7d2ddb8f1311f571f8aa9b375cceed6567860dc42e240472e9af66bc6eff0f podkit-linux-x64.tar.gz