# `Clir.Openssl.X509`

Lectura de certificados X.509 vía `:public_key.pkix_decode_cert/2` (formato OTP interno).

# `otp_cert`

```elixir
@type otp_cert() :: tuple()
```

Certificado en formato OTP (`:OTPCertificate`).

# `fingerprint`

```elixir
@spec fingerprint(otp_cert(), :md5 | :sha | :sha256) :: String.t()
```

Huella del DER del certificado. `algo` puede ser `:md5`, `:sha` o `:sha256`.

# `from_der`

```elixir
@spec from_der(binary()) :: {:ok, otp_cert()} | {:error, term()}
```

Parsea certificado DER y devuelve la tupla OTP.

# `from_file`

```elixir
@spec from_file(String.t()) :: {:ok, otp_cert()} | {:error, term()}
```

Lee certificado desde archivo (.cer DER o PEM).

# `from_pem`

```elixir
@spec from_pem(String.t()) :: {:ok, otp_cert()} | {:error, term()}
```

Parsea certificado PEM.

# `get_pem`

```elixir
@spec get_pem(binary()) :: {:ok, String.t()} | {:error, term()}
```

Convierte certificado DER a PEM, o lee un archivo si `der_or_path` es una ruta existente.

# `issuer`

```elixir
@spec issuer(otp_cert()) :: String.t()
```

Issuer en formato estilo LDAP.

# `no_certificado`

```elixir
@spec no_certificado(otp_cert()) :: String.t()
```

Número de certificado SAT: si el serial en hex son pares ASCII de dígitos (`0`–`9`), se decodifica a string decimal; si no, se devuelve el hex.

# `serial`

```elixir
@spec serial(otp_cert()) :: String.t()
```

Número de serie en hexadecimal (mayúsculas), como string.

# `subject`

```elixir
@spec subject(otp_cert()) :: String.t()
```

Subject en formato estilo LDAP (CN=..., O=..., ...).

# `validity`

```elixir
@spec validity(otp_cert()) :: %{not_before: DateTime.t(), not_after: DateTime.t()}
```

Vigencia como `%{not_before: DateTime.t(), not_after: DateTime.t()}` en UTC.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
