Skip to main content
← Back to list
01Issue
BugClosedSwamp CLI
AssigneesNone

#297 Extension update rejects multiple .ts files extending the same target type within one local extension (regression)

Opened by 4chems · 5/8/2026

Summary

Multiple files under extensions/models/*.ts that each declare export const extension targeting the same model type are rejected as duplicate-type claims, even though they are part of the same local extension. This worked in 20260506.233640.0-sha.5729ac50 and broke in 20260508.001043.0-sha.3d787176.

Reproduction

In a swamp repo with no manifest.yaml at the root (so files are loaded as the implicit @local/operations extension), create two extension files targeting the same type:

// extensions/models/foo_a.ts
import { z } from "npm:zod@4";
export const extension = {
  type: "@me/some-model",
  methods: [{
    method_a: { description: "a", arguments: z.object({}),
                execute: async () => ({ dataHandles: [] }) },
  }],
};

// extensions/models/foo_b.ts
import { z } from "npm:zod@4";
export const extension = {
  type: "@me/some-model",
  methods: [{
    method_b: { description: "b", arguments: z.object({}),
                execute: async () => ({ dataHandles: [] }) },
  }],
};

Run any command that triggers extension discovery, e.g. swamp extension pull <any> or swamp extension update.

Expected

Both files contribute methods to @me/some-model. This is the documented "extending existing model types" pattern in the swamp-extension-model skill.

Actual

Type "@me/some-model" (kind=extension) is already claimed by @local/[email protected]
at /.../extensions/models/foo_a.ts. Cannot install @local/[email protected] at
/.../extensions/models/foo_b.ts — filesystem changes rolled back. Run
\`swamp extension rm @local/operations\` first if you intended to replace it.

The error blocks `swamp extension update` from updating any unrelated upstream extension. In our repo (5 files extending `@4chems/node-provisioner`), this prevents @keeb/docker and @keeb/ssh from being updated despite being unrelated to the conflict.

Environment

  • swamp 20260508.001043.0-sha.3d787176 (broken)
  • swamp 20260506.233640.0-sha.5729ac50 (works)
  • macOS 15.4.0 (Darwin 25.4.0), arm64
  • No `manifest.yaml` at repo root; extensions live in `extensions/models/*.ts` and are loaded as `@local/[email protected]`.

Notes

  • The previous version cleanly merged multiple files' `methods[]` arrays under the same target type. Documentation does not state that one local extension may only have one file per target type.
  • Consolidating all files into a single `.ts` is a workaround but a substantial refactor for codebases that organize extension methods by domain (e.g. firewall, KVM, RDP, snapshot — each in its own file for readability).
  • A backwards-compatible fix would be: when `extensionName` is the same for both conflicting paths, merge `methods[]` instead of rejecting.
02Bog Flow
OPENTRIAGEDIN PROGRESSCLOSED

Closed

5/8/2026, 11:59:43 AM

No activity in this phase yet.

03Sludge Pulse
Editable. Press Enter to edit.

stack72 commented 5/8/2026, 11:59:41 AM

hey @4chems

I am going to handle this as part of #269 as I am deep into refactoring this subsustem to make it less brittle

Paul

Sign in to post a ripple.