package main import ( "encoding/pem" "fmt") // pemToDER returns the bytes of the first PEM block, which must carry the expected label.func pemToDER(data []byte, label string) ([]byte, error) { block, _ := pem.Decode(data) // the second result is whatever follows the block if block == nil { return nil, fmt.Errorf("no PEM block found") } if block.Type != label { return nil, fmt.Errorf("PEM block is %q, want %q", block.Type, label) } return block.Bytes, nil // already DER: PEM is base64 of DER plus a label} // derToPEM wraps DER bytes in a PEM block ("CERTIFICATE", "PRIVATE KEY", "PUBLIC KEY", ...).func derToPEM(der []byte, label string) []byte { return pem.EncodeToMemory(&pem.Block{Type: label, Bytes: der})} How it works
pem.Decode(data)returns the first*pem.Blockand the rest of the input;block.Bytesalready is the DER — 563 bytes for the certificate, 138 for the PKCS#8 key.- Check
block.Typeagainst the label you expect (CERTIFICATE,PRIVATE KEY,PUBLIC KEY…) before handing the bytes to a parser. pem.EncodeToMemory(&pem.Block{Type: label, Bytes: der})writes 64-character base64 lines; the round trip reproduces the original files exactly.- Parse the DER with the function that matches its label:
x509.ParseCertificate,x509.ParsePKCS8PrivateKey,x509.ParsePKIXPublicKey.
Gotchas
pem.Decodereturnsnilfor input without a PEM block — no error value — so check it, aspemToDERdoes (no PEM block found).x509.ParseECPrivateKeyreads only SEC1 (EC PRIVATE KEY); on PKCS#8 DER it fails withx509: failed to parse private key (use ParsePKCS8PrivateKey instead for this key format).pem.Decodereturns only the first block; loop on its second return value to reach every certificate of a bundle — the run finds both blocks of a two-certificate file that way.
Related recipes
- How to convert a certificate and a private key between PEM and DER in Python
- How to convert a certificate and a private key between PEM and DER in Rust
- How to convert a certificate and a private key between PEM and DER with OpenSSL
- How to export a public key as PEM in Go
- How to decode an X.509 certificate in Go