ipfs/kubo · error
pin check failed: %w
Error message
pin check failed: %w
What it means
FilterPinned checks each CID against the pinset before block removal. If the pinner itself fails (e.g. the underlying blockstore/datastore read of pin metadata errors), it emits a RemovedBlock whose Error wraps that failure with 'pin check failed' on the output channel and aborts filtering (returns nil). The removal operation typically surfaces this as a per-block error rather than a returned error.
Source
Thrown at blocks/blockstoreutil/remove.go:82
out <- &RemovedBlock{Hash: c.String(), Error: err}
} else if !opts.Quiet {
out <- &RemovedBlock{Hash: c.String()}
}
}
}()
return out, nil
}
// FilterPinned takes a slice of Cids and returns it with the pinned Cids
// removed. If a Cid is pinned, it will place RemovedBlock objects in the given
// out channel, with an error which indicates that the Cid is pinned.
// This function is used in RmBlocks to filter out any blocks which are not
// to be removed (because they are pinned).
func FilterPinned(ctx context.Context, pins pin.Pinner, out chan<- any, cids []cid.Cid) []cid.Cid {
stillOkay := make([]cid.Cid, 0, len(cids))
res, err := pins.CheckIfPinned(ctx, cids...)
if err != nil {
out <- &RemovedBlock{Error: fmt.Errorf("pin check failed: %w", err)}
return nil
}
for _, r := range res {
if !r.Pinned() {
stillOkay = append(stillOkay, r.Key)
} else {
out <- &RemovedBlock{
Hash: r.Key.String(),
Error: errors.New(r.String()),
}
}
}
return stillOkay
}
View on GitHub (pinned to 329838acdf)
Solutions
- Run `ipfs repo fsck` / `ipfs pin ls` to verify pin metadata integrity, then retry the removal
- Check datastore health (disk space, permissions) and repair or restore the repo datastore
- Stop concurrent pin/gc operations that may race, then retry
- Inspect the wrapped inner error (the %w chain) with errors.Is/As to identify the datastore-level cause
Defensive patterns
Strategy: try-catch
Validate before calling
// pre-check pins before removal
res, err := pins.CheckIfPinned(ctx, cids...)
if err != nil { return fmt.Errorf("pinset unreadable: %w", err) } Try / catch
cids, errCh := blockstoreutil.FilterPinned(ctx, pins, out, cids)
for rb := range out {
if b, ok := rb.(*blockstoreutil.RemovedBlock); ok && b.Error != nil {
if strings.HasPrefix(b.Error.Error(), "pin check failed") {
// datastore/pin metadata failure: fsck repo, retry
}
}
} Prevention
- Run `ipfs repo fsck` when pin metadata is suspected corrupt
- Avoid racing `pin rm`/`pin add` with `repo gc`/`block rm`
- Monitor disk space and datastore health
When it happens
Trigger: Calling RmBlocks/FilterPinned when pins.CheckIfPinned returns an error — corrupted pin metadata in the datastore, direct/pin-mode datastore failures, or passing a closed/invalid pinset. Also triggered when the caller's `out` channel consumer cannot keep up (blocks removal mid-check).
Common situations: 'ipfs pin ls' or 'ipfs repo gc' after a datastore corruption; disk full or levelds/badger I/O errors while reading pin records; concurrent 'ipfs pin rm' racing with 'ipfs repo gc'; running repo operations on a repo from an incompatible newer version.
Related errors
- r.String()
- assets: could load Asset '%s': %s
- ipfs api address could not be found
- unexpected redirect
- unsupported file type '%s'
AI-assisted analysis of ipfs/kubo@329838acdf (2026-09-03).
Data as JSON: /api/errors/ea8e02bb1f44a933.
Report an issue: GitHub.