First
[anni] / lib / pleroma / bookmark.ex
1 # Pleroma: A lightweight social networking server
2 # Copyright © 2017-2022 Pleroma Authors <https://pleroma.social/>
3 # SPDX-License-Identifier: AGPL-3.0-only
4
5 defmodule Pleroma.Bookmark do
6   use Ecto.Schema
7
8   import Ecto.Changeset
9   import Ecto.Query
10
11   alias Pleroma.Activity
12   alias Pleroma.Bookmark
13   alias Pleroma.Repo
14   alias Pleroma.User
15
16   @type t :: %__MODULE__{}
17
18   schema "bookmarks" do
19     belongs_to(:user, User, type: FlakeId.Ecto.CompatType)
20     belongs_to(:activity, Activity, type: FlakeId.Ecto.CompatType)
21
22     timestamps()
23   end
24
25   @spec create(FlakeId.Ecto.CompatType.t(), FlakeId.Ecto.CompatType.t()) ::
26           {:ok, Bookmark.t()} | {:error, Changeset.t()}
27   def create(user_id, activity_id) do
28     attrs = %{
29       user_id: user_id,
30       activity_id: activity_id
31     }
32
33     %Bookmark{}
34     |> cast(attrs, [:user_id, :activity_id])
35     |> validate_required([:user_id, :activity_id])
36     |> unique_constraint(:activity_id, name: :bookmarks_user_id_activity_id_index)
37     |> Repo.insert()
38   end
39
40   @spec for_user_query(FlakeId.Ecto.CompatType.t()) :: Ecto.Query.t()
41   def for_user_query(user_id) do
42     Bookmark
43     |> where(user_id: ^user_id)
44     |> join(:inner, [b], activity in assoc(b, :activity))
45     |> preload([b, a], activity: a)
46   end
47
48   def get(user_id, activity_id) do
49     Bookmark
50     |> where(user_id: ^user_id)
51     |> where(activity_id: ^activity_id)
52     |> Repo.one()
53   end
54
55   @spec destroy(FlakeId.Ecto.CompatType.t(), FlakeId.Ecto.CompatType.t()) ::
56           {:ok, Bookmark.t()} | {:error, Changeset.t()}
57   def destroy(user_id, activity_id) do
58     from(b in Bookmark,
59       where: b.user_id == ^user_id,
60       where: b.activity_id == ^activity_id
61     )
62     |> Repo.one()
63     |> Repo.delete()
64   end
65 end