ipfs/kubo · error

cannot add named links to a non-UnixFS dag-pb node; pass --a

Error message

cannot add named links to a non-UnixFS dag-pb node; pass --allow-non-unixfs to skip validation

What it means

ObjectAPI.AddLink links by name into a dag-pb node, but named links are only safe on UnixFS nodes (directory/hash metadata must stay consistent). When the target node's data cannot be parsed as a UnixFS node, the API refuses to edit it and suggests the --allow-non-unixfs escape hatch, which skips validation (with known HAMT-shard consistency risks, see issue 7190).

Source

Thrown at core/coreapi/object.go:70

		return path.ImmutablePath{}, err
	}

	basePb, ok := baseNd.(*dag.ProtoNode)
	if !ok {
		return path.ImmutablePath{}, dag.ErrNotProtobuf
	}

	// This command operates at the dag-pb level via dagutils.Editor, which
	// only manipulates ProtoNode links without updating UnixFS metadata.
	// Only plain UnixFS Directory nodes are safe to mutate this way.
	// File nodes: adding links corrupts Blocksizes, content lost on read-back.
	// HAMTShard nodes: bitfield not updated, shard trie becomes inconsistent.
	// https://specs.ipfs.tech/unixfs/#pbnode-links-name
	// https://github.com/ipfs/kubo/issues/7190
	if !options.SkipUnixFSValidation {
		fsNode, err := ft.FSNodeFromBytes(basePb.Data())
		if err != nil {
			return path.ImmutablePath{}, fmt.Errorf(
				"cannot add named links to a non-UnixFS dag-pb node; " +
					"pass --allow-non-unixfs to skip validation")
		}
		switch fsNode.Type() {
		case ft.TDirectory:
			// plain directories: safe, no link-count metadata to desync
		case ft.THAMTShard:
			return path.ImmutablePath{}, fmt.Errorf(
				"cannot add links to a HAMTShard at the dag-pb level " +
					"(would corrupt the HAMT bitfield); use 'ipfs files' " +
					"commands instead, or pass --allow-non-unixfs to override")
		default:
			return path.ImmutablePath{}, fmt.Errorf(
				"cannot add named links to a UnixFS %s node, "+
					"only Directory nodes support link addition at the dag-pb level "+
					"(see https://specs.ipfs.tech/unixfs/)",
				fsNode.Type())
		}

View on GitHub (pinned to 329838acdf)

Solutions

  1. Verify the target CID is a UnixFS directory (created via `ipfs add` or MFS), not a raw dag-pb node.
  2. Inspect with `ipfs dag get <cid>` or `ipfs files stat` to confirm the node type.
  3. If you explicitly need to edit a non-UnixFS dag-pb node, pass --allow-non-unixfs (SkipUnixFSValidation=true) and accept the consistency risk.
  4. Use MFS (`ipfs files`) to build/edit directory structures instead of raw object patching.

Example fix

// before
ipfs object patch <raw-dagpb-cid> add-link name <target>  # fails
// after
# only if you know the node is not UnixFS:
ipfs object patch --allow-non-unixfs <cid> add-link name <target>
Defensive patterns

Strategy: validation

Validate before calling

node, err := api.Dag().Get(ctx, path.New(targetCid))
if err != nil {
    return err
}
pb, ok := node.(ipldprime.Node) // inspect Data via dag-pb codec
// confirm the node is a UnixFS directory before AddLink; otherwise use MFS

Try / catch

ip, err := api.Object().AddLink(ctx, base, name, child, opts)
if err != nil && strings.Contains(err.Error(), "non-UnixFS dag-pb") {
    // rebuild the directory with MFS or retry with --allow-non-unixfs
}

Prevention

When it happens

Trigger: Calling AddLink on a dag-pb node whose Data field is not valid UnixFS protobuf (raw dag-pb node, custom data, or empty), with SkipUnixFSValidation=false (the default).

Common situations: Manually crafted dag-pb nodes added via the DAG API, then edited with `ipfs object patch <cid> add-link`; HAMT-shard directories with deserialized data; nodes created by other tools with non-UnixFS Data.

Related errors


AI-assisted analysis of ipfs/kubo@329838acdf (2026-09-03). Data as JSON: /api/errors/90473690210f8e2b. Report an issue: GitHub.