netbirdio/netbird · error

failed to extend revocation list: %w

Error message

failed to extend revocation list: %w

What it means

Returned when reposign.ExtendRevocationList fails (client/internal/updater/reposign/revocation.go:181). The function adds the key ID to the parsed RevocationList, stamps LastUpdated and a new ExpiresAt, signs with Ed25519, and json.Marshal's the list and signature. All inputs (root key, list, KeyID) were already validated by earlier steps, so like the create path this wraps internal marshal failures that stock code cannot realistically produce.

Source

Thrown at client/cmd/signer/revocation.go:148

	rlBytes, err := os.ReadFile(revocationListFile)
	if err != nil {
		return fmt.Errorf("failed to read revocation list file: %w", err)
	}

	rl, err := reposign.ParseRevocationList(rlBytes)
	if err != nil {
		return fmt.Errorf("failed to parse revocation list: %w", err)
	}

	kid, err := reposign.ParseKeyID(keyID)
	if err != nil {
		return fmt.Errorf("invalid key ID: %w", err)
	}

	newRLBytes, sigBytes, err := reposign.ExtendRevocationList(*privateRootKey, *rl, kid, expirationDuration)
	if err != nil {
		return fmt.Errorf("failed to extend revocation list: %w", err)
	}

	if err := writeOutputFiles(revocationListFile, revocationListFile+".sig", newRLBytes, sigBytes); err != nil {
		return fmt.Errorf("failed to write output files: %w", err)
	}

	cmd.Println("✅ Revocation list extended successfully")
	return nil
}

func handleVerifyRevocationList(cmd *cobra.Command, revocationListFile, signatureFile, publicRootKeyFile string) error {
	// Read revocation list file
	rlBytes, err := os.ReadFile(revocationListFile)
	if err != nil {
		return fmt.Errorf("failed to read revocation list file: %w", err)
	}

	// Read signature file

View on GitHub (pinned to 93e97f4bf1)

Solutions

  1. Read the %w chain to find the failing step (sign vs marshal list vs marshal signature)
  2. Re-run once to rule out a transient fault
  3. Diff client/internal/updater/reposign/revocation.go against upstream and revert local structural changes
  4. Report upstream with the full chain if stock code triggers it
Defensive patterns

Strategy: try-catch

Try / catch

if _, _, err := reposign.ExtendRevocationList(*privateRootKey, *rl, kid, expiration); err != nil {
    // inputs were all validated upstream; treat as internal failure and abort
    return fmt.Errorf("extend revocation list: %w", err)
}

Prevention

When it happens

Trigger: extend-revocation-list where reading and parsing all succeeded but json.Marshal of the extended list or the Signature bundle errors — only reachable via a modified reposign package or an anomalous runtime state.

Common situations: Nearly unreachable in the field; if seen, it points at a forked/altered reposign (for example an unmarshalable field added to RevocationList) rather than a usage mistake.

Related errors


AI-assisted analysis of netbirdio/netbird@93e97f4bf1 (2026-08-16). Data as JSON: /api/errors/2780663a607da52b. Report an issue: GitHub.