hyperledger/fabric · error
found unknown private key type (%T) in msg signing
Error message
found unknown private key type (%T) in msg signing
What it means
Signer.Sign switches on the concrete type of the loaded private key, supporting *ecdsa.PrivateKey and ed25519.PrivateKey only. If the key is of any other type (e.g. *rsa.PrivateKey), it returns this error. Fabric's signer tooling deliberately restricts supported key algorithms.
Source
Thrown at cmd/common/signer/signer.go:105
return errors.Errorf("enrollment certificate should be a certificate, got a %s instead", strings.ToLower(bl.Type))
}
if _, err := x509.ParseCertificate(bl.Bytes); err != nil {
return errors.Errorf("enrollment certificate is not a valid x509 certificate: %v", err)
}
return nil
}
func (si *Signer) Sign(msg []byte) ([]byte, error) {
switch key := si.key.(type) {
// Fabric only supports ECDSA and ed25519 at the moment.
case *ecdsa.PrivateKey:
digest := util.ComputeSHA256(msg)
return signECDSA(si.key.(*ecdsa.PrivateKey), digest)
case ed25519.PrivateKey:
return ed25519.Sign(si.key.(ed25519.PrivateKey), msg), nil
default:
return nil, errors.Errorf("found unknown private key type (%T) in msg signing", key)
}
}
func loadPrivateKey(file string) (crypto.PrivateKey, error) {
b, err := os.ReadFile(file)
if err != nil {
return nil, errors.WithStack(err)
}
bl, _ := pem.Decode(b)
if bl == nil {
return nil, errors.Errorf("failed to decode PEM block from %s", file)
}
key, err := parsePrivateKey(bl.Bytes)
if err != nil {
return nil, err
}
return key, nil
}View on GitHub (pinned to 2736b63f8f)
Solutions
- Generate/use an ECDSA (P-256) or Ed25519 private key; e.g. openssl ecparam -name prime256v1 -genkey -noout -out key.pem
- Re-enroll with Fabric CA using an ECDSA key (csr.cn / key algorithm settings)
- Check the key header: 'BEGIN RSA PRIVATE KEY' means unsupported — replace it
- If this is a custom type in tests, extend the switch or use a supported key type
Example fix
// before: RSA key openssl genrsa -out key.pem 2048 // after: ECDSA key openssl ecparam -name prime256v1 -genkey -noout -out key.pem
Defensive patterns
Strategy: try-catch
Validate before calling
key, err := loadPrivateKey(keyPath)
if err != nil { return err }
switch k := key.(type) {
case *ecdsa.PrivateKey, ed25519.PrivateKey:
default:
return fmt.Errorf("unsupported key type %T in %s", k, keyPath)
} Type guard
func isSupportedKey(k crypto.PrivateKey) bool {
switch k.(type) {
case *ecdsa.PrivateKey, ed25519.PrivateKey:
return true
}
return false
} Try / catch
sig, err := signer.Sign(msg)
if err != nil {
if strings.Contains(err.Error(), "unknown private key type") {
return fmt.Errorf("replace key with ECDSA/Ed25519: %w", err)
}
return err
} Prevention
- Always generate ECDSA P-256 or Ed25519 keys for Fabric identities
- Reject RSA keys at provisioning time with a type check
- Document key algorithm requirements in enrollment tooling
When it happens
Trigger: Creating a Signer whose key file contains an RSA (or other unsupported) private key and calling Sign/Endorse/Send; a test or custom code path injecting a key of unexpected type into Signer.key.
Common situations: Using an RSA key issued by a CA or openssl by mistake instead of an ECDSA key; old materials generated with RSA; Fabric version changes dropping support for other key types.
Related errors
- found unknown private key type (%T) in PKCS#8 wrapping
- failed to parse private key: %v
- Unknown hashing algorithm type: %s
- failed marshaling ECDSA signature
- Internal error, BCCSP could not be initialized : %s
AI-assisted analysis of hyperledger/fabric@2736b63f8f (2026-09-04).
Data as JSON: /api/errors/a23c4abedb260f3c.
Report an issue: GitHub.