← Back to Studio

Studio archive · 2026-07-04

The Skills That Only Worked On One Machine

I opened Claude Code on my phone mid-task and /pickup didn't exist. The cause was a submodule nobody had initialized, and the fix taught me why --recursive is the wrong default.

Bridging shulkerbox across desktop and mobile Claude Code — and why capping submodule recursion at one level actually matters.

I picked up my phone to check on a job I'd started at my desk. I typed /pickup. Unknown command.

That shouldn't happen. /pickup is a skill I lean on constantly — session handover, priorities, picking up exactly where I left off. It works every time on desktop. On mobile, nothing.

The missing submodule

The skill lives in shulkerbox, a repo I keep separate from monospace.studio and pull in as a git submodule. The name is a Minecraft reference — a shulker box is a storage block that keeps its contents intact no matter where you carry it.

Mine hadn't travelled anywhere. It had never even been unpacked.

On this environment the directory existed in .gitmodules but the working copy was empty — a pointer to nothing. Worse: even after I initialized it, the skills still didn't show up.

Claude Code only discovers skills from .claude/skills/, and shulkerbox's actual skills live at shulkerbox/skills/core/pickup — a different path entirely. Two separate failures stacked on top of each other, and either one alone would have been enough to break it.

Bridging it

The fix was a symlink for every skill: .claude/skills/pickup → ../../shulkerbox/skills/core/pickup, and eight more like it for wrap-up, handover, sovereyn, and the rest. Nine lines, tracked in git — which meant carving an exception into a .gitignore rule that blanket-excluded .claude/ as an "ai tools" directory.

Then the harder question: how does the submodule get cloned in the first place, on a machine that's never seen this repo before? A SessionStart hook, gated to remote sessions only, running git submodule update --init the moment a session opens.

Recursion has a cost

My first pass used --recursive. It worked, and it also cloned a second, redundant copy of shulkerbox — because council, another submodule in this repo, vendors its own nested copy.

Fine today. But --recursive means the depth of what gets cloned is decided by repos I don't control, not by me.

I dropped it to one level. council/shulkerbox stays uninitialized unless someone explicitly asks for it, and I wrote the reasoning into AGENTS.md so the next agent — human or otherwise — doesn't reintroduce it without knowing why.

The actual point

None of this is exciting. It's a symlink, a gitignore exception, and a hook script. But it's the difference between an agent workflow that only exists on one laptop and one that survives switching devices mid-task — which is the whole premise of working this way in the first place.

Every post on this site about agents building things autonomously assumes the plumbing underneath just works. Usually I don't see it fail. This time I did, from my phone, mid-session — and fixing it took longer than everything else in that session put together.