PKCS#8 PEM, not this host's own base64. The mesh delivers a PEM certificate beside it and every TLS server there is reads PEM: nginx's ssl_certificate_key, Go's LoadX509KeyPair, openssl s_server. Stored the other way the file was intact, present, correctly permissioned, and unusable — the machine failed at the moment something connected, which the lab found by connecting. A key in the old encoding is refused by name rather than called corrupt: it is replaced by enrolling again, and that is a different remedy from a damaged file.
72 lines
2.2 KiB
Go
72 lines
2.2 KiB
Go
package identity
|
|
|
|
import (
|
|
"crypto/ed25519"
|
|
"crypto/x509"
|
|
"encoding/pem"
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
"testing"
|
|
)
|
|
|
|
// The whole reason the file exists is that something else reads it.
|
|
//
|
|
// A key in this host's own encoding is intact, unusable, and indistinguishable from a working one
|
|
// until the moment a client connects — the mesh delivers the certificate, the file is there with
|
|
// the right permissions, and the server will not start.
|
|
func TestTheServingKeyIsWrittenInTheFormatAServerReads(t *testing.T) {
|
|
made, err := GenerateServingKey()
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
path := filepath.Join(t.TempDir(), "serving.key")
|
|
if err := WriteServingKey(path, made); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
raw, err := os.ReadFile(path)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
block, _ := pem.Decode(raw)
|
|
if block == nil {
|
|
t.Fatalf("the serving key is not PEM, so nothing serving TLS can read it:\n%s", raw)
|
|
}
|
|
parsed, err := x509.ParsePKCS8PrivateKey(block.Bytes)
|
|
if err != nil {
|
|
t.Fatalf("the serving key is PEM and not a key: %v", err)
|
|
}
|
|
// And it is the key that was written, not merely a key — a file that round-trips through the
|
|
// wrong half would certify a public key the machine cannot prove it holds.
|
|
if _, isEd25519 := parsed.(ed25519.PrivateKey); !isEd25519 {
|
|
t.Fatalf("the serving key is a %T", parsed)
|
|
}
|
|
read, err := LoadServingKey(path)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if read.Public != made.Public {
|
|
t.Fatal("the key read back is not the key written, so the mesh would certify the wrong one")
|
|
}
|
|
}
|
|
|
|
// The old encoding is refused by name, because the remedy is different from a corrupt file and
|
|
// the difference is invisible from the outside.
|
|
func TestAServingKeyInTheOldEncodingIsNamedRatherThanCalledCorrupt(t *testing.T) {
|
|
made, err := GenerateServingKey()
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
path := filepath.Join(t.TempDir(), "serving.key")
|
|
if err := os.WriteFile(path, []byte(made.Private+"\n"), 0o600); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
_, err = LoadServingKey(path)
|
|
if err == nil {
|
|
t.Fatal("a key nothing can serve with was accepted")
|
|
}
|
|
if !strings.Contains(err.Error(), "enrolling again") {
|
|
t.Fatalf("refused without naming the remedy: %v", err)
|
|
}
|
|
}
|