Ensure private keys are not logged

Ideally we’d use a single common HTTP request error format handling
for _all_ HTTP requests (including non-ActivityPub requests, e.g. NodeInfo).
But for the purpose of this commit this would create too much noise
and it is significant effort to go through all error pattern matches etc
too ensure it is still all correct or update as needed.
This commit is contained in:
Oneric 2025-09-06 00:00:00 +00:00
parent ff46e448c8
commit 2b4b68eba7
4 changed files with 31 additions and 2 deletions

View file

@ -16,6 +16,20 @@ defmodule Pleroma.HTTP.Middleware.HTTPSignature do
(Note: the third argument holds static middleware options from client creation)
"""
@doc """
If logging raw Tesla.Env use this if you wish to redact signing key details
"""
def redact_keys(env) do
case get_in(env, [:opts, :httpsig, :signing_key]) do
nil -> env
key -> put_in(env, [:opts, :httpsig, :signing_key], redact_key_details(key))
end
end
defp redact_key_details(%SigningKey{key_id: id}), do: id
defp redact_key_details(key), do: key
@impl true
def call(env, next, _options) do
env = maybe_sign(env)

View file

@ -417,6 +417,13 @@ def get_object(id) do
{:ok, %{status: code}} when code in [404, 410] ->
{:error, :not_found}
{:ok, %{status: code, headers: headers}} ->
{:error, {:http_error, code, headers}}
# connection/protocol-related error
{:ok, %Tesla.Env{} = env} ->
{:error, {:http_error, :connect, Pleroma.HTTP.Middleware.HTTPSignature.redact_keys(env)}}
{:error, e} ->
{:error, e}

View file

@ -69,7 +69,7 @@ def publish_one(
else
{_post_result, response} ->
unless params["unreachable_since"], do: Instances.set_unreachable(inbox)
{:error, response}
{:error, format_error_response(response)}
end
end
@ -82,6 +82,14 @@ def publish_one(%{"actor_id" => actor_id} = params) do
|> publish_one()
end
defp format_error_response(%Tesla.Env{status: code, headers: headers}),
do: {:http_error, code, headers}
defp format_error_response(%Tesla.Env{} = env),
do: {:http_error, :connect, Pleroma.HTTP.Middleware.HTTPSignature.redact_keys(env)}
defp format_error_response(response), do: response
defp blocked_instances do
Config.get([:instance, :quarantined_instances], []) ++
Config.get([:mrf_simple, :reject], [])

View file

@ -40,7 +40,7 @@ def perform(%Job{args: %{"op" => "publish_one", "module" => module_name, "params
# instance / actor was explicitly deleted; theres nothing to deliver to anymore
# since we dont know whether the whole instance is gone or just this actor,
# do NOT immediately mark the instance as unreachable
{:error, %{status: 410}} ->
{:error, {:http_error, 410, _}} ->
:ok
res ->