ipfs/kubo · error

pinning service not available

Error message

pinning service not available

What it means

The `ipfs pin` commands (rm/ls) require a pinning subsystem on the node. When the node runs with a remote pinning service only (no local pinning, e.g. `Pinning` is nil because the node was constructed without local pinning support), kubo returns this error. Local pin operations are impossible without it.

Source

Thrown at core/commands/pin/pin.go:471

		cmds.StringOption(pinTypeOptionName, "t", "The type of pinned keys to list. Can be \"direct\", \"indirect\", \"recursive\", or \"all\".").WithDefault("all"),
		cmds.BoolOption(pinQuietOptionName, "q", "Output only the CIDs of pins."),
		cmds.StringOption(pinNameOptionName, "n", "Limit returned pins to ones with names that contain the value provided (case-sensitive, partial match). Implies --names=true."),
		cmds.BoolOption(pinStreamOptionName, "s", "Enable streaming of pins as they are discovered."),
		cmds.BoolOption(pinNamesOptionName, "Include pin names in the output (slower, disabled by default)."),
	},
	Run: func(req *cmds.Request, res cmds.ResponseEmitter, env cmds.Environment) error {
		api, err := cmdenv.GetApi(env, req)
		if err != nil {
			return err
		}

		n, err := cmdenv.GetNode(env)
		if err != nil {
			return err
		}

		if n.Pinning == nil {
			return fmt.Errorf("pinning service not available")
		}

		typeStr, _ := req.Options[pinTypeOptionName].(string)
		stream, _ := req.Options[pinStreamOptionName].(bool)
		displayNames, _ := req.Options[pinNamesOptionName].(bool)
		name, _ := req.Options[pinNameOptionName].(string)

		// Validate name filter
		if err := cmdutils.ValidatePinName(name); err != nil {
			return err
		}

		mode, ok := pin.StringToMode(typeStr)
		if !ok {
			return fmt.Errorf("invalid type '%s', must be one of {direct, indirect, recursive, all}", typeStr)
		}

		// For backward compatibility, we accumulate the pins in the same output type as before.

View on GitHub (pinned to 329838acdf)

Solutions

  1. Run the command against a full kubo daemon with local pinning enabled.
  2. Use the remote pinning API instead: `ipfs pin remote add/rm/ls --service=<name>` for service-based pinning.
  3. If embedding kubo, ensure the node constructor wires a pinning implementation into the CoreAPI.
  4. Check `ipfs config Pinning` to confirm which pinning services are configured locally.

Example fix

// before
client.Request("pin/rm", cid).Send(ctx)
// after — remote pinning path for service-only nodes
client.Request("pin/remote/rm").Option("service", "pinata").Arguments(cid).Send(ctx)
Defensive patterns

Strategy: fallback

Validate before calling

idOut, err := client.Request("id").Send(ctx) // full daemons support local pinning
// for service-only nodes, prefer pin/remote endpoints

Try / catch

if _, err := client.Request("pin/rm", cid).Send(ctx); err != nil {
    if strings.Contains(err.Error(), "pinning service not available") {
        return client.Request("pin/remote/rm").Option("service", svc).Arguments(cid).Send(ctx)
    }
    return err
}

Prevention

When it happens

Trigger: Running `ipfs pin rm <cid>` (or ls) against a node whose CoreAPI `Pinning` is nil — a node configured without a local pinning implementation (e.g. certain cluster/remote-only setups).

Common situations: Running pin commands against a node that delegates pinning to ipfs-cluster or a remote pinning service; stripped-down library-embedded nodes (kubo-as-a-library) built without pinning.

Related errors


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