Eggs
Multi-user desktop pet
Features
- Multiple pets — Compatible with Codex pet packs.
- Custom pet states — Define arbitrary states per pet.
- Multiplayer remote sessions — Sync pet status and chat with peers.
- Agent hooks — Render local hook events as pet bubbles.
- Skills — Built-in compatibility with the community Skills ecosystem.
Quick Start
Build and run the desktop binary:
./desktop/dev fast
./desktop/src-tauri/target/release-fast/eggs
Or run through wrapper helpers:
./desktop/dev run
./desktop/dev run remote
Common helper targets:
./desktop/dev fast
./desktop/dev release
./desktop/dev check
./desktop/dev clean
./desktop/dev test
CLI (Desktop Binary)
The same binary is both GUI and CLI:
eggs
eggs run
eggs start
eggs stop
eggs restart
eggs status
eggs list
eggs pet <source> <id>
eggs state <name>
eggs install <pet-dir>
eggs hook "<text>"
eggs message "<text>"
eggs remote help
eggs uninstall-cli
Notes:
eggs start launches detached and writes PID to ~/.eggs/eggs.pid.
- CLI mutations are file-driven (
state.json / remote.json) and picked up by the running GUI via polling + single-instance forwarding.
- First GUI launch from packaged builds attempts best-effort CLI install into PATH (platform-specific).
Remote Multiplayer
Remote state is stored in ~/.eggs/remote.json and defaults to:
server_url: http://localhost:8787
mode: random
room_limit: 5
Key commands:
eggs remote
eggs remote random
eggs remote room <code> [limit]
eggs remote leave
eggs remote off
eggs remote server <url>
eggs remote status
eggs remote upload [pet_id]
Behavior highlights:
remote and remote on keep the saved mode/room.
remote room <code> [limit] persists invite room mode and cap.
remote random switches mode without clearing saved room code.
- Pet switch in remote mode gates local change on successful upload to keep local/peer view consistent.
eggs pet <source> <id> targets an exact pet source: builtin, local, or remote.
- Upload is source-aware (
pet_source + pet) while peer downloads are content-addressed by content_id from server-provided asset URLs.
- The detailed upload/download protocol is documented in
desktop/README.md under Remote Asset Flow.
Codex Hook Integration
Project hook scripts are in:
.codex/hooks.json
.codex/hooks/*.py
These scripts emit local desktop bubbles by calling:
eggs hook "<text>"
So if hooks are enabled in your Codex environment, hook events can be visualized as pet bubbles.
Data Directory
Runtime data is in ~/.eggs/ (or EGGS_APP_DIR override):
state.json: current pet, pet source, state, scale, window position
client.json: device identity
remote.json: remote config
eggs.pid: detached GUI pid
pets/<id>/: installed pets
remote/: cached peer sprite assets and blobs
bubble-spool/: queued local bubble events
Pet lookup priority:
EGGS_PETS_DIR (if set, exclusive)
~/.eggs/pets
$CODEX_HOME/pets or ~/.codex/pets
- Remote cache under
~/.eggs/remote
Pet Asset Format
Each pet folder:
<pet-id>/
pet.json
spritesheet.webp # or png
pet.json fields used by desktop runtime:
id
displayName
description (optional)
spritesheetPath
Custom Atlas Builder
If you already have 9 horizontal strip images for custom pet states, you can turn them into 192x208 frames and compose a Codex-style 8x9 atlas with:
uv run --with pillow python scripts/build_custom_pet_atlas.py \
--input-dir /absolute/path/to/custom-strips \
--output-dir /absolute/path/to/custom-build
Input expectations:
--input-dir must contain exactly 9 strip images.
- Supported formats are
png, webp, jpg, and jpeg.
- The script assumes a chroma-key background and uses
#FF00FF by default.
- Rows are ordered by filename sort order, so name the files in the row order you want.
- Each detected frame is centered into a
192x208 cell, and unused cells in the 8x9 atlas remain transparent.
Optional chroma-key override:
uv run --with pillow python scripts/build_custom_pet_atlas.py \
--input-dir /absolute/path/to/custom-strips \
--output-dir /absolute/path/to/custom-build \
--chroma-key '#00FF00'
Outputs written under --output-dir:
spritesheet.png
spritesheet.webp
contact-sheet.png
custom-frames-manifest.json
frames/<state>/<index>.png
Remote Server
Go server lives in server/:
cd server
go build -o eggs-server .
./eggs-server -addr :8787 -data ~/.codex/eggs-server -base-url http://localhost:8787
It uses pure-Go SQLite (modernc.org/sqlite) and does not require system SQLite shared libraries on target hosts.
Packaging
For app bundles: