diff options
Diffstat (limited to 'lib')
| -rw-r--r-- | lib/pleroma/emails/admin_email.ex | 2 | ||||
| -rw-r--r-- | lib/pleroma/web/activity_pub/activity_pub.ex | 3 | ||||
| -rw-r--r-- | lib/pleroma/web/controller_helper.ex | 7 | ||||
| -rw-r--r-- | lib/pleroma/web/feed/feed_view.ex | 40 | ||||
| -rw-r--r-- | lib/pleroma/web/feed/tag_controller.ex | 41 | ||||
| -rw-r--r-- | lib/pleroma/web/feed/user_controller.ex (renamed from lib/pleroma/web/feed/feed_controller.ex) | 13 | ||||
| -rw-r--r-- | lib/pleroma/web/metadata/feed.ex | 2 | ||||
| -rw-r--r-- | lib/pleroma/web/metadata/utils.ex | 13 | ||||
| -rw-r--r-- | lib/pleroma/web/router.ex | 6 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/_activity.xml.eex | 2 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/_tag_activity.atom.eex | 51 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/_tag_activity.xml.eex | 15 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/_tag_author.atom.eex | 18 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/tag.atom.eex | 22 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/tag.rss.eex | 15 | ||||
| -rw-r--r-- | lib/pleroma/web/templates/feed/feed/user.xml.eex (renamed from lib/pleroma/web/templates/feed/feed/feed.xml.eex) | 6 | 
16 files changed, 233 insertions, 23 deletions
| diff --git a/lib/pleroma/emails/admin_email.ex b/lib/pleroma/emails/admin_email.ex index b15e4041b..d7dd4b2e0 100644 --- a/lib/pleroma/emails/admin_email.ex +++ b/lib/pleroma/emails/admin_email.ex @@ -17,7 +17,7 @@ defmodule Pleroma.Emails.AdminEmail do    end    defp user_url(user) do -    Helpers.feed_url(Pleroma.Web.Endpoint, :feed_redirect, user.id) +    Helpers.user_feed_url(Pleroma.Web.Endpoint, :feed_redirect, user.id)    end    def report(to, reporter, account, statuses, comment) do diff --git a/lib/pleroma/web/activity_pub/activity_pub.ex b/lib/pleroma/web/activity_pub/activity_pub.ex index 2e9d56ee5..1ac67b618 100644 --- a/lib/pleroma/web/activity_pub/activity_pub.ex +++ b/lib/pleroma/web/activity_pub/activity_pub.ex @@ -728,7 +728,6 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do        params        |> Map.put("user", reading_user)        |> Map.put("actor_id", user.ap_id) -      |> Map.put("whole_db", true)      recipients =        user_activities_recipients(%{ @@ -746,7 +745,6 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do        |> Map.put("type", ["Create", "Announce"])        |> Map.put("user", reading_user)        |> Map.put("actor_id", user.ap_id) -      |> Map.put("whole_db", true)        |> Map.put("pinned_activity_ids", user.pinned_activities)      params = @@ -773,7 +771,6 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do        params        |> Map.put("type", ["Create", "Announce"])        |> Map.put("instance", params["instance"]) -      |> Map.put("whole_db", true)      fetch_activities([Pleroma.Constants.as_public()], params, :offset)      |> Enum.reverse() diff --git a/lib/pleroma/web/controller_helper.ex b/lib/pleroma/web/controller_helper.ex index 9a4e322c9..e3d7a465b 100644 --- a/lib/pleroma/web/controller_helper.ex +++ b/lib/pleroma/web/controller_helper.ex @@ -76,8 +76,7 @@ defmodule Pleroma.Web.ControllerHelper do      end    end -  def try_render(conn, target, params) -      when is_binary(target) do +  def try_render(conn, target, params) when is_binary(target) do      case render(conn, target, params) do        nil -> render_error(conn, :not_implemented, "Can't display this activity")        res -> res @@ -87,4 +86,8 @@ defmodule Pleroma.Web.ControllerHelper do    def try_render(conn, _, _) do      render_error(conn, :not_implemented, "Can't display this activity")    end + +  @spec put_in_if_exist(map(), atom() | String.t(), any) :: map() +  def put_in_if_exist(map, _key, nil), do: map +  def put_in_if_exist(map, key, value), do: put_in(map, key, value)  end diff --git a/lib/pleroma/web/feed/feed_view.ex b/lib/pleroma/web/feed/feed_view.ex index bb1332fd3..334802e0a 100644 --- a/lib/pleroma/web/feed/feed_view.ex +++ b/lib/pleroma/web/feed/feed_view.ex @@ -13,21 +13,53 @@ defmodule Pleroma.Web.Feed.FeedView do    require Pleroma.Constants -  def prepare_activity(activity) do +  @spec pub_date(String.t() | DateTime.t()) :: String.t() +  def pub_date(date) when is_binary(date) do +    date +    |> Timex.parse!("{ISO:Extended}") +    |> pub_date +  end + +  def pub_date(%DateTime{} = date), do: Timex.format!(date, "{RFC822}") + +  def prepare_activity(activity, opts \\ []) do      object = activity_object(activity) +    actor = +      if opts[:actor] do +        Pleroma.User.get_cached_by_ap_id(activity.actor) +      end +      %{        activity: activity,        data: Map.get(object, :data), -      object: object +      object: object, +      actor: actor      }    end +  def most_recent_update(activities) do +    with %{updated_at: updated_at} <- List.first(activities) do +      NaiveDateTime.to_iso8601(updated_at) +    end +  end +    def most_recent_update(activities, user) do      (List.first(activities) || user).updated_at      |> NaiveDateTime.to_iso8601()    end +  def feed_logo do +    case Pleroma.Config.get([:feed, :logo]) do +      nil -> +        "#{Pleroma.Web.base_url()}/static/logo.png" + +      logo -> +        "#{Pleroma.Web.base_url()}#{logo}" +    end +    |> MediaProxy.url() +  end +    def logo(user) do      user      |> User.avatar_url() @@ -40,6 +72,8 @@ defmodule Pleroma.Web.Feed.FeedView do    def activity_title(%{data: %{"content" => content}}, opts \\ %{}) do      content +    |> Pleroma.Web.Metadata.Utils.scrub_html() +    |> Pleroma.Emoji.Formatter.demojify()      |> Formatter.truncate(opts[:max_length], opts[:omission])      |> escape()    end @@ -50,6 +84,8 @@ defmodule Pleroma.Web.Feed.FeedView do      |> escape()    end +  def activity_content(_), do: "" +    def activity_context(activity), do: activity.data["context"]    def attachment_href(attachment) do diff --git a/lib/pleroma/web/feed/tag_controller.ex b/lib/pleroma/web/feed/tag_controller.ex new file mode 100644 index 000000000..9accd0872 --- /dev/null +++ b/lib/pleroma/web/feed/tag_controller.ex @@ -0,0 +1,41 @@ +# Pleroma: A lightweight social networking server +# Copyright © 2017-2019 Pleroma Authors <https://pleroma.social/> +# SPDX-License-Identifier: AGPL-3.0-only + +defmodule Pleroma.Web.Feed.TagController do +  use Pleroma.Web, :controller + +  alias Pleroma.Config +  alias Pleroma.Web.ActivityPub.ActivityPub +  alias Pleroma.Web.Feed.FeedView + +  import Pleroma.Web.ControllerHelper, only: [put_in_if_exist: 3] + +  def feed(conn, %{"tag" => raw_tag} = params) do +    {format, tag} = parse_tag(raw_tag) + +    activities = +      %{"type" => ["Create"], "tag" => tag} +      |> put_in_if_exist("max_id", params["max_id"]) +      |> ActivityPub.fetch_public_activities() + +    conn +    |> put_resp_content_type("application/atom+xml") +    |> put_view(FeedView) +    |> render("tag.#{format}", +      activities: activities, +      tag: tag, +      feed_config: Config.get([:feed]) +    ) +  end + +  @spec parse_tag(binary() | any()) :: {format :: String.t(), tag :: String.t()} +  defp parse_tag(raw_tag) when is_binary(raw_tag) do +    case Enum.reverse(String.split(raw_tag, ".")) do +      [format | tag] when format in ["atom", "rss"] -> {format, Enum.join(tag, ".")} +      _ -> {"rss", raw_tag} +    end +  end + +  defp parse_tag(raw_tag), do: {"rss", raw_tag} +end diff --git a/lib/pleroma/web/feed/feed_controller.ex b/lib/pleroma/web/feed/user_controller.ex index d0e23007d..f5096834b 100644 --- a/lib/pleroma/web/feed/feed_controller.ex +++ b/lib/pleroma/web/feed/user_controller.ex @@ -2,13 +2,16 @@  # Copyright © 2017-2019 Pleroma Authors <https://pleroma.social/>  # SPDX-License-Identifier: AGPL-3.0-only -defmodule Pleroma.Web.Feed.FeedController do +defmodule Pleroma.Web.Feed.UserController do    use Pleroma.Web, :controller    alias Fallback.RedirectController    alias Pleroma.User    alias Pleroma.Web.ActivityPub.ActivityPub    alias Pleroma.Web.ActivityPub.ActivityPubController +  alias Pleroma.Web.Feed.FeedView + +  import Pleroma.Web.ControllerHelper, only: [put_in_if_exist: 3]    plug(Pleroma.Plugs.SetFormatPlug when action in [:feed_redirect]) @@ -27,7 +30,7 @@ defmodule Pleroma.Web.Feed.FeedController do    def feed_redirect(conn, %{"nickname" => nickname}) do      with {_, %User{} = user} <- {:fetch_user, User.get_cached_by_nickname(nickname)} do -      redirect(conn, external: "#{feed_url(conn, :feed, user.nickname)}.atom") +      redirect(conn, external: "#{user_feed_url(conn, :feed, user.nickname)}.atom")      end    end @@ -36,15 +39,15 @@ defmodule Pleroma.Web.Feed.FeedController do        activities =          %{            "type" => ["Create"], -          "whole_db" => true,            "actor_id" => user.ap_id          } -        |> Map.merge(Map.take(params, ["max_id"])) +        |> put_in_if_exist("max_id", params["max_id"])          |> ActivityPub.fetch_public_activities()        conn        |> put_resp_content_type("application/atom+xml") -      |> render("feed.xml", +      |> put_view(FeedView) +      |> render("user.xml",          user: user,          activities: activities,          feed_config: Pleroma.Config.get([:feed]) diff --git a/lib/pleroma/web/metadata/feed.ex b/lib/pleroma/web/metadata/feed.ex index 8043e6c54..ee48913a7 100644 --- a/lib/pleroma/web/metadata/feed.ex +++ b/lib/pleroma/web/metadata/feed.ex @@ -16,7 +16,7 @@ defmodule Pleroma.Web.Metadata.Providers.Feed do         [           rel: "alternate",           type: "application/atom+xml", -         href: Helpers.feed_path(Endpoint, :feed, user.nickname) <> ".atom" +         href: Helpers.user_feed_path(Endpoint, :feed, user.nickname) <> ".atom"         ], []}      ]    end diff --git a/lib/pleroma/web/metadata/utils.ex b/lib/pleroma/web/metadata/utils.ex index 589d11901..000bd9f66 100644 --- a/lib/pleroma/web/metadata/utils.ex +++ b/lib/pleroma/web/metadata/utils.ex @@ -21,15 +21,22 @@ defmodule Pleroma.Web.Metadata.Utils do    def scrub_html_and_truncate(content, max_length \\ 200) when is_binary(content) do      content +    |> scrub_html +    |> Emoji.Formatter.demojify() +    |> HtmlEntities.decode() +    |> Formatter.truncate(max_length) +  end + +  def scrub_html(content) when is_binary(content) do +    content      # html content comes from DB already encoded, decode first and scrub after      |> HtmlEntities.decode()      |> String.replace(~r/<br\s?\/?>/, " ")      |> HTML.strip_tags() -    |> Emoji.Formatter.demojify() -    |> HtmlEntities.decode() -    |> Formatter.truncate(max_length)    end +  def scrub_html(content), do: content +    def attachment_url(url) do      MediaProxy.url(url)    end diff --git a/lib/pleroma/web/router.ex b/lib/pleroma/web/router.ex index ef6e5a565..b5c1d85c7 100644 --- a/lib/pleroma/web/router.ex +++ b/lib/pleroma/web/router.ex @@ -527,8 +527,10 @@ defmodule Pleroma.Web.Router do      get("/notice/:id", OStatus.OStatusController, :notice)      get("/notice/:id/embed_player", OStatus.OStatusController, :notice_player) -    get("/users/:nickname/feed", Feed.FeedController, :feed) -    get("/users/:nickname", Feed.FeedController, :feed_redirect) +    get("/users/:nickname/feed", Feed.UserController, :feed, as: :user_feed) +    get("/users/:nickname", Feed.UserController, :feed_redirect, as: :user_feed) + +    get("/tags/:tag", Feed.TagController, :feed, as: :tag_feed)    end    scope "/", Pleroma.Web do diff --git a/lib/pleroma/web/templates/feed/feed/_activity.xml.eex b/lib/pleroma/web/templates/feed/feed/_activity.xml.eex index 514eacaed..ac8a75009 100644 --- a/lib/pleroma/web/templates/feed/feed/_activity.xml.eex +++ b/lib/pleroma/web/templates/feed/feed/_activity.xml.eex @@ -9,7 +9,7 @@    <ostatus:conversation ref="<%= activity_context(@activity) %>">      <%= activity_context(@activity) %>    </ostatus:conversation> -  <link ref="<%= activity_context(@activity) %>" rel="ostatus:conversation"/> +  <link href="<%= activity_context(@activity) %>" rel="ostatus:conversation"/>    <%= if @data["summary"] do %>      <summary><%= @data["summary"] %></summary> diff --git a/lib/pleroma/web/templates/feed/feed/_tag_activity.atom.eex b/lib/pleroma/web/templates/feed/feed/_tag_activity.atom.eex new file mode 100644 index 000000000..da4fa6d6c --- /dev/null +++ b/lib/pleroma/web/templates/feed/feed/_tag_activity.atom.eex @@ -0,0 +1,51 @@ +<entry> +    <activity:object-type>http://activitystrea.ms/schema/1.0/note</activity:object-type> +    <activity:verb>http://activitystrea.ms/schema/1.0/post</activity:verb> +     +    <%= render @view_module, "_tag_author.atom", assigns %> +     +    <id><%= @data["id"] %></id> +    <title><%= activity_title(@object, Keyword.get(@feed_config, :post_title, %{})) %></title> +    <content type="html"><%= activity_content(@object) %></content> + +  <%= if @activity.local do %> +    <link type="application/atom+xml" href='<%= @data["id"] %>' rel="self"/> +    <link type="text/html" href='<%= @data["id"] %>' rel="alternate"/> +  <% else %> +    <link type="text/html" href='<%= @data["external_url"] %>' rel="alternate"/> +  <% end %> + +    <published><%= @data["published"] %></published> +    <updated><%= @data["published"] %></updated> + +    <ostatus:conversation ref="<%= activity_context(@activity) %>"> +      <%= activity_context(@activity) %> +    </ostatus:conversation> +    <link href="<%= activity_context(@activity) %>" rel="ostatus:conversation"/> + +   <%= if @data["summary"] do %> +    <summary><%= @data["summary"] %></summary> +   <% end %> +   +    <%= for id <- @activity.recipients do %> +      <%= if id == Pleroma.Constants.as_public() do %> +        <link rel="mentioned" +          ostatus:object-type="http://activitystrea.ms/schema/1.0/collection" +          href="http://activityschema.org/collection/public"/> +      <% else %> +        <%= unless Regex.match?(~r/^#{Pleroma.Web.base_url()}.+followers$/, id) do %> +          <link rel="mentioned" +            ostatus:object-type="http://activitystrea.ms/schema/1.0/person" +            href="<%= id %>" /> +        <% end %> +      <% end %> +    <% end %> +   +    <%= for tag <- @data["tag"] || [] do %> +      <category term="<%= tag %>"></category> +    <% end %> + +    <%= for {emoji, file} <- @data["emoji"] || %{} do %> +      <link name="<%= emoji %>" rel="emoji" href="<%= file %>"/> +    <% end %> +</entry> diff --git a/lib/pleroma/web/templates/feed/feed/_tag_activity.xml.eex b/lib/pleroma/web/templates/feed/feed/_tag_activity.xml.eex new file mode 100644 index 000000000..295574df1 --- /dev/null +++ b/lib/pleroma/web/templates/feed/feed/_tag_activity.xml.eex @@ -0,0 +1,15 @@ +<item> +  <title><%= activity_title(@object, Keyword.get(@feed_config, :post_title, %{})) %></title> +   +   +  <guid isPermalink="true"><%= activity_context(@activity) %></guid> +  <link><%= activity_context(@activity) %></link> +  <pubDate><%= pub_date(@data["published"]) %></pubDate> +   +  <description><%= activity_content(@object) %></description> +  <%= for attachment <- @data["attachment"] || [] do %> +    <enclosure url="<%= attachment_href(attachment) %>" type="<%= attachment_type(attachment) %>"/> +  <% end %> +   +</item> + diff --git a/lib/pleroma/web/templates/feed/feed/_tag_author.atom.eex b/lib/pleroma/web/templates/feed/feed/_tag_author.atom.eex new file mode 100644 index 000000000..997c4936e --- /dev/null +++ b/lib/pleroma/web/templates/feed/feed/_tag_author.atom.eex @@ -0,0 +1,18 @@ +<author> +    <activity:object-type>http://activitystrea.ms/schema/1.0/person</activity:object-type> +    <id><%= @actor.ap_id %></id> +    <uri><%= @actor.ap_id %></uri> +    <name><%= @actor.nickname %></name> +    <summary><%= escape(@actor.bio) %></summary> +    <link rel="avatar" href="<%= User.avatar_url(@actor) %>"/> +    <%= if User.banner_url(@actor) do %> +      <link rel="header" href="<%= User.banner_url(@actor) %>"/> +    <% end %> +    <%= if @actor.local do %> +      <ap_enabled>true</ap_enabled> +    <% end %> +   +    <poco:preferredUsername><%= @actor.nickname %></poco:preferredUsername>         +    <poco:displayName><%= @actor.name %></poco:displayName> +    <poco:note><%= escape(@actor.bio) %></poco:note>     +</author> diff --git a/lib/pleroma/web/templates/feed/feed/tag.atom.eex b/lib/pleroma/web/templates/feed/feed/tag.atom.eex new file mode 100644 index 000000000..a288539ed --- /dev/null +++ b/lib/pleroma/web/templates/feed/feed/tag.atom.eex @@ -0,0 +1,22 @@ +<?xml version="1.0" encoding="UTF-8"?> + +<feed xml:lang="en-US" xmlns="http://www.w3.org/2005/Atom" +      xmlns:thr="http://purl.org/syndication/thread/1.0" +      xmlns:georss="http://www.georss.org/georss" +      xmlns:activity="http://activitystrea.ms/spec/1.0/" +      xmlns:media="http://purl.org/syndication/atommedia" +      xmlns:poco="http://portablecontacts.net/spec/1.0" +      xmlns:ostatus="http://ostatus.org/schema/1.0" +      xmlns:statusnet="http://status.net/schema/api/1/"> + +    <id><%= '#{tag_feed_url(@conn, :feed, @tag)}.rss' %></id> +    <title>#<%= @tag %></title> + +    <subtitle>These are public toots tagged with #<%= @tag %>. You can interact with them if you have an account anywhere in the fediverse.</subtitle> +    <logo><%= feed_logo() %></logo> +    <updated><%= most_recent_update(@activities) %></updated> +    <link rel="self" href="<%= '#{tag_feed_url(@conn, :feed, @tag)}.atom'  %>" type="application/atom+xml"/> +    <%= for activity <- @activities do %> +    <%= render @view_module, "_tag_activity.atom", Map.merge(assigns, prepare_activity(activity, actor: true)) %> +    <% end %> +</feed> diff --git a/lib/pleroma/web/templates/feed/feed/tag.rss.eex b/lib/pleroma/web/templates/feed/feed/tag.rss.eex new file mode 100644 index 000000000..eeda01a04 --- /dev/null +++ b/lib/pleroma/web/templates/feed/feed/tag.rss.eex @@ -0,0 +1,15 @@ +<?xml version="1.0" encoding="UTF-8"?> +<rss version="2.0" xmlns:webfeeds="http://webfeeds.org/rss/1.0"> +  <channel> + + +    <title>#<%= @tag %></title> +    <description>These are public toots tagged with #<%= @tag %>. You can interact with them if you have an account anywhere in the fediverse.</description> +    <link><%= '#{tag_feed_url(@conn, :feed, @tag)}.rss' %></link> +    <webfeeds:logo><%= feed_logo() %></webfeeds:logo> +    <webfeeds:accentColor>2b90d9</webfeeds:accentColor> +    <%= for activity <- @activities do %> +    <%= render @view_module, "_tag_activity.xml", Map.merge(assigns, prepare_activity(activity)) %> +    <% end %> +  </channel> +</rss> diff --git a/lib/pleroma/web/templates/feed/feed/feed.xml.eex b/lib/pleroma/web/templates/feed/feed/user.xml.eex index 5ae36d345..d274c08ae 100644 --- a/lib/pleroma/web/templates/feed/feed/feed.xml.eex +++ b/lib/pleroma/web/templates/feed/feed/user.xml.eex @@ -6,16 +6,16 @@    xmlns:poco="http://portablecontacts.net/spec/1.0"    xmlns:ostatus="http://ostatus.org/schema/1.0"> -  <id><%= feed_url(@conn, :feed, @user.nickname) <> ".atom" %></id> +  <id><%= user_feed_url(@conn, :feed, @user.nickname) <> ".atom" %></id>    <title><%= @user.nickname <> "'s timeline" %></title>    <updated><%= most_recent_update(@activities, @user) %></updated>    <logo><%= logo(@user) %></logo> -  <link rel="self" href="<%= '#{feed_url(@conn, :feed, @user.nickname)}.atom' %>" type="application/atom+xml"/> +  <link rel="self" href="<%= '#{user_feed_url(@conn, :feed, @user.nickname)}.atom' %>" type="application/atom+xml"/>    <%= render @view_module, "_author.xml", assigns %>    <%= if last_activity(@activities) do %> -    <link rel="next" href="<%= '#{feed_url(@conn, :feed, @user.nickname)}.atom?max_id=#{last_activity(@activities).id}' %>" type="application/atom+xml"/> +    <link rel="next" href="<%= '#{user_feed_url(@conn, :feed, @user.nickname)}.atom?max_id=#{last_activity(@activities).id}' %>" type="application/atom+xml"/>    <% end %>    <%= for activity <- @activities do %> | 
