npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

goosetools-worker

v0.2.2

Published

The Goose Tools carousel worker — your computer drafts and renders carousel slides for goosetools.com using your own Claude account.

Downloads

347

Readme

carousel-maker

Brand-aware Instagram carousel generator. Photos, clips and words in → ready-to-post 1080×1350 slides out (PNG, or MP4 for slides built on a video).

How it works

  1. brand.yml — your colors, fonts, handle. Set once; every slide inherits it.
  2. A stylestyles/<name>/ holds a template set + style.yml (font/color overrides) + the reference images that inspired it. Like Recraft: drop inspo screenshots in styles/<name>/refs/, have the agent distill them into templates, reuse forever. brand.yml → defaultStyle picks the default; a carousel can override with style: <name> in its slides.yml.
  3. A carousel foldercarousels/<name>/ with a slides.yml (and photos/ + videos/ alongside it).
  4. Render — HTML templates filled with your brand tokens, screenshotted headless at 2x.

Usage

npm install && npx playwright install chromium   # first time only

node src/render.js carousels/my-post
# → carousels/my-post/output/slide-01.png, slide-02.png, ...

# optional, last: only if you want video slides (see below)
brew install ffmpeg

slides.yml

slides:
  - template: cover        # bold hook on brand color + "swipe →"
    text: |-
      the hook
      goes here
  - template: photo        # your photo, text over a dark gradient
    photo: photos/desk.jpg
    text: caption over the photo
  - template: photo        # same template, but the background MOVES
    video: videos/build.mp4
    text: caption over the clip
  - template: text         # dark slide, *asterisks* render in accent color
    text: |-
      body copy with
      *highlighted* words
  - template: cta          # gradient closer with follow pill — put last
    text: your call to action

Templates

| template | look | |---|---| | cover | brand gradient, big bold hook | | photo | full-bleed photo, gradient scrim, caption at bottom | | text | dark background, bold copy, *text* → accent color | | light | off-white background, dark copy, *text* → primary color | | cta | brand gradient, centered text + "follow @handle" pill |

Every slide gets a progress bar + page counter baked in, and a swipe chevron on the right edge — except the last slide, where the missing chevron and full bar signal the end. Alternate dark/light templates for visual rhythm.

Add a template by dropping a new templates/<name>.html — it gets the full brand.yml context plus {{text}}, {{photoSrc}}, {{handle}}, {{ui}} (the progress bar + chevron; include it in every template). If the new template has a light background, add its name to LIGHT_TEMPLATES in src/render.js so the chrome adapts.

Video slides

Any slide that takes a photo: takes a video: instead — same template, same focus: / zoom: framing controls, but the clip plays full-bleed behind the slide's text. Instagram carousels accept video items, so a deck can mix stills and motion freely.

  - template: photo
    video: videos/build.mp4
    focus: "60% 45%"   # centre of the subject, as on a photo
    zoom: 1.8
    text: watch it *come together*

How it renders: the slide is screenshotted twice — once normally over a frame pulled out of the clip (slide-03.png — what the framing self-check reads), and once with every background stripped so only the artwork remains. ffmpeg then crops the clip to the slide shape and burns that artwork over it (slide-03.mp4, H.264 / yuv420p, 1080 wide, audio kept, first 60s).

This means no template needs to know about video — every style's photo template gained video support for free.

ffmpeg (optional, but required for video)

Video slides need ffmpeg and ffprobe on your PATH. They do not come with Node, npm, or Playwright — Playwright bundles an ffmpeg, but it's built --disable-everything for WebM screen recording: no H.264, no AAC, no ffprobe. So it's a real install:

brew install ffmpeg              # macOS
winget install Gyan.FFmpeg       # Windows
sudo apt install ffmpeg          # Linux

It's genuinely optional: a deck with no video: slides never even checks for it. But a deck with clips fails loudly rather than quietly rendering them as stills — a carousel that looks finished and silently isn't the one you asked for is the worse outcome. goosetools-worker status shows whether this computer can do video.

Goose Tools worker

This repo doubles as the worker behind goosetools.com's Carousel Maker. The web app queues jobs; a worker on your own computer claims them, drafts the slide copy with your local Claude Code login (your subscription), renders with the engine above, and uploads the finished slides.

# one-time: install Claude Code + sign in, then
npx --yes goosetools-worker install --url https://goosetools.com --token gt_...   # token from the website

install saves the token to ~/.goosetools/env and registers a login service (launchd on macOS, a Scheduled Task on Windows) so the worker runs in the background whenever the computer is on — even after a restart. npx --yes goosetools-worker uninstall removes it. To run in the foreground instead: npx --yes goosetools-worker run --url … --token ….

Optional env: VOICE_DIR points at a writing-voice folder the drafts should follow (see worker/index.js).

Worker commands

| Command | What it does | | --- | --- | | install --token gt_… | First-time setup: save the token, install the background copy, register the service. | | update | Pull the newest code into the background copy and restart it. Reuses the saved token. | | status | What's installed, whether it's running, and recent log lines. Start here when something's wrong. | | uninstall | Remove the service and the saved token. | | run | Run the loop in this window instead of in the background. |

All of them work via npx --yes goosetools-worker@latest <command>.

Worker FAQ

The website says my computer isn't connected. Run npx --yes goosetools-worker@latest status. It tells you whether the worker is installed, whether the process is actually running, and whether a token is saved. Each line is one of the things that has to be true for the website to show "Connected".

How do I get a new version onto my computer? npx --yes goosetools-worker@latest update.

This matters more than it looks. The background service does not run from wherever you ran npx, or from a git checkout — it runs a copy installed under ~/.goosetools/app. New code only reaches that copy when you reinstall it, and the running process only picks the new code up when it restarts (Node reads every file once, at startup). update does both, and reuses your saved token so you don't have to find it again.

I updated but nothing changed. Check status — the "Installed" line is the version the daemon will run, and "Running" shows the live process. If Installed is the new version but the behavior is old, the process didn't restart; run update again.

status shows errors — is my worker broken? Look at the "last written" time next to the error block. The service restarts itself and keeps its old log, so errors from days ago sit there long after they stopped mattering. If "Activity" was written recently and "Errors" wasn't, the worker is fine — it's polling normally.

"Poll failed (will retry)" is the worker not reaching the server: laptop asleep, wifi dropped, or the site briefly down. It retries every 30s on its own; no action needed unless it's still happening now.

"This computer's worker is outdated for this job" means the website sent a kind of job this worker version doesn't know how to do. Run update.

"Style X isn't installed on this computer yet" — styles live on the machine that renders them (styles/<slug>/). A style generated on a different computer won't exist on this one; regenerate it here.

Jobs sit in "queued" forever. Queued means the website has the job but no worker has claimed it. Confirm the worker is running with status, and confirm it's pointed at the same server (the "Server" line) as the site you queued from.

Where are the logs? ~/.goosetools/worker.log (activity) and ~/.goosetools/worker.err.log (errors). status tails both.

Do I need to keep a terminal open? No — that's what install sets up. run is the foreground alternative if you'd rather watch it work.

Publishing a new worker version

Users get updates from npm, so pushing to git is not enough — update and npx goosetools-worker@latest both resolve to the published version:

npm version patch   # or minor/major
npm publish
git push --follow-tags

Until you publish, npm view goosetools-worker version will lag the repo and everyone else stays on the older code. status flags the mismatch on your own machine ("you're ahead — local dev build").

Roadmap

  • Secondary font (TBD in brand.yml)
  • Per-platform handle overrides
  • Draft the words too (hook + slide copy from a rough idea)
  • Hook into build-in-public as a skill