Pular para o conteúdo
ecdsa.com
Ruby openssl gemRuby

Mensagem de erro

Could not parse PKey (OpenSSL::PKey::PKeyError)

Também aparece como

  • OpenSSL::PKey::PKeyError: Could not parse PKey
  • Neither PUB key nor PRIV key (OpenSSL::PKey::RSAError)
  • invalid curve name (OpenSSL::PKey::ECError)

Sem tratamento, o Ruby imprime “…: Could not parse PKey (OpenSSL::PKey::PKeyError)”. Os construtores específicos de cada classe lançam `OpenSSL::PKey::RSAError` / `ECError` com textos próprios.

Ruby openssl gem — OpenSSL::PKey.read / OpenSSL::PKey::RSA.new / OpenSSL::PKey::EC.new

O que significa

O `OpenSSL::PKey.read` tentou todos os formatos de chave que o OpenSSL conhece (PEM e DER, pública e privada, criptografada com a senha informada) e nenhum funcionou. O Ruby não repassa o motivo específico do OpenSSL, então o mesmo texto cobre um PEM corrompido, uma frase secreta errada e dados que nem são uma chave. Os construtores específicos de cada algoritmo falham de forma parecida: `RSA.new` com “Neither PUB key nor PRIV key”, `EC.new` com “invalid curve name” (ele trata uma entrada que não consegue analisar como um nome de curva).

Por que acontece

Como corrigir

  1. 1.

    Restaurar as quebras de linha e conferir o que foi carregado

    Converta as sequências `\n` de volta, leia a chave uma única vez na inicialização e confirme o tipo dela e se ela é privada.

    ruby
    pem = ENV.fetch("JWT_PUBLIC_KEY").gsub("\\n", "\n")   # restore real newlines
    key = OpenSSL::PKey.read(pem)
    raise "expected a public EC key" if key.private? || !key.is_a?(OpenSSL::PKey::EC)
  2. 2.

    Armazenar chaves de várias linhas onde elas ficam intactas

    As credenciais criptografadas do Rails ou um arquivo de segredo montado preservam o PEM exatamente, ao contrário das variáveis de ambiente de uma linha só.

    ruby
    # Rails: keep multi-line keys in encrypted credentials instead of ENV
    # bin/rails credentials:edit
    #   jwt:
    #     public_key: |
    #       -----BEGIN PUBLIC KEY-----
    #       ...
    key = OpenSSL::PKey.read(Rails.application.credentials.dig(:jwt, :public_key))

Erros relacionados

Ver toda a base de erros de assinatura