Change user.discoverable field to user.is_discoverable
[akkoma] / lib / pleroma / plugs / http_signature.ex
index d87fa52fa521b1df96df165491ddddf9073c7d3c..036e2a7739e0ca16fb05412d15249fa6594c2ab3 100644 (file)
@@ -1,9 +1,10 @@
 # Pleroma: A lightweight social networking server
-# Copyright © 2017-2019 Pleroma Authors <https://pleroma.social/>
+# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
 # SPDX-License-Identifier: AGPL-3.0-only
 
 defmodule Pleroma.Web.Plugs.HTTPSignaturePlug do
   import Plug.Conn
+  import Phoenix.Controller, only: [get_format: 1, text: 2]
   require Logger
 
   def init(options) do
@@ -15,24 +16,27 @@ defmodule Pleroma.Web.Plugs.HTTPSignaturePlug do
   end
 
   def call(conn, _opts) do
-    [signature | _] = get_req_header(conn, "signature")
+    if get_format(conn) == "activity+json" do
+      conn
+      |> maybe_assign_valid_signature()
+      |> maybe_require_signature()
+    else
+      conn
+    end
+  end
 
-    if signature do
+  defp maybe_assign_valid_signature(conn) do
+    if has_signature_header?(conn) do
       # set (request-target) header to the appropriate value
       # we also replace the digest header with the one we computed
-      conn =
-        conn
-        |> put_req_header(
-          "(request-target)",
-          String.downcase("#{conn.method}") <> " #{conn.request_path}"
-        )
+      request_target = String.downcase("#{conn.method}") <> " #{conn.request_path}"
 
       conn =
-        if conn.assigns[:digest] do
-          conn
-          |> put_req_header("digest", conn.assigns[:digest])
-        else
-          conn
+        conn
+        |> put_req_header("(request-target)", request_target)
+        |> case do
+          %{assigns: %{digest: digest}} = conn -> put_req_header(conn, "digest", digest)
+          conn -> conn
         end
 
       assign(conn, :valid_signature, HTTPSignatures.validate_conn(conn))
@@ -41,4 +45,21 @@ defmodule Pleroma.Web.Plugs.HTTPSignaturePlug do
       conn
     end
   end
+
+  defp has_signature_header?(conn) do
+    conn |> get_req_header("signature") |> Enum.at(0, false)
+  end
+
+  defp maybe_require_signature(%{assigns: %{valid_signature: true}} = conn), do: conn
+
+  defp maybe_require_signature(conn) do
+    if Pleroma.Config.get([:activitypub, :authorized_fetch_mode], false) do
+      conn
+      |> put_status(:unauthorized)
+      |> text("Request not signed")
+      |> halt()
+    else
+      conn
+    end
+  end
 end